RabbitMQ Stomp over websocket:无法检索排队的消息

Posted

技术标签:

【中文标题】RabbitMQ Stomp over websocket:无法检索排队的消息【英文标题】:RabbitMQ Stomp over websocket : Unable to retrieve queued messages 【发布时间】:2016-06-04 15:23:38 【问题描述】:

我正在使用 RabbitMQ Stomp 的持久订阅(文档here)。根据文档,当客户端使用相同的 id 重新连接(订阅)时,他应该得到所有排队的消息。但是,即使消息在服务器端排队,我也无法取回任何东西。以下是我正在使用的代码:

RabbitMQ 版本:3.6.0

客户端代码:

var sock;
var stomp;
var messageCount = 0;
var stompConnect = function() 

sock = new SockJS(options.url);

stomp = Stomp.over(sock);
stomp.connect(, function(frame) 
debug('Connected: ', frame);
console.log(frame);

var id = stomp.subscribe('<url>' + options.source + "." + options.type + "." + options.id, function(d) 
    console.log(messageCount);
    messageCount = messageCount + 1;
, 'auto-delete' : false, 'persistent' : true , 'id' : 'unique_id', 'ack' : 'client');
, function(err) 
console.log(err);
debug('error', err, err.stack);
setTimeout(stompConnect, 10);
);
;

服务器代码:

public class WebSocketConfig extends AbstractWebSocketMessageBrokerConfigurer 
    @Override
    public void configureMessageBroker(final MessageBrokerRegistry config) 
        config.enableStompBrokerRelay("<endpoint>", "<endpoint>").setRelayHost(host)
        .setSystemLogin(username).setSystemPasscode(password).setClientLogin(username)
                .setClientPasscode(password);
    

    @Override
    public void registerStompEndpoints(final StompEndpointRegistry registry) 
        registry.addEndpoint("<endpoint>").setAllowedOrigins("*").withSockJS();
    

我正在执行的步骤:

在客户端运行脚本,发送订阅请求。 在服务器端创建了一个队列(名称为 stomp-subscription-*),所有消息都被推送到队列中,并且客户端能够流式传输这些消息。 杀死脚本,这会导致断开连接。服务器日志显示客户端已断开连接,消息开始排队。 使用相同的 ID 再次运行脚本。它以某种方式设法连接到服务器,但是,服务器没有返回任何消息。该队列上的消息计数保持不变(此外,RabbitMQ 管理控制台不显示该队列的任何使用者)。 10 秒后,连接断开,并在客户端日志上打印以下内容:

哎呀!与

的连接丢失
服务器也显示相同的消息(即客户端断开连接)。如客户端代码所示,它会在 10 秒后尝试建立连接,然后再次重复相同的循环。

我尝试了以下方法:

    删除了'ack' : 'client' 标头。这导致所有消息都从队列中排出,但是没有任何消息到达客户端。我在通过this SO 回答后添加了这个标题。 在增加 messageCount 之前,在函数中添加了d.ack();。这会导致服务器端出错,因为它会在会话关闭后尝试确认消息(由于断开连接)。

另外,在某些情况下,当我重新连接时排队的消息数量少于 100 条时,我能够获取所有消息。但是,一旦超过 100,就什么也没有发生(不确定这是否与问题有关)。

不知道是服务器端还是客户端问题。有输入吗?

【问题讨论】:

您解决问题了吗?我正在尝试同样的事情并面临确切的问题。连接中断时发布的消息,在重新建立连接后永远不会传递给客户端。 【参考方案1】:

最后,我能够找到(并解决)问题。我们使用 nginx 作为代理,它的 proxy_buffering 设置为 on(默认值),请查看文档 here。

它是这样说的:

启用缓冲后,nginx 会收到来自代理的响应 服务器尽快,将其保存到由服务器设置的缓冲区中 proxy_buffer_size 和 proxy_buffers 指令。

因此,消息被缓冲(延迟),导致断开连接。我们尝试绕过 nginx,它工作正常,然后我们禁用了代理缓冲,现在它似乎工作正常,即使使用 nginx 代理也是如此。

【讨论】:

我没有代理。所以,不要认为这是我们的问题。无论如何,感谢您的回复

以上是关于RabbitMQ Stomp over websocket:无法检索排队的消息的主要内容,如果未能解决你的问题,请参考以下文章

Spring 4 websocket + stomp + rabbitmq 和集群

Spring stomp over websocket SubscribeMapping 不起作用

RabbitMQ - 使用 AMQP 和 STOMP 连接到同一个交易所

Spring STOMP over Websocket - “私人”消息传递

SockJS over stomp 使用 angular2 和 spring boot

春天引导+的Spring Web插槽+ RabbitMQ的STOMP网站