<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>Eventuate, Inc</title>
        <description>About Eventuate, Inc</description>
        <link>http://eventuate.io</link>
        <atom:link href="http://eventuate.io/feed.xml" rel="self" type="application/rss+xml" />
        
        <item>
            <title>New Eventuate platform APIs that support Async API: part 1 - events</title>
            <description>&lt;h1 id=&quot;new-eventuate-platform-apis-that-support-async-api-part-1---events&quot;&gt;New Eventuate platform APIs that support Async API: part 1 - events&lt;/h1&gt;

&lt;p&gt;I recently developed a &lt;a href=&quot;https://github.com/eventuate-platform/eventuate-tram-spring-wolf-support/&quot;&gt;plugin for SpringWolf&lt;/a&gt; that configures an Eventuate service to expose an &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;/springwolf/docs&lt;/code&gt; endpoint that returns an Async API document describing the messages that the service sends and receives.
While implementing the plugin, however, I discovered that the existing Eventuate APIs were not well suited to exposing Async API-style metadata.
For example, the messages sent by the service — and the channels to which it sent them — were not explicitly defined; instead, these details were hidden within the code&lt;/p&gt;

&lt;p&gt;This realization prompted the creation of a new set of Eventuate APIs for sending and receiving messages.
The old APIs still work but only limited metadata can be generated from them.
In this article, I’ll describe the new APIs for publishing and subscribing to events.
A later article will describe the new APIs for commands and sagas.
Let’s first look at the changes to event publishing.&lt;/p&gt;

&lt;h2 id=&quot;event-publishing&quot;&gt;Event publishing&lt;/h2&gt;

&lt;p&gt;Let’s first look at the old way of publishing events.
After that I describe the new approach.&lt;/p&gt;

&lt;h3 id=&quot;original-event-publishing-api&quot;&gt;Original event publishing API&lt;/h3&gt;

&lt;p&gt;Previously, domain logic simply used the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventPublisher&lt;/code&gt; to publish events:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerService&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;DomainEventPublisher&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventPublisher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;

  &lt;span class=&quot;nd&quot;&gt;@Transactional&lt;/span&gt;
  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Customer&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;createCustomer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;String&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;name&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Money&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;creditLimit&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;...&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;domainEventPublisher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;publish&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;class&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(),&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerWithEvents&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;events&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
  &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;As a result, the channels and event types were not explicitly defined.&lt;/p&gt;

&lt;h3 id=&quot;new-event-publishing-api&quot;&gt;New event publishing API&lt;/h3&gt;

&lt;p&gt;The new approach consists of defining one or more &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventPublisherForAggregate&lt;/code&gt; &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@Beans&lt;/code&gt;.
A &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventPublisherForAggregate&lt;/code&gt; publishes events for a specific aggregate.
Although defining &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventPublisherForAggregates&lt;/code&gt; involves more code, it explicitly defines the channels and events.
The Eventuate plugin for Spring Wolf uses the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventPublisherForAggregate&lt;/code&gt; &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@Beans&lt;/code&gt; to generate an Async API document describing the published events and their channels.&lt;/p&gt;

&lt;p&gt;Here’s the definition of a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventPublisherForAggregate&lt;/code&gt; for the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;Customer&lt;/code&gt; aggregate:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;interface&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEventPublisher&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;extends&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;DomainEventPublisherForAggregate&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Long&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;It’s injected into the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;CustomerService&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerService&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;final&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEventPublisher&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerEventPublisher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;reserveCredit&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;kt&quot;&gt;long&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;orderId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;long&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Money&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;orderTotal&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;

      &lt;span class=&quot;nc&quot;&gt;CustomerCreditReservedEvent&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerCreditReservedEvent&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt;
              &lt;span class=&quot;k&quot;&gt;new&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;CustomerCreditReservedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;customerId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;orderId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;

      &lt;span class=&quot;n&quot;&gt;customerEventPublisher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;publish&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerCreditReservedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;


&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Finally, here is the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@Bean&lt;/code&gt; implementation of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;CustomerEventPublisher&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nd&quot;&gt;@Component&lt;/span&gt;
&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEventPublisherImpl&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;extends&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;AbstractDomainEventPublisherForAggregateImpl&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Long&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;implements&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEventPublisher&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;

    &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;CustomerEventPublisherImpl&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;DomainEventPublisher&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventPublisher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
        &lt;span class=&quot;kd&quot;&gt;super&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Customer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;class&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nl&quot;&gt;Customer:&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;:&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;getId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventPublisher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;class&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;Let’s now look at the new event handling API.&lt;/p&gt;

&lt;h2 id=&quot;subscribing-to-events&quot;&gt;Subscribing to events&lt;/h2&gt;

&lt;p&gt;Let’s first look at the old way of subscribing to events.
After that I describe the new approach.&lt;/p&gt;

&lt;h3 id=&quot;original-event-handling-api&quot;&gt;Original event handling API&lt;/h3&gt;

&lt;p&gt;Previously, event handlers were configured by defining a class that constructed &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventHandlers&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;OrderEventConsumer&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;DomainEventHandlers&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;domainEventHandlers&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;()&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;DomainEventHandlersBuilder&lt;/span&gt;
            &lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;forAggregateType&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;io.eventuate.examples.tram.ordersandcustomers.orders.domain.Order&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt;
            &lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;onEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;OrderCreatedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;class&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;this&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;::&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;handleOrderCreatedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt;
            &lt;span class=&quot;o&quot;&gt;...&lt;/span&gt;
            &lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;build&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
  &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;handleOrderCreatedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;DomainEventEnvelope&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;OrderCreatedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventEnvelope&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;o&quot;&gt;...&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventHandlers&lt;/code&gt; was then passed to a &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventDispatcherFactory&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerConfiguration&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;

  &lt;span class=&quot;nd&quot;&gt;@Bean&lt;/span&gt;
  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;OrderEventConsumer&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;orderEventConsumer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;CustomerService&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerService&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;k&quot;&gt;new&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;OrderEventConsumer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;customerService&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;);&lt;/span&gt;
  &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;

  &lt;span class=&quot;nd&quot;&gt;@Bean&lt;/span&gt;
  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;DomainEventDispatcher&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;domainEventDispatcher&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;OrderEventConsumer&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;orderEventConsumer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;DomainEventDispatcherFactory&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventDispatcherFactory&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;return&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventDispatcherFactory&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;make&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;s&quot;&gt;&quot;orderServiceEvents&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;orderEventConsumer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;domainEventHandlers&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;());&lt;/span&gt;
  &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The Eventuate plugin for Spring Wolf can use the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;DomainEventDispatcher&lt;/code&gt; &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@Beans&lt;/code&gt; to generate an Async API document describing the subscribed to events and their channels.
However, there’s no obvious way to customize the Async API document by, for example, specifying additional documentation.&lt;/p&gt;

&lt;h3 id=&quot;new-event-handling-api&quot;&gt;New event handling API&lt;/h3&gt;

&lt;p&gt;The new approach is to define beans that have methods annotated with &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@EventuateDomainEventHandler&lt;/code&gt;.
The annotation specifies the event handler’s subscriber ID and the channel.
The event type is obtained from the method parameter.&lt;/p&gt;

&lt;div class=&quot;language-java highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;&lt;span class=&quot;nd&quot;&gt;@Component&lt;/span&gt;
&lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kd&quot;&gt;class&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;OrderEventConsumer&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
  &lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;Logger&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;logger&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;LoggerFactory&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getLogger&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;getClass&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;());&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;private&lt;/span&gt; &lt;span class=&quot;nc&quot;&gt;CustomerService&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerService&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;

  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;OrderEventConsumer&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;CustomerService&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerService&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;k&quot;&gt;this&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;customerService&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;customerService&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;;&lt;/span&gt;
  &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;

  &lt;span class=&quot;nd&quot;&gt;@EventuateDomainEventHandler&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;subscriberId&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;s&quot;&gt;&quot;OrderEventConsumer&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;,&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;channel&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;s&quot;&gt;&quot;io.eventuate.examples.tram.ordersandcustomers.orders.domain.Order&quot;&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt;
  &lt;span class=&quot;kd&quot;&gt;public&lt;/span&gt; &lt;span class=&quot;kt&quot;&gt;void&lt;/span&gt; &lt;span class=&quot;nf&quot;&gt;handleOrderCreatedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;DomainEventEnvelope&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;OrderCreatedEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;&amp;gt;&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventEnvelope&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;)&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;{&lt;/span&gt;
    &lt;span class=&quot;nc&quot;&gt;OrderCreatedEvent&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;event&lt;/span&gt; &lt;span class=&quot;o&quot;&gt;=&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;domainEventEnvelope&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getEvent&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;();&lt;/span&gt;
    &lt;span class=&quot;n&quot;&gt;customerService&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;reserveCredit&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;nc&quot;&gt;Long&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;parseLong&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(&lt;/span&gt;&lt;span class=&quot;n&quot;&gt;domainEventEnvelope&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;getAggregateId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;()),&lt;/span&gt;
            &lt;span class=&quot;n&quot;&gt;event&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;orderDetails&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;().&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;customerId&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;(),&lt;/span&gt; &lt;span class=&quot;n&quot;&gt;event&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;.&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;orderDetails&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;().&lt;/span&gt;&lt;span class=&quot;na&quot;&gt;orderTotal&lt;/span&gt;&lt;span class=&quot;o&quot;&gt;());&lt;/span&gt;
  &lt;span class=&quot;o&quot;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;The Eventuate plugin for Spring Wolf can search the application context for &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@Beans&lt;/code&gt; that have methods annotated with &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;@EventuateDomainEventHandler&lt;/code&gt;.
Moreover, in the future, it will support additional annotations that allow you to customize the generated Async API document.&lt;/p&gt;

&lt;h2 id=&quot;show-me-the-code&quot;&gt;Show me the code&lt;/h2&gt;

&lt;ul&gt;
  &lt;li&gt;The Eventuate Spring Wolf repository contains some &lt;a href=&quot;https://github.com/eventuate-platform/eventuate-tram-spring-wolf-support?tab=readme-ov-file#example-async-api-documentation&quot;&gt;example Async API docs&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;The &lt;a href=&quot;https://github.com/eventuate-tram/eventuate-tram-examples-customers-and-orders/tree/development&quot;&gt;development branch&lt;/a&gt; of the &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;eventuate-tram-examples-customers-and-orders&lt;/code&gt; repository contains an example application that uses the new APIs.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2 id=&quot;whats-next&quot;&gt;What’s next&lt;/h2&gt;

&lt;p&gt;A later post will describe the new APIs for sagas and command handlers.&lt;/p&gt;
</description>
            <pubDate>Tue, 11 Mar 2025 08:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2025/03/11/eventuate-new-apis-part-1.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2025/03/11/eventuate-new-apis-part-1.html</guid>
        </item>
        
        <item>
            <title>Simplified getting started experience for Spring Boot applications</title>
            <description>&lt;h1 id=&quot;simplified-getting-started-experience-for-spring-boot-applications&quot;&gt;Simplified getting started experience for Spring Boot applications&lt;/h1&gt;

&lt;p&gt;There’s a &lt;a href=&quot;/docs/manual/eventuate-tram/latest/getting-started-eventuate-tram-spring-boot.html&quot;&gt;new guide that describes a simpler getting started experience&lt;/a&gt; for Spring Boot applications that use the Eventuate platform.
It currently describes how to configure Gradle. 
The Maven instructions will be added soon.&lt;/p&gt;
</description>
            <pubDate>Thu, 09 Jan 2025 08:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2025/01/09/simplified-getting-started-for-spring-boot.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2025/01/09/simplified-getting-started-for-spring-boot.html</guid>
        </item>
        
        <item>
            <title>Eventuate now supports Quarkus</title>
            <description>&lt;h1 id=&quot;eventuate-now-supports-quarkus&quot;&gt;Eventuate now supports Quarkus&lt;/h1&gt;

&lt;p&gt;We are very excited to announce that Eventuate now supports the &lt;a href=&quot;https://quarkus.io/&quot;&gt;Quarkus framework&lt;/a&gt; in addition to Spring Boot, Micronaut, and .NET.&lt;/p&gt;

&lt;p&gt;You can now easily write Quarkus-based that use the &lt;a href=&quot;/post/eventuate/2020/02/24/why-eventuate.html&quot;&gt;Saga and CQRS patterns&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Please see the &lt;a href=&quot;/exampleapps.html&quot;&gt;example applications&lt;/a&gt; and the &lt;a href=&quot;/gettingstarted.html&quot;&gt;getting start docs&lt;/a&gt;.&lt;/p&gt;
</description>
            <pubDate>Fri, 04 Jun 2021 07:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2021/06/04/eventuate-quarkus.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2021/06/04/eventuate-quarkus.html</guid>
        </item>
        
        <item>
            <title>Quickly get started with @SpringBoot and @EventuateIO with start.eventuate.io</title>
            <description>&lt;h1 id=&quot;quickly-get-started-with-springboot-and-eventuateio-with-starteventuateio&quot;&gt;Quickly get started with @SpringBoot and @EventuateIO with start.eventuate.io&lt;/h1&gt;

&lt;p&gt;The website &lt;a href=&quot;https://start.eventuate.io/&quot;&gt;start.eventuate.io&lt;/a&gt; is a quick and convenient way to start the development of an Eventuate/Spring Boot-based service.&lt;/p&gt;

&lt;p&gt;There are many Eventuate dependencies to choose from:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;
    &lt;p&gt;If you want to using event sourcing, then select the Eventuate Local dependencies.&lt;/p&gt;
  &lt;/li&gt;
  &lt;li&gt;
    &lt;p&gt;Otherwise, if you want to use traditional persistence then select the Eventuate Tram and Eventuate Saga dependencies.
Don’t forget you need to pick exactly one transport for the message broker that you want to use.&lt;/p&gt;
  &lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href=&quot;https://start.eventuate.io/&quot;&gt;Start.eventuate.io&lt;/a&gt; built on &lt;a href=&quot;https://github.com/spring-io/initializr/&quot;&gt;Spring Initialzr&lt;/a&gt;.
You can, for example, use the command line to generate a service project:&lt;/p&gt;

&lt;div class=&quot;language-plaintext highlighter-rouge&quot;&gt;&lt;div class=&quot;highlight&quot;&gt;&lt;pre class=&quot;highlight&quot;&gt;&lt;code&gt;curl https://start.eventuate.io/starter.zip \
-d type=maven-project \
-d language=java \
-d platformVersion=2.3.2.RELEASE \
-d packaging=jar \
-d jvmVersion=11 \
-d groupId=io.eventuate.example.sagas \
-d artifactId=orchestrator \
-d name=orchestrator \
-d description=Demo%20project%20Eventuate%2C%20domain%20events%2C%20and%20saga%20orchestration \
-d packageName=io.eventuate.example.sagas.orchestrator \
-d dependencies=eventuatetramdomainevents,eventuatetramsagaorchestrator,eventuatetramkafka,actuator \
-o demo.zip
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;

&lt;p&gt;&lt;img src=&quot;/i/Start.Eventuate.IO.smaller.png&quot; class=&quot;img-responsive&quot; /&gt;&lt;/p&gt;
</description>
            <pubDate>Sun, 02 Aug 2020 09:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2020/08/02/getting-started-with-start-eventuate-io.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2020/08/02/getting-started-with-start-eventuate-io.html</guid>
        </item>
        
        <item>
            <title>An overview of the Eventuate Platform</title>
            <description>&lt;h1 id=&quot;an-overview-of-the-eventuate-platform&quot;&gt;An overview of the Eventuate Platform&lt;/h1&gt;

&lt;p&gt;Here is an overview of the Eventuate Platform.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/i/005.Overview_of_Eventuate.005.png&quot; class=&quot;img-responsive&quot; /&gt;&lt;/p&gt;

&lt;h2 id=&quot;slides&quot;&gt;Slides&lt;/h2&gt;

&lt;iframe src=&quot;//www.slideshare.net/slideshow/embed_code/key/KHykjOdtqWlkkF&quot; width=&quot;595&quot; height=&quot;485&quot; frameborder=&quot;0&quot; marginwidth=&quot;0&quot; marginheight=&quot;0&quot; scrolling=&quot;no&quot; style=&quot;border:1px solid #CCC; border-width:1px; margin-bottom:5px; max-width: 100%;&quot; allowfullscreen=&quot;&quot;&gt; &lt;/iframe&gt;
&lt;div style=&quot;margin-bottom:5px&quot;&gt; &lt;strong&gt; &lt;a href=&quot;//www.slideshare.net/chris.e.richardson/an-overview-of-the-eventuate-platform&quot; title=&quot;An overview of the Eventuate Platform&quot; target=&quot;_blank&quot;&gt;An overview of the Eventuate Platform&lt;/a&gt; &lt;/strong&gt; from &lt;strong&gt;&lt;a href=&quot;https://www.slideshare.net/chris.e.richardson&quot; target=&quot;_blank&quot;&gt;Chris Richardson&lt;/a&gt;&lt;/strong&gt; &lt;/div&gt;

&lt;h2 id=&quot;video&quot;&gt;Video&lt;/h2&gt;

&lt;iframe width=&quot;560&quot; height=&quot;315&quot; src=&quot;https://www.youtube.com/embed/-SFuv4XWgYQ&quot; frameborder=&quot;0&quot; allow=&quot;accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture&quot; allowfullscreen=&quot;&quot;&gt;&lt;/iframe&gt;
</description>
            <pubDate>Sun, 24 May 2020 13:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2020/05/24/eventuate-overview.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2020/05/24/eventuate-overview.html</guid>
        </item>
        
        <item>
            <title>New version of the Eventuate platform released!</title>
            <description>&lt;h1 id=&quot;new-version-of-the-eventuate-platform-released&quot;&gt;New version of the Eventuate platform released!&lt;/h1&gt;

&lt;p&gt;We are excited to announce that a new version of the Eventuate platform has been released:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;Eventuate Tram &lt;a href=&quot;https://bintray.com/eventuateio-oss/eventuate-maven-release/eventuate-tram/0.24.0.RELEASE/link&quot;&gt;&lt;img src=&quot;https://api.bintray.com/packages/eventuateio-oss/eventuate-maven-release/eventuate-tram/images/download.svg?version=0.24.0.RELEASE&quot; /&gt;&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;Eventuate Tram Sagas &lt;a href=&quot;https://bintray.com/eventuateio-oss/eventuate-maven-release/eventuate-tram-sagas/0.13.0.RELEASE/link&quot;&gt;&lt;img src=&quot;https://api.bintray.com/packages/eventuateio-oss/eventuate-maven-release/eventuate-tram-sagas/images/download.svg?version=0.13.0.RELEASE&quot; /&gt;&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;Eventuate Local &lt;a href=&quot;https://bintray.com/eventuateio-oss/eventuate-maven-release/eventuate-local/0.32.0.RELEASE/link&quot;&gt;&lt;img src=&quot;https://api.bintray.com/packages/eventuateio-oss/eventuate-maven-release/eventuate-local/images/download.svg?version=0.32.0.RELEASE&quot; /&gt;&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;Eventuate CDC Service &lt;a href=&quot;https://bintray.com/eventuateio-oss/eventuate-maven-release/eventuate-cdc/0.6.1.RELEASE/link&quot;&gt;&lt;img src=&quot;https://api.bintray.com/packages/eventuateio-oss/eventuate-maven-release/eventuate-cdc/images/download.svg?version=0.6.1.RELEASE&quot; /&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;There are several major enhancements to the platform including:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;Support for &lt;a href=&quot;https://micronaut.io/&quot;&gt;Micronaut&lt;/a&gt; - see the &lt;a href=&quot;/exampleapps.html&quot;&gt;Micronaut versions of the Eventuate example apps&lt;/a&gt; and the &lt;a href=&quot;/docs/manual/eventuate-tram/latest/&quot;&gt;user manual&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;Improved Eventuate CDC service performance - more on that in a later post&lt;/li&gt;
  &lt;li&gt;&lt;a href=&quot;https://start.eventuate.io/&quot;&gt;start.eventuate.io&lt;/a&gt; - for quickly bootstrapping an Eventuate service: search for the Eventuate dependencies&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Please read this previous post on &lt;a href=&quot;/2020/03/31/upcoming-eventuate-release.html&quot;&gt;upgrading to this new version&lt;/a&gt;.&lt;/p&gt;
</description>
            <pubDate>Sun, 03 May 2020 13:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2020/05/03/eventuate-releases.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2020/05/03/eventuate-releases.html</guid>
        </item>
        
        <item>
            <title>Eventuate Tram supports Java 14 and @SpringBoot 2.2.6.RELEASE</title>
            <description>&lt;h1 id=&quot;eventuate-tram-supports-java-14-and-springboot-226release-alltestsgreenonjdk14&quot;&gt;Eventuate Tram supports Java 14 and @SpringBoot 2.2.6.RELEASE #AllTestsGreenOnJDK14&lt;/h1&gt;

&lt;p&gt;We just upgraded the development branches of a couple of example applications to Java 14 and @SpringBoot 2.2.6.RELEASE:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://github.com/eventuate-tram/eventuate-tram-examples-customers-and-orders/tree/development&quot;&gt;Eventuate Tram Customers and Orders - Spring Boot&lt;/a&gt; - demonstrates how to maintain data consistency in an Spring Boot, JPA-based microservice architecture using &lt;a href=&quot;http://microservices.io/patterns/data/saga.html&quot;&gt;choreography-based sagas&lt;/a&gt;.&lt;/p&gt;
  &lt;/li&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://github.com/eventuate-tram/eventuate-tram-sagas-examples-customers-and-orders/tree/development&quot;&gt;Eventuate Tram Sagas Customers and Orders - Spring Boot&lt;/a&gt; - demonstrates how to maintain data consistency in an Spring Boot, JPA-based microservice architecture using &lt;a href=&quot;http://microservices.io/patterns/data/saga.html&quot;&gt;orchestration-based sagas&lt;/a&gt;.&lt;/p&gt;
  &lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;When the Eventuate Tram libraries, which are &lt;a href=&quot;/post/eventuate/2020/03/31/upcoming-eventuate-release.html&quot;&gt;currently &lt;code class=&quot;language-plaintext highlighter-rouge&quot;&gt;RC&lt;/code&gt;&lt;/a&gt;, are released the changes will be merged into master.&lt;/p&gt;
</description>
            <pubDate>Tue, 31 Mar 2020 09:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2020/03/31/eventuate-tram-java-14.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2020/03/31/eventuate-tram-java-14.html</guid>
        </item>
        
        <item>
            <title>Eventuate for Spring Boot and now Micronaut - upgrade information</title>
            <description>&lt;h1 id=&quot;upgrading-to-the-upcoming-release-of-eventuate&quot;&gt;Upgrading to the upcoming release of Eventuate&lt;/h1&gt;

&lt;p&gt;Eventuate is a platform that solves the distributed data management problems inherent in a microservice architecture.
It makes it straightforward to use &lt;a href=&quot;/post/eventuate/2020/02/24/why-eventuate.html&quot;&gt;patterns such as Sagas, CQRS and Event Sourcing&lt;/a&gt; and enables you focus on your business logic.&lt;/p&gt;

&lt;p&gt;The latest versions of Eventuate Local (0.32.0.RC4), Eventuate Tram (0.24.0.RC4), Eventuate Tram Sagas (0.13.0.RC4) now support both Spring Boot and Micronaut.
We plan to make .RELEASE versions shortly.&lt;/p&gt;

&lt;p&gt;Here are the Eventuate Micronaut example applications:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://github.com/eventuate-tram-examples/eventuate-tram-examples-micronaut-customers-and-orders&quot;&gt;Eventuate Tram Customers and Orders - Micronaut&lt;/a&gt; - demonstrates how to maintain data consistency in an Micronaut, JPA-based microservice architecture using &lt;a href=&quot;http://microservices.io/patterns/data/saga.html&quot;&gt;choreography-based sagas&lt;/a&gt;.&lt;/p&gt;
  &lt;/li&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://github.com/eventuate-tram-examples/eventuate-tram-sagas-micronaut-examples-customers-and-orders&quot;&gt;Eventuate Tram Sagas Customers and Orders - Micronaut&lt;/a&gt; - demonstrates how to maintain data consistency in an Micronaut, JPA-based microservice architecture using &lt;a href=&quot;http://microservices.io/patterns/data/saga.html&quot;&gt;orchestration-based sagas&lt;/a&gt;.&lt;/p&gt;
  &lt;/li&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://github.com/eventuate-examples/eventuate-micronaut-examples-customers-and-orders&quot;&gt;Eventuate Customers and Orders - Micronaut&lt;/a&gt; - demonstrates how to maintain data consistency in an Micronaut, JPA-based microservice architecture using Micronaut, Event Sourcing, &lt;a href=&quot;http://microservices.io/patterns/data/saga.html&quot;&gt;choreography-based sagas&lt;/a&gt; and CQRS.&lt;/p&gt;
  &lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;There are &lt;a href=&quot;/exampleapps.html&quot;&gt;numerous other example applications for Spring Boot&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Please note that adding support for Micronaut required changing the names of both Maven artifacts and packages.
In order to upgrade to these versions, you must edit your source code.
To simplify the process, we created a &lt;a href=&quot;https://github.com/eventuate-tram/eventuate-upgrade-scripts&quot;&gt;Python-based upgrade script&lt;/a&gt; that makes all but one of the needed renames for Eventuate Local, Tram and Saga applications.
It would be great if you try it and provide feedback.&lt;/p&gt;
</description>
            <pubDate>Tue, 31 Mar 2020 09:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2020/03/31/upcoming-eventuate-release.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2020/03/31/upcoming-eventuate-release.html</guid>
        </item>
        
        <item>
            <title>Eventuate explained using microservices patterns</title>
            <description>&lt;h1 id=&quot;eventuate-explained-using-microservices-patterns&quot;&gt;Eventuate explained using microservices patterns&lt;/h1&gt;

&lt;p&gt;A while back I came up with this diagram that explains Eventuate using microservice architecture patterns.&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/i/Why_Eventuate.png&quot; class=&quot;img-responsive&quot; /&gt;&lt;/p&gt;

&lt;p&gt;Let’s look at each of the patterns in turn starting with the Database per Service pattern.&lt;/p&gt;

&lt;h2 id=&quot;database-per-service-pattern&quot;&gt;Database per Service pattern&lt;/h2&gt;

&lt;p&gt;A key characteristic of the Microservice Architecture is loose coupling.
There are two types of coupling:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;design-time coupling - changing one service requires other services to change.
Services must be loosely coupled from a design-time perspective in order to ensure that teams are loosely coupled and, therefore, productive.&lt;/li&gt;
  &lt;li&gt;runtime coupling - the failure of one service prevents another service from handling a request.
Services must also be loosely coupled from a runtime perspective in order to maximize availability.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This requirement for loose coupling significantly impacts the database architecture and creates the need for the &lt;a href=&quot;https://microservices.io/patterns/data/database-per-service.html&quot;&gt;Database per Service pattern&lt;/a&gt;.
At a minimum, to avoid design time coupling, services must not share database tables.
And, &lt;em&gt;ideally&lt;/em&gt;, to reduce runtime coupling, each service should have its own database server.&lt;/p&gt;

&lt;h2 id=&quot;distributed-data-management-patterns&quot;&gt;Distributed data management patterns&lt;/h2&gt;

&lt;p&gt;The &lt;a href=&quot;https://microservices.io/patterns/data/database-per-service.html&quot;&gt;Database per Service pattern&lt;/a&gt; creates distributed data management challenges.
There are two key distributed data management patterns that solve these problems:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;Saga pattern - implements transactions that span services&lt;/li&gt;
  &lt;li&gt;CQRS pattern - implements queries that span services&lt;/li&gt;
&lt;/ul&gt;

&lt;h3 id=&quot;transaction-management-with-the-saga-pattern&quot;&gt;Transaction management with the Saga pattern&lt;/h3&gt;

&lt;p&gt;Some update operations (a.k.a. &lt;a href=&quot;https://microservices.io/articles/glossary#command&quot;&gt;commands&lt;/a&gt;) need to update data in multiple services.
Such an operation typically doesn’t use traditional distributed transactions (2PC) since that’s a type of runtime coupling.
Instead, a command that spans services must be implemented using the &lt;a href=&quot;https://microservices.io/patterns/data/saga.html&quot;&gt;Saga pattern&lt;/a&gt;.
A saga is a series of local transactions that are coordinated by the participating services exchanging &lt;a href=&quot;https://microservices.io/patterns/communication-style/messaging.html&quot;&gt;messages&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;As I describe in this &lt;a href=&quot;http://chrisrichardson.net/post/antipatterns/2019/07/09/developing-sagas-part-1.html&quot;&gt;series of blog posts about sagas&lt;/a&gt; there are two types of saga coordination mechanisms:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;choreography-based sagas - services collaborate by exchanging &lt;a href=&quot;https://microservices.io/patterns/data/domain-event.html&quot;&gt;domain events&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;orchestration-based sagas - a centralized coordinator sending command messages to participants, which respond with reply messages&lt;/li&gt;
&lt;/ul&gt;

&lt;h3 id=&quot;implementing-queries-with-the-cqrs-pattern&quot;&gt;Implementing queries with the CQRS pattern&lt;/h3&gt;

&lt;p&gt;Some &lt;a href=&quot;https://microservices.io/articles/glossary#query&quot;&gt;queries&lt;/a&gt; need to retrieve data from multiple services.
Since each database is private, the data can only be retrieved using each service’s API.
One option is to use &lt;a href=&quot;https://microservices.io/patterns/data/api-composition.html&quot;&gt;API Composition&lt;/a&gt; and simply invokes query operations on the services.
However, sometimes API composition is inefficient and instead the application must use the &lt;a href=&quot;https://microservices.io/patterns/data/cqrs.html&quot;&gt;CQRS pattern&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;The CQRS pattern maintains an easily queryable replica of the data using &lt;a href=&quot;https://microservices.io/patterns/data/domain-event.html&quot;&gt;domain events&lt;/a&gt; published by the services that own the data.&lt;/p&gt;

&lt;h2 id=&quot;how-eventuate-solves-these-distributed-data-management-challenges&quot;&gt;How Eventuate solves these distributed data management challenges&lt;/h2&gt;

&lt;p&gt;Eventuate is a family of frameworks that solve the distributed data management challenges in microservice architecture.
By using Eventuate, you can easily implement the Saga and CQRS patterns in your application.
Eventuate also provides the messaging primitives for general purpose &lt;em&gt;transactional&lt;/em&gt; messaging between services.&lt;/p&gt;

&lt;p&gt;The following diagram shows the Eventuate family of frameworks:&lt;/p&gt;

&lt;p&gt;&lt;img src=&quot;/i/Eventuate_Frameworks.png&quot; class=&quot;img-responsive&quot; /&gt;&lt;/p&gt;

&lt;p&gt;There are the following frameworks:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;Eventuate Tram Sagas - an orchestration-based saga framework&lt;/li&gt;
  &lt;li&gt;Eventuate Tram - a transactional message framework&lt;/li&gt;
  &lt;li&gt;Eventuate Local - an event sourcing framework&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Let’s look at the capabilities of these frameworks.&lt;/p&gt;

&lt;h3 id=&quot;orchestration-based-sagas&quot;&gt;Orchestration-based sagas&lt;/h3&gt;

&lt;p&gt;The &lt;a href=&quot;https://github.com/eventuate-tram/eventuate-tram-sagas&quot;&gt;Eventuate Tram Sagas&lt;/a&gt; framework implements orchestration-based sagas.
It provides an easy to use Java-based domain-specific language for the defining the steps of your saga and their compensating transactions.
The saga execution engine is embedded within your services, which simplifies the architecture and improves scalability and availability.&lt;/p&gt;

&lt;h3 id=&quot;choreography-based-sagas-and-cqrs&quot;&gt;Choreography-based sagas and CQRS&lt;/h3&gt;

&lt;p&gt;Eventuate makes it easy to implement event-driven microservices that use choreography-based sagas and CQRS.
It provides an API for publishing and consuming events.
Services can use Eventuate to publish events as part of a database transaction that updates business entity.
Other services can use Eventuate to consume events with automatic duplicate detection, which ensures that your &lt;a href=&quot;https://microservices.io/patterns/communication-style/idempotent-consumer.html&quot;&gt;message handlers are idempotent&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Eventuate provides different event-driven programming models&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;Explicit event publishing - use for applications that persist business entities using traditional (e.g. JDBC/JPA) persistence.
The &lt;a href=&quot;https://eventuate.io/abouteventuatetram.html&quot;&gt;Eventuate Tram framework&lt;/a&gt; provides APIs for publishing and consuming events.&lt;/li&gt;
  &lt;li&gt;&lt;a href=&quot;https://microservices.io/patterns/data/event-sourcing.html&quot;&gt;Event sourcing&lt;/a&gt; - an event-centric way of writing your business logic and persisting your business objects. Event sourcing is useful for application that need to maintain the history of changes to business entities.
The &lt;a href=&quot;https://eventuate.io/usingeventuate.html&quot;&gt;Eventuate Local framework&lt;/a&gt; is Eventuate’s event sourcing framework.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3 id=&quot;foundational-messaging-patterns&quot;&gt;Foundational messaging patterns&lt;/h3&gt;

&lt;p&gt;These higher level capabilities are built on several foundational patterns:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://microservices.io/patterns/data/transactional-outbox.html&quot;&gt;Transactional Outbox&lt;/a&gt; - publish a message as part of the database transaction that updates business entities.
This pattern is essential for maintaining consistency.
Without it, there is a risk of either updating the database without sending a message or sending a message without the corresponding database update.&lt;/p&gt;
  &lt;/li&gt;
  &lt;li&gt;
    &lt;p&gt;&lt;a href=&quot;https://microservices.io/patterns/communication-style/idempotent-consumer.html&quot;&gt;Idempotent Consumer&lt;/a&gt; - detect and discard duplicate messages by tracking the messages that have already been processed.
This pattern handles the scenario where a failure causes the message broker to deliver a message more than once.&lt;/p&gt;
  &lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This patterns are implemented by both the Eventuate Tram and Eventuate Local frameworks.&lt;/p&gt;

&lt;h2 id=&quot;learn-more&quot;&gt;Learn more&lt;/h2&gt;

&lt;p&gt;To learn more please take a look at the following resources:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;Read &lt;a href=&quot;https://eventuate.io/gettingstarted.html&quot;&gt;Eventuate Getting Started Guide&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;Read &lt;a href=&quot;https://microservices.io/book&quot;&gt;Chris Richardson’s microservice patterns book&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
            <pubDate>Mon, 24 Feb 2020 09:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/eventuate/2020/02/24/why-eventuate.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/eventuate/2020/02/24/why-eventuate.html</guid>
        </item>
        
        <item>
            <title>Developing sagas with Eventuate Tram</title>
            <description>&lt;h1 id=&quot;developing-sagas-with-eventuate-tram&quot;&gt;Developing sagas with Eventuate Tram&lt;/h1&gt;

&lt;p&gt;&lt;a href=&quot;https://twitter.com/crichardson&quot;&gt;Chris Richardson&lt;/a&gt; has written a series of blog posts describing how to implement &lt;a href=&quot;https://microservices.io/patterns/data/saga.html&quot;&gt;sagas&lt;/a&gt; using &lt;a href=&quot;/abouteventuatetram.html&quot;&gt;Eventuate Tram&lt;/a&gt;:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;&lt;a href=&quot;http://chrisrichardson.net/post/antipatterns/2019/07/09/developing-sagas-part-1.html&quot;&gt;Part 1 - Overview of sagas&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;&lt;a href=&quot;http://chrisrichardson.net/post/sagas/2019/08/04/developing-sagas-part-2.html&quot;&gt;Part 2 - Coordinating sagas&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;&lt;a href=&quot;http://chrisrichardson.net/post/sagas/2019/08/15/developing-sagas-part-3.html&quot;&gt;Part 3 - Choreography-based sagas&lt;/a&gt;&lt;/li&gt;
  &lt;li&gt;&lt;a href=&quot;http://chrisrichardson.net/post/sagas/2019/12/12/developing-sagas-part-4.html&quot;&gt;Part 4 - Orchestration-based sagas&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
            <pubDate>Sat, 04 Jan 2020 09:01:00 +0000</pubDate>
            <link>http://eventuate.io/post/sagas/2020/01/04/developing-sagas-with-eventuate.html</link>
            <guid isPermaLink="true">http://eventuate.io/post/sagas/2020/01/04/developing-sagas-with-eventuate.html</guid>
        </item>
        
    </channel>
</rss>
