如何使用Sneakers(RabbitMQ客户端)实现消息最多重入队列5次?
获取Sneakers消息失败尝试次数的解决方案
旧版Sneakers(2015年前后)支持的全局配置方式已被移除,当前版本需要通过消息头(Headers)手动追踪失败次数,实现根据次数决定重入或拒绝消息的逻辑,具体步骤如下:
1. 修改Worker方法签名,获取消息属性
Sneakers的work方法可接收三个参数:消息内容、投递信息、消息属性。通过第三个参数properties可以读取消息的头信息,从中提取失败次数。
2. 实现失败次数追踪与重入逻辑
在异常捕获时,递增失败次数,根据阈值决定是手动重发消息(更新头信息)还是直接拒绝:
修改后的Worker代码:
module Workers class BB include Sneakers::Worker # 若需消息持久化,可添加 durable: true 等队列配置 from_queue :backbone def work(msg, delivery_info, properties) # 从消息头获取失败次数,默认值为0 failed_attempts = (properties.dig(:headers, 'failed_attempts') || 0).to_i # ... 你的消息处理逻辑 ... ack! rescue StandardError => e log :fatal, e.message log :fatal, e.backtrace failed_attempts += 1 if failed_attempts <= 5 # 手动发布消息到原队列,更新失败次数头信息 publish( msg, routing_key: delivery_info.routing_key, headers: { 'failed_attempts' => failed_attempts }, # 继承原消息的持久化属性(如果原消息是持久化的) persistent: properties[:persistent] ) # 确认原消息已处理,避免重复消费 ack! else # 超过重试阈值,拒绝消息(不会重回队列) reject! end end end end
3. 关键说明
- 不用
requeue!的原因:原生requeue!会直接将消息放回原队列,但无法修改消息头信息,因此无法追踪失败次数。手动发布消息可在头信息中携带次数数据,实现循环计数。 - 持久化配置:如果业务需要消息重启RabbitMQ后不丢失,需确保队列配置
durable: true,且发布消息时继承原消息的persistent属性。 - 计数准确性:每次重发都会更新头信息中的次数,确保每次消费都能拿到准确的失败尝试次数。
内容的提问来源于stack exchange,提问作者alilland
相关产品推荐
相关产品推荐

