RabbitMQ:发布服务器确认中的奇怪行为
我是RabbitMQ新手,我使用Publisher Confirm确保消息成功传递 但是我面临一个奇怪的行为,当我发布一条消息并获取一个sequenceNumber时,函数channel.basicaks被激发n次,其中n是DeliveryTag,因此如果此消息的DeliveryTag是5,那么函数channel.basicaks被激发5次 这是我的代码:RabbitMQ:发布服务器确认中的奇怪行为,rabbitmq,message-queue,rabbitmqctl,Rabbitmq,Message Queue,Rabbitmqctl,我是RabbitMQ新手,我使用Publisher Confirm确保消息成功传递 但是我面临一个奇怪的行为,当我发布一条消息并获取一个sequenceNumber时,函数channel.basicaks被激发n次,其中n是DeliveryTag,因此如果此消息的DeliveryTag是5,那么函数channel.basicaks被激发5次 这是我的代码: IModel channel = _customRabbitMQ.GetChannel();
IModel channel = _customRabbitMQ.GetChannel();
IBasicProperties properties = _customRabbitMQ.GetBasicProperties();
ulong sequenceNumber = channel.NextPublishSeqNo;
message.SequenceNumber = sequenceNumber.ToString();
_context.Messages.Update(message);
await _context.SaveChangesAsync();
try
{
_customRabbitMQ.AddOutstandingConfirm(sequenceNumber, message.Id);
channel.BasicPublish(message.ExchangeName, message.RoutingKey, properties, Encoding.UTF8.GetBytes(JsonSerializer.Serialize(message)));
Console.WriteLine("Message Published");
}
catch (Exception ex)
{
// TODO: log to custom logger here
Console.WriteLine($"Error => {ex.Message}");
}
channel.BasicAcks += async (sender, ea) =>
{
try
{
Console.WriteLine("Message Confirmed");
using var scope = _provider.CreateScope();
var _context = scope.ServiceProvider.GetService<Data.DataContext>();
var _customRabbitMQ = scope.ServiceProvider.GetService<CustomRabbitMQ>();
Guid messageId = _customRabbitMQ.GetOutstandingConfirm(ea.DeliveryTag);
Message message = await _context.Messages.Where(m => m.Id == messageId).FirstOrDefaultAsync();
message.Status = MessageStatuses.INQUEUE;
_context.Messages.Update(message);
await _context.SaveChangesAsync();
_customRabbitMQ.RemoveOutstandingConfirm(ea.DeliveryTag);
}
catch (Exception ex)
{
Console.WriteLine($"Error => {ex.Message}");
}
};
channel.BasicNacks += (sender, ea) =>
{
Console.WriteLine("Message Not Confirmed");
_customRabbitMQ.RemoveOutstandingConfirm(ea.DeliveryTag);
};
}
IModel通道=_customRabbitMQ.GetChannel();
IBasicProperties=\u customRabbitMQ.GetBasicProperties();
ulong sequenceNumber=channel.NextPublishSeqNo;
message.SequenceNumber=SequenceNumber.ToString();
_context.Messages.Update(message);
wait_context.SaveChangesAsync();
尝试
{
_customRabbitMQ.AddOutstandingConfirm(sequenceNumber,message.Id);
channel.BasicPublish(message.ExchangeName、message.RoutingKey、properties、Encoding.UTF8.GetBytes(JsonSerializer.Serialize(message));
Console.WriteLine(“消息已发布”);
}
捕获(例外情况除外)
{
//TODO:在此处登录到自定义记录器
WriteLine($“Error=>{ex.Message}”);
}
channel.BasicAcks+=异步(发送方,ea)=>
{
尝试
{
Console.WriteLine(“消息已确认”);
使用var scope=_provider.CreateScope();
var_context=scope.ServiceProvider.GetService();
var_customRabbitMQ=scope.ServiceProvider.GetService();
Guid messageId=\u customRabbitMQ.GetOutstandingConfirm(ea.DeliveryTag);
Message Message=wait_context.Messages.Where(m=>m.Id==messageId).FirstOrDefaultAsync();
message.Status=MessageStatuses.INQUEUE;
_context.Messages.Update(message);
wait_context.SaveChangesAsync();
_customRabbitMQ.RemoveOutstandingConfirm(ea.DeliveryTag);
}
捕获(例外情况除外)
{
WriteLine($“Error=>{ex.Message}”);
}
};
channel.BasicNacks+=(发送方,ea)=>
{
Console.WriteLine(“消息未确认”);
_customRabbitMQ.RemoveOutstandingConfirm(ea.DeliveryTag);
};
}
那么,为什么会发生这种情况,如何阻止它,并使它只确认一次
提前感谢。我认为问题在于每次发布消息时都要初始化侦听器。
因此,当您发布带有
DT=1
的消息时,您可以通过添加channel.BasicAck+=fun
来创建一个侦听器,当添加带有DT=2
的消息时,您可以创建另一个侦听器,因此当DT_2上的确认返回时,它将被推送到两个侦听器,这就解释了为什么你会收到一个带有相同号码的送货标签的确认。我还不完全清楚这个问题,但可能选项multiple
会有所帮助,实际上,“multiple”标志总是“false”,但是函数调用了多次。