Spring Integration:文件轮询内存消耗

时间:2017-07-11 08:38:29

标签: spring-integration poller

我使用Poller跟随InboundChannelAdapter每隔30秒处理一次文件。文件并不大但我意识到即使没有文件出现,内存消耗也会持续增长。

@Bean
@InboundChannelAdapter(value = "flowFileInChannel" ,poller = @Poller(fixedDelay ="30000", maxMessagesPerPoll = "1"))
public MessageSource<File> flowInboundFileAdapter(@Value("${integration.path}") File directory) {
    FileReadingMessageSource source = new FileReadingMessageSource();
    source.setDirectory(directory);
    source.setFilter(flowPathFileFilter);
    source.setUseWatchService(true);
    source.setScanEachPoll(true);
    source.setAutoCreateDirectory(false);
    return source;
}

enter image description here

每次轮询后是否有内部队列未清除?如何配置以避免占用内存。

在深入挖掘后,看起来下面的Spring IntegrationFlow处理来自InboundChannelDapter的数据在每次文件轮询后都会占用内存。在我评论中间部分后,内存消耗似乎稳定(而不是增加消耗)。现在我想知道我们如何强制Spring IntegrationFlows在它们通过不同的通道后(即在下面的最后一个通道之后)清除那些消息和标题

public IntegrationFlow incomingLocateFlow(){
        return IntegrationFlows.from(locateIncomingChannel())

//                .split("locateItemSplitter","split")
//                .transform(locateItemEnrichmentTransformer)
//                .transform(locateRequestTransformer)
//                .aggregate(new Consumer<AggregatorSpec>() {                        // 32
//
//                    @Override
//                    public void accept(AggregatorSpec aggregatorSpec) {
//                        aggregatorSpec.processor(locateRequestProcessor, null);                // 33
//                    }
//
//                }, null)
//                .transform(locateIncomingResultTransformer)
//                .transform(locateExceptionReportWritingHandler)
                .channel(locateIncomingCompleteChannel())
                .get();
    }

1 个答案:

答案 0 :(得分:0)

确实有AcceptOnceFileListFilter代码如下:

private final Queue<F> seen;

private final Set<F> seenSet = new HashSet<F>();

在每次调查中,这些内部集合都会补充新文件。

为此,您可以考虑将FileSystemPersistentAcceptOnceFileListFilter与持久MetadataStore实现一起使用以避免内存consumption

还要考虑使用一些工具来分析内存内容。您可能在flowFileInChannel下游有其他内容。

<强>更新

由于您使用.aggregate(),因此它绝对是默认使用内存的点。这是因为有SimpleMessageStore来保留用于分组的消息。此外,还有一个expireGroupsUponCompletion(boolean)选项,默认为false。因此,即使在成功发布后,某些信息仍然在MessageStore。这就是你的记忆不时消耗的方式。

默认情况下,该选项为false,以便在我们丢弃已完成组的延迟消息时设置逻辑。当它为true时,您可以为同一correlationKey形成新组。

Reference Manual中查看有关聚合器的更多信息。