2017-03-04 85 views
0

在spring-batch中,可以通过ExecutionContext在各个步骤之间传递数据。您可以在一个步骤中设置细节,并在下一步中检索。我们在春季融合中是否有这种类型的东西?如何在弹簧集成组件之间传递信息?

我的用例是我必须从ftp位置获取文件,然后根据特定的业务逻辑对其进行拆分,然后对其进行处理。根据文件名将导出客户端ID。此客户端ID将用于分离器,服务激活器和聚合器组件。

从我在春季的新手级别的专业知识中,我找不到任何能够帮助我分享特定运行状态的内容。我想知道春季整合是否以某种方式提供了这种状态共享上下文。

请让我知道是否有办法在春季背景下做。

回答

0

在Spring集成应用中存在的状态共享没有单一的ExecutionContext。相反,正如Gary Russel所述,每条消息都会在其有效载荷或其标题中携带所有信息。

如果您使用Spring Integration Java DSL并希望通过邮件头来传输clientId,则可以使用enrichHeader变压器。提供了一个HeaderEnricherSpec,它可以接受一个函数,它为指定的头返回动态确定的值。随着你的使用情况,这可能是这样的:

return IntegrationFlows 
    .from(/*ftp source*/) 
    .enrichHeaders(e -> e.headerFunction("clientId", this::deriveClientId)) 
    ./*split, aggregate, etc the file according to clientId*/ 

,其中deriveClientId方法可能是一个排序:

private String deriveClientId(Message<File> fileMessage) { 
    String fileName = fileMessage.getHeaders().get(FileHeaders.FILENAME, String.class); 
    String clientId = /*some other logic for deriving clientId from*/fileName; 
    return clientId; 
} 

FILENAME报头由FTP消息源提供)

当您需要访问下游流程中某处的clientId标头时,您可以使用与上述文件名相同的方法:

String clientId = message.getHeaders().get("clientId", String.class); 

但请确保message仍包含此类标头,因为它可能已在中间流项目中的某处丢失。如果您在某些时候手动构建消息并进一步发送消息,可能会发生这种情况。为了不失去从前面的消息,你可以在建筑过程中复制它们的任何标题:

Message<PayloadType> newMessage = MessageBuilder 
     .withPayload(payloadValue) 
     .copyHeaders(precedingMessage.getHeaders()) 
     .build(); 

请注意,消息头和Spring集成不变。这意味着您不能只添加或更改现有消息的标题。您应该创建一条新消息或为此目的使用HeaderEnricher。上面介绍了两种方法的例子。