stompjs + rabbitmq - 创建自动删除队列

4
我们正在使用RabbitMQ + StompJS(带有SockJS和Spring Websocket作为中间件)来促进通过websockets广播消息。一切正常,除了无论我们尝试什么,StompJS都会创建非自动删除的队列,这意味着我们最终会拥有大量队列。
我们现在正在处理一个策略,清除几个小时后不活动的队列,但是我们宁愿只有在所有客户端断开连接后才终止的自动删除队列。
我们已经尝试设置标题auto_deleteauto-deleteautoDelete和我们可以找到的每个其他可能的咒语。
如果我们停止并检查在发送之前的帧(在StompJS源代码深处的最低层),我们可以看到这些标头存在。但是,它们似乎没有传递到RabbitMQ(或者它只是不在“SUBSCRIPTION”命令上查看它们??),并将它们创建为非自动删除。
有趣的是,如果我们预先手动创建自动删除的队列,则StompJS注册调用会出错,因为请求的SUBSCRIBE需要非自动删除。这表明是StompJS(或SockJS)明确指定为非自动删除,但我们检查过源代码,排除了这种可能性。
那么,百万美元的问题是:我们如何使用StompJS实现自动删除队列?拜托了,请提供帮助并感谢您的支持 :) 示例注册
function reg(dest, callback, headers){
    stomp.subscribe(dest, callback, headers);
}

function cb(payload){
    console.log(JSON.parse(payload.body));
}

reg('/queue/foobar', cb, {});

设置细节 RabbitMQ 3.5.2和StompJS 2.3.3

** 注意 ** 如果我直接订阅交换机 (例如 /exchange/foo 或 /topic/foo),交换机将被定义为自动删除。只有队列不是自动删除。


你使用的是哪个stompjs和sockjs实现?我通过谷歌搜索看到了好几个。 - Derick Bailey
@DerickBailey 好主意。已添加信息。 - David Welch
你修复过这个问题吗?我遇到了完全相同的问题。 - ajames
我还没有跟进,但我已经提交了一个工单,显然更新的版本可以实现这一点。请参见 https://github.com/rabbitmq/rabbitmq-stomp/issues/24#issuecomment-137896165 - David Welch
2个回答

0

0

我正在生产中使用StompJS / RabbitMQ,但我没有遇到这个问题。我不能确定你的问题是什么,但我可以详细说明我的设置,希望你能发现一些可能有所帮助的差异。

  • 我正在运行Rabbit MQ 3.0.1。
  • 我正在使用SockJS 0.3.4,我记得使用GitHub上更新的版本时遇到了一些问题,但不幸的是我没有记录笔记,所以我不确定问题是什么。
  • 我正在使用StompJS 2.3.4

由于某些原因,我在此处不会详细介绍 - 我已禁用WebSockets传输,通过将所有其他传输列入白名单来实现。

以下是一些简化的代码,显示了我如何连接:

var socket = new SockJS(config.stompUrl, null, { protocols_whitelist: ['xdr-streaming', 'xhr-streaming', 'iframe-eventsource', 'iframe-htmlfile', 'xdr-polling', 'xhr-polling', 'iframe-xhr-polling', 'jsonp-polling'] });
var client = Stomp.over(socket);
client.debug = function () { };
client.heartbeat.outgoing = 0;
client.heartbeat.incoming = 0;

client.connect(config.rabbitUsername, config.rabbitPassword, function () {
   onConnected();
}, function () {
   reconnect(d);
}, '/');

这是我断开连接的方法:

// close the socket first, otherwise STOMP throws an error on disconnect
socket.close();

client.disconnect(function () {
   isConnected = false;
});

这是我订阅的方式(在我的onConnected函数内执行):

client.subscribe('/topic/{routing-key}', function (x) {
   var message = JSON.parse(x.body);

   // do stuff with message
});

我的第一条建议是尝试我列出的客户端库的特定版本。我曾经遇到过一些问题,但这些版本对我来说可以正常工作。


所以你的例子可以正常工作,并且在大多数情况下都能很好地工作,但在我的场景中,我需要 stomp 客户端直接绑定到队列(而不是交换机)。据我所知,如果目标是 '/queue/foo',RabbitMQ 将定义队列,但它不是自动删除的(如果之前存在自动删除队列,则会抛出错误)。 - David Welch
啊 - 抱歉,我没有注意到那个细节。好吧。 - Jim Liddell

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接