【发布时间】:2018-01-29 17:46:23
【问题描述】:
我目前正在运行一个基本的 RabbitMQ 主题发布,每 3 秒发布一次。
我的班级是这样的:
import com.rabbitmq.client.*;
import java.io.IOException;
public class EmitLogTopic {
private static final String EXCHANGE_NAME = "topic_logs";
@Scheduled(fixedRate = 3000)
public void publish(String[] argv)
throws Exception {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("localhost");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
channel.exchangeDeclare(EXCHANGE_NAME, "topic");
String routingKey = getRouting(argv);
String message = getMessage(argv);
channel.basicPublish(EXCHANGE_NAME, routingKey, null, message.getBytes());
System.out.println(" [x] Sent '" + routingKey + "':'" + message + "'");
channel.close();
connection.close();
}
//...
}
我希望每次运行方法发布时,它都会发布,然后通道和连接都关闭,防止每 3 秒有一个新的通道和连接卡在内存中。
但是,当我查看我的 RabbitMQ 管理界面(在概览页面)时,全局计数部分显示连接总数和通道总数都在不断增加。
最终,由于达到了 Socket 限制和内存限制,我的应用程序崩溃了。
所以看起来 close() 并没有删除使用的通道和连接,并且仍然将它们保留在内存中,最终导致所有内存被消耗。在通道和连接上使用什么正确方法来确保他们不会这样做?
【问题讨论】:
-
你不能重复使用相同的连接和通道,而不是每次都创建它们吗?
-
您应该保持一个通道打开并将其用于多条消息。
-
@Berger 嗨,我最初是使用 AMQP 执行此操作的,它在应用程序首次启动时创建连接和通道。但是,我的新要求是我必须能够即时更改主机、用户名和密码,而不必停止应用程序。
-
@OrangeDog 由于这个限制,我明确地创建了连接,因此在创建时我可以设置连接的本地主机、用户名和密码,而无需停止应用程序。
-
您应该只覆盖相关的工厂和/或配置,而不是完全重新实现
spring-amqp。
标签: java spring rabbitmq connection channel