对于我使用弹簧启动,弹簧批量和弹簧集成的应用程序。
我的问题是,在启动时,当所有内容都自动配置并自动连线时,连接到RabbitMQ的spring-integration @MessageEndpoints开始处理其队列中的可用消息。根据收到的消息,这些@MessageEndpoints试图通过它自动连线的JobRegistery来启动特定的弹簧批处理作业。
由于所有自动配置,并非所有作业都已注册到使用过的JobRegistery! (几秒钟之后他们会)。
将所有弹出批处理作业注册到JobRegistery后,应启动@MessageEndpoints。这可能吗?也许以为ContextRefreshEvent?
答案 0 :(得分:0)
我只看了代码,问题似乎是AutomaticJobRegistrar
使用上下文刷新事件来加载作业;它应该真正实现SmartLifecycle
并从“早期”阶段开始。
spring集成组件实现SmartLifecycle
,入站端点(例如Rabbit端点)在后期开始。
我建议您打开批处理的JIRA - AutomaticJobRegistrar
代码中有一个TODO:
// TODO: With Spring 3 a SmartLifecycle is started automatically
作为解决方法,您可以在入站适配器上将autoStartup
设置为false
,并使用您自己的事件侦听器在上下文刷新事件中启动它们。
听众应该实施Ordered
; AutomaticJobRegistrar
为Ordered.LOWEST_PRECEDENCE
,因此您希望以更高的优先级(较低优先级)运行。
答案 1 :(得分:0)
Gary Russell感谢你为正确的方向努力!我解决了它如下:
public static void main(final String[] args) {
ConfigurableApplicationContext context = SpringApplication.run(SpringBatchApplication.class, args);
startInboundChannelAdapters(context);
}
private static void startInboundChannelAdapters(ConfigurableApplicationContext context) {
Map<String, AmqpInboundChannelAdapter> adapters = context.getBeansOfType(AmqpInboundChannelAdapter.class);
adapters.forEach((name, adapter) -> {
if (!adapter.isRunning()) {
adapter.start();
}
});
}