Introduction to Spring Integration – 春天集成简介

最后修改: 2016年 12月 13日

1. Introduction


This article will introduce the core concepts of Spring Integration primarily through small, practical examples.

本文将主要通过小型的实际例子来介绍Spring Integration的核心概念

Spring Integration provides a lot of powerful components that can greatly enhance the interconnectivity of systems and processes within an enterprise architecture.

Spring Integration提供了很多强大的组件,可以大大增强企业架构中系统和流程的互连性。

It embodies the some of the finest and most popular design patterns, helping developers avoid rolling their own.


We will take a look at the specific needs that this library fills in an enterprise application and why it is advisable over some of its alternatives. We will also look at some available tools for further simplifying the development of Spring Integration-based applications.


2. Setup



You can download the latest versions of Spring Integration Core and the Spring Integration File Support from Maven Central.


3. The Messaging Pattern


One of the foundational patterns in this library is Messaging. The pattern is centered around messages – discrete payloads of data that move from an originating system or process to one or multiple systems or processes via predefined channels.


Historically, the pattern arose as the most flexible way to integrate multiple disparate systems in a way that:


  • Almost completely decouples the systems involved in the integration
  • Allows participant systems in the integration to be completely agnostic of each others underlying protocols, formatting, or other implementation details
  • Encourages the development and reuse of components involved in the integration

4. Messaging Integration in Action


Let’s consider a basic example that copies a MPEG video file from a designated folder to another configured folder:


public class BasicIntegrationConfig{
    public String INPUT_DIR = "the_source_dir";
    public String OUTPUT_DIR = "the_dest_dir";
    public String FILE_PATTERN = "*.mpeg";

    public MessageChannel fileChannel() {
        return new DirectChannel();

    @InboundChannelAdapter(value = "fileChannel", poller = @Poller(fixedDelay = "1000"))
    public MessageSource<File> fileReadingMessageSource() {
        FileReadingMessageSource sourceReader= new FileReadingMessageSource();
        sourceReader.setDirectory(new File(INPUT_DIR));
        sourceReader.setFilter(new SimplePatternFileListFilter(FILE_PATTERN));
        return sourceReader;

    @ServiceActivator(inputChannel= "fileChannel")
    public MessageHandler fileWritingMessageHandler() {
        FileWritingMessageHandler handler = new FileWritingMessageHandler(new File(OUTPUT_DIR));
        return handler;

The code above configures a service activator, an integration channel, and an inbound channel adapter.


We’ll examine each of these component types in greater detail shortly. The @EnableIntegration annotation designates this class as a Spring Integration configuration.


Let’s start our Spring Integration application context:

让我们开始我们的Spring Integration应用上下文。

public static void main(String... args) {
    AbstractApplicationContext context 
      = new AnnotationConfigApplicationContext(BasicIntegrationConfig.class);
    Scanner scanner = new Scanner(;
    System.out.print("Please enter q and press <enter> to exit the program: ");
    while (true) {
       String input = scanner.nextLine();
       if("q".equals(input.trim())) {

The main method above starts up the integration context; it also accepts the “q” character input from the command line to exit the program. Let us examine the components in more detail.


5. Spring Integration Components


5.1. Message


The org.springframework.integration.Message interface defines the spring Message: the unit of data transfer within a Spring Integration context.

org.springframework.integration.Message 接口定义了spring Message:Spring Integration上下文中的数据传输单位。

public interface Message<T> {
    T getPayload();
    MessageHeaders getHeaders();

It defines accessors to two key elements:


  • Message headers, essentially a key-value container that can be used to transmit metadata, as defined in the org.springframework.integration.MessageHeaders class
  • The message payload, which is the actual data that is of value to be transferred — in our use-case, the video file is the payload

5.2. Channel


A channel in Spring Integration (and indeed, EAI) is the basic plumbing in an integration architecture. It’s the pipe by which messages are relayed from one system to another.

Spring Integration(乃至EAI)中的通道是集成架构中的基本管道。它是消息从一个系统传递到另一个系统的管道。

You can think of it as a literal pipe through which an integrated system or process can push messages to (or receive messages from) other systems.


Channels in Spring Integration come in various flavors, depending on your need. They are largely configurable and usable out of the box, without any custom code, but should you have custom needs, there’s a robust framework available.

根据你的需要,Spring Integration中的通道有多种形式。它们在很大程度上是可配置的,可以开箱即用,不需要任何自定义代码,但如果你有自定义需求,也有一个强大的框架可以使用。

Point-to-Point (P2P) channels are used to establish 1-to-1 communication lines between systems or components. One component publishes a message to the channel so another can pick it up. There can be only one component at each end of the channel.


As we have seen, configuring a channel is as simple as returning an instance of DirectChannel:


public MessageChannel fileChannel1() {
    return new DirectChannel();

public MessageChannel fileChannel2() {
    return new DirectChannel();

public MessageChannel fileChannel3() {
    return new DirectChannel();

Here, we have defined three separate channels all identified by the name of their respective getter methods.


Publish-Subscribe (Pub-Sub) channels are used to establish a one-to-many communication line between systems or components. This will allow us to publish to all 3 of the direct channels that we created earlier.


So following our example, we can replace the P2P channel with a pub-sub channel:


public MessageChannel pubSubFileChannel() {
    return new PublishSubscribeChannel();

@InboundChannelAdapter(value = "pubSubFileChannel", poller = @Poller(fixedDelay = "1000"))
public MessageSource<File> fileReadingMessageSource() {
    FileReadingMessageSource sourceReader = new FileReadingMessageSource();
    sourceReader.setDirectory(new File(INPUT_DIR));
    sourceReader.setFilter(new SimplePatternFileListFilter(FILE_PATTERN));
    return sourceReader;

We have now converted the inbound channel adapter to publish to a Pub-Sub channel. This will allow us to send the files that are being read from the source folder to multiple destinations.


5.3. Bridge


A bridge in Spring Integration is used to connect two message channels or adapters if for any reason they can’t connect directly.

在Spring Integration中,如果两个消息通道或适配器由于某种原因不能直接连接,那么桥接器就是用来连接它们的。

In our case, we can use a bridge to connect our Pub-Sub channel to three different P2P channels (because P2P and Pub-Sub channels can’t be connected directly):


@BridgeFrom(value = "pubSubFileChannel")
public MessageChannel fileChannel1() {
    return new DirectChannel();

@BridgeFrom(value = "pubSubFileChannel")
public MessageChannel fileChannel2() {
    return new DirectChannel();

@BridgeFrom(value = "pubSubFileChannel")
public MessageChannel fileChannel3() {
    return new DirectChannel();

The above bean configuration now bridges the pubSubFileChannel to three P2P channels. The @BridgeFrom annotation is what defines a bridge and can be applied to any number of channels that need to subscribe to the Pub-Sub channel.

上面的bean配置现在将pubSubFileChannel与三个P2P通道连接起来。@BridgeFrom 注解是定义桥梁的东西,可以应用于需要订阅Pub-Sub通道的任何数量的通道。

We can read the above code as “create a bridge from the pubSubFileChannel to fileChannel1, fileChannel2, and fileChannel3 so that messages from pubSubFileChannel can be fed to all three channels simultaneously.”

我们可以将上述代码理解为 “从pubSubFileChannelfileChannel1、fileChannel2和fileChannel3创建一个桥梁,以便pubSubFileChannel的消息可以同时输入到所有三个通道。”

5.4. Service Activator


The Service Activator is any POJO that defines the @ServiceActivator annotation on a given method. This allows us to execute any method on our POJO when a message is received from an inbound channel, and it allows us to write messages to an outward channel.


In our example, our service activator receives a file from the configured input channel and writes it to the configured folder.


5.5. Adapter


The Adapter is an enterprise integration pattern-based component that allows one to “plug-in” to a system or data source. It is almost literally an adapter as we know it from plugging into a wall socket or electronic device.

适配器是一个基于企业集成模式的组件,允许人们 “插入 “到一个系统或数据源。它几乎就是我们所知的插在墙上的插座或电子设备上的适配器。

It allows reusable connectivity to otherwise “black-box” systems like databases, FTP servers and messaging systems such as JMS, AMQP, and social networks like Twitter. The ubiquity of the need to connect to these systems means that adapters are very portable and reusable (in fact there’s a small catalog of adapters, freely available and ready to use by anyone).

它允许可重复使用的连接到其他 “黑盒 “系统,如数据库、FTP 服务器和消息传递系统,如 JMS、AMQP 和 Twitter 等社交网络。连接这些系统的需求无处不在,这意味着适配器是非常可移植和可重用的(事实上,有一个小型的适配器目录,任何人都可以免费使用)。

Adapters fall into two broad categories — inbound and outbound.


Let’s examine these categories in the context of the adapters in use in our sample scenario:


Inbound adapters, as we have seen, are used to bring in messages from the external system (in this case a filesystem directory).


Our inbound adapter configuration consists of:


  • An @InboundChannelAdapter annotation that marks the bean configuration as an adapter — we configure the channel to which the adapter will feed its messages (in our case, an MPEG file) and a poller, a component which helps the adapter poll the configured folder at the specified interval
  • A standard Spring java configuration class that returns a FileReadingMessageSource, the Spring Integration class implementation that handles filesystem polling

Outbound adapters are used to send messages outwards. Spring Integration supports a large variety of out-of-the-box adapters for various common use cases.

出站适配器用于向外发送消息。Spring Integration支持大量的开箱即用的适配器,用于各种常见的使用情况。

6. Conclusion


We have examined a basic use case with Spring Integration that demonstrates the java-based configuration of the library and reusability of the available components.

我们研究了一个使用Spring Integration的基本用例,展示了基于java的配置库和可用组件的重用性。

Spring Integration code is deployable as a standalone project within JavaSE as well as part of something larger in a Jakarta EE environment. While it doesn’t directly compete with other EAI-centric products and patterns like Enterprise Service Buses (ESBs), it is a viable, lightweight alternative to solving many of the same problems that ESBs were built to solve.

Spring Integration的代码可以作为JavaSE中的一个独立项目进行部署,也可以作为Jakarta EE环境中更大的项目的一部分。虽然它没有直接与其他以EAI为中心的产品和模式(如企业服务总线(ESB))竞争,但它是一个可行的、轻量级的替代方案,可以解决ESB所要解决的许多相同问题。

You can find the source code for this article in the Github project.