springboot 整合 rabbitmq時,容器中注入exchange,queue Bean但rabbitmq server 未建立的原因
阿新 • • 發佈:2021-02-09
技術標籤:rabbitmqspring cloud alibaba
public class RabbitAdmin implements AmqpAdmin, ApplicationContextAware, ApplicationEventPublisherAware,
BeanNameAware, InitializingBean
RabbitAdmin implements InitializingBean
在afterPropertiesSet方法中發現,建立queue exchange 的原理
this.connectionFactory.addConnectionListener (connection -> {
if (!initializing.compareAndSet(false, true)) {
// If we are already initializing, we don't need to do it again...
return;
}
try {
/*
* ...but it is possible for this to happen twice in the same ConnectionFactory (if more than
* one concurrent Connection is allowed). It's idempotent, so no big deal (a bit of network
* chatter). In fact it might even be a good thing: exclusive queues only make sense if they are
* declared for every connection. If anyone has a problem with it: use auto-startup="false".
*/
if (this.retryTemplate != null) {
this.retryTemplate.execute(c -> {
initialize();
return null;
});
}
else {
initialize();
}
}
finally {
initializing.compareAndSet(true, false);
}
});
initialize 中的
this.rabbitTemplate.execute (channel -> {
declareExchanges(channel, exchanges.toArray(new Exchange[exchanges.size()]));
declareQueues(channel, queues.toArray(new Queue[queues.size()]));
declareBindings(channel, bindings.toArray(new Binding[bindings.size()]));
return null;
});
因為
/**
* A listener for connection creation and closing.
*
* @author Dave Syer
* @author Gary Russell
*
*/
@FunctionalInterface
public interface ConnectionListener
rabbitmq connection 啟動時不會建立。因此ConnectionListener不會被觸發
initialize 不會被呼叫
解決方案
@Bean
ApplicationRunner runner(ConnectionFactory cf) {
return args -> cf.createConnection().close();
}
OR
@RabbitListener(queues = “temp”)
使其觸發ConnectionListener
Reference:
https://stackoverflow.com/questions/64857283/spring-amqp-rabbitmq-connection-is-not-created-on-application-startup