Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Enterprise Integration Patterns - Spring way

Enterprise Integration Patterns - Spring way

We are living in a connected word, where unrestricted sharing of data becomes an ultimate goal.
This reflects the architecture of the software systems where the main focus is on building enterprise integrated solutions.
Enterprise Integration Patterns (EIP) are used to architecture and design integrated solutions.

During the past decades following integration styles have been identified:
- file transfer
- shared DB
- messaging

Asynchronous messaging is the most used architectural style for enterprise integration. It allows building of the loosely coupled solutions which overcomes limitations of the remote communication.

This talk is about messaging, and the way Spring supports EIP via Spring Integration project.


Dragan Gajic

October 26, 2014



  2. INTEGRATION • Creating a single, monolite app to cover all

    aspects of business is hard • Enterpises are comprised of applications which can be: custom build, 3rd party, legacy • Connecting computer systems, companies or people • Share data and processes
  3. INTEGRATION CHALLENGES • Networks: unreliable & slow • Differences: language,

    platform & data format • Changes • Limited control • Standards • Maintenance
  4. INTEGRATION STYLES • File transfer • Shared DB • RMI

    • Messaging • asyncronous • reliable transfer • common format (messages) • Loose coupling
  5. MESSAGE AND CHANNEL • Message • Header – information about

    the data • Payload (body) – the data being transmitted • Channel • Point-to-Point • Publish-Subscribe Header Payload Header Payload Header Payload Consumer Producer Header Payload Header Payload
  6. PIPES AND FILTERS Persist Pipe Create validation email Pipe Pipe

    Filter Filter Send validation email SMTP Pipe Filter USER Registration • Divide complex processing • Filters – independent processing steps • Pipes – connect filters into a sequence • Fundamental architectural style for messaging • Pipe = Channel • Filter = Endpoint
  7. SPRING INTEGRATION • Top-level project in spring.io • Enables lightweight

    messaging • Combines DI, POJO and Messaging • Implements most of EIP • Includes wide selection of channel adapters • SI != MOM, ESB
  8. EXAMPLE: USER REGISTRATION • After user registration validate email address

    by sending confirmation link to email and notify moderators about new profile • In steps: • Generate confirmation link (UUID) • Store userId -> UUID • Send confirmation email • Notify site moderators about the new profile SMTP ADMIN REST API
  9. CHANNEL ADAPTER @RequestMapping(method = RequestMethod.POST) @ResponseStatus(HttpStatus.CREATED) public ProfileResource register(@Valid @RequestBody

    RegistrationResource registration) { Profile profile = profileService.save(regResToProfile.convert(registration)); publisher.publishEvent(new RegistrationEvent(this, profile)); return profileToProfileResource.convert(profile); } <int-event:inbound-channel-adapter channel="event-channel" event-types=“x.x.RegistrationEvent"/> <channel id="event-channel“ />
  10. ENRICHER <header-enricher input-channel="event-channel"> <header name="uuid“ expression="T(java.util.UUID).randomUUID.toString()"/> </header-enricher>

  11. WIRE-TAP <wire-tap channel="logger"/>

  12. PIPING IT ALL TOGETHER <int-event:inbound-channel-adapter channel="event-channel" event-types="com.levi9.samples.eip.registration.event.RegistrationEvent" /> <channel id="event-channel"

    /> <header-enricher input-channel="event-channel" output-channel=“logger"> <header name="uuid" expression="T(java.util.UUID).randomUUID().toString()" /> </header-enricher> <logging-channel-adapter id="logger" level="INFO" log-full-message="true" />

  14. SPLITTER & ROUTER <splitter input-channel="confirmation-channel“ output-channel="splitted" method="split"> <beans:bean class="com.levi9.samples.eip.registration.splitter.ProfileSplitter" />

    </splitter> <payload-type-router input-channel="splitted"> <mapping type="java.lang.Long" channel="save" /> <mapping type="com.levi9.samples.eip.registration.model.Profile" channel=“email" /> </payload-type-router> public Object[] split(RegistrationEvent event) { Profile profile = event.getProfile(); return new Object[] {profile.getId(), profile}; }
  15. <service-activator input-channel="save" output-channel="done" expression="@profileService.pending(headers.uuid, payload)" /> <chain input-channel="email" output-channel="done"> <int-mail:header-enricher>

    <int-mail:from value="EIP" /> <int-mail:to expression="payload.email" /> <int-mail:subject value="Registration confirmation" /> </int-mail:header-enricher> <transformer expression="'Dear ' + payload.name + ', please click on the following link #{ environment['host.name'] }/confirm/' + headers.uuid + ' in order to confirm email address.'" /> </chain> SERVICE ACTIVATOR & TRANSLATOR public boolean pending(String uuid, Long id) { return confirmations.put(uuid, id) == null; }
  16. <aggregator input-channel="done" method="aggregate" message-store=“store" output-channel="mail-outbound" > <bean class="com.levi9.samples.eip.registration.aggregator.ConfirmationAggregator"/> </aggregator> <channel

    id="mail-outbound" /> <int-mail:outbound-channel-adapter channel="mail-outbound" host="#{ environment['mail.smtp.host']}" port="#{ environment['mail.smtp.port']}" /> <bean id=“store" class="org.springframework.integration.store.SimpleMessageStore" /> AGGREGATOR & MAIL ADAPTER public String aggregate(List<Message<?>> messages) { return (String) messages .stream() .filter(p -> p.getPayload() instanceof String) .findFirst().orElse(null).getPayload(); }

  18. DEMO https://gitlab.levi9.com/d.gajic/eip/tree/code3

  19. RESOURCES • Book • Enterprise Integration Patterns • Gregor Hohpe,

    Bobby Woolf • Spring Integration • http://projects.spring.io/spring-integration • Samples • https://gitlab.levi9.com/d.gajic/eip.git • Patterns • http://www.enterpriseintegrationpatterns.com
  20. Q&A