如何在轮询目录时防止重复的 Spring Integration 服务激活

2023-11-29

我有一个 Spring Integration 目录轮询器:

<task:executor id="filePollingExecutor" pool-size="1" />
<int:channel id="inboundFilesChannel" datatype="java.io.File" />
<int-file:inbound-channel-adapter id="inboundFilesAdapter" 
      channel="inboundFilesChannel"
      directory="/my/files/queue"
      prevent-duplicates="true">
  <int:poller id="poller" fixed-delay="1000" 
              max-messages-per-poll="1" 
              task-executor="filePollingExecutor" />
</int-file:inbound-channel-adapter>

为了响应目录中出现的文件,我有一个服务激活器,它调用服务上的方法:

不幸的是,我发现当文件到达时该服务始终被调用两次。最初我认为这是因为有多个执行程序线程,但您可能会注意到上面,我尝试通过将轮询器绑定到池大小为 1 的 taskExecutor 来解决这个问题。

我发现我可以通过增加民意调查之间的延迟来解决这个问题。我认为关键是它比处理一个文件所需的时间要长。

<int:poller id="poller" fixed-delay="10000" 
            max-messages-per-poll="100" 
            task-executor="filePollingExecutor" />

然而,这感觉像是一个拼凑而不是解决方案。

我是否缺少一些应该用来防止重复的配置?

可能值得注意的是我确实尝试过使用nio-locker,但问题是处理的一部分涉及发送附有文件的电子邮件。文件锁阻止了这种操作的完成,因为文件在锁定期间不再可读。


这个答案是基于加里·拉塞尔在上面评论中的提示。

双重处理文件的原因是根配置和 Web 配置都在初始化文件系统侦听器,因此每个文件处理两次。

我避免在多个上下文中使用文件侦听器的方法如下。

首先定义一个 Web 配置,它仅选取“web”包下的类。

@Configuration
@ComponentScan(basePackages = { "com.myapp.web" })
@EnableWebMvc
public class WebConfig extends WebMvcConfigurerAdapter {
    @Override
    public void configureDefaultServletHandling(
            DefaultServletHandlerConfigurer configurer) {
        configurer.enable();
    }
}

创建单独的根配置,仅加载不在“web”包中的bean。 IE。

@Configuration
@ComponentScan(basePackages = { "com.myapp.services" })
public class ServicesConfig {
}

配置中的另一个因素需要一些时间才能解决,那就是我的 servlet 过滤器和 Web 安全配置需要位于“根”上下文而不是 Web 上下文中。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何在轮询目录时防止重复的 Spring Integration 服务激活 的相关文章

随机推荐