Skip to content

v0.31.0

Compare
Choose a tag to compare
@paneq paneq released this 17 Jul 20:53
· 5145 commits to master since this release

Warning

  • When upgrading from v0.30 to v0.31, make sure all events serialized when using the old version are already processed by all async handlers and new events are not generated.
  • Rolling deploy of a new version might cause issues due to slight changes on how events are serialized for async handlers.

RailsEventStore

  • Add: Correlation between events in synchronous event handlers. When you publish events, their metadata will be enriched with correlation_id and causation_id [#374]. You can read more about correlation and causation in our documentation.

  • Change: Subtle change in metadata assignment disallowing overwriting key, once it is present. [#374]

  • Change: Signature change of RailsEventStore::ActiveJobDispatcher#call from (subscriber, event) to (subscriber, event, serialized_event). Dispatcher receives now also a serialized event (serialization happens via configured mapper, by default that is still YAML) [#363]

  • Change: Signature change of RailsEventStore::AsyncProxyStrategy::Inline#call and RailsEventStore::AsyncProxyStrategy::AfterCommit#call from (klass, event) to (klass, serialized_event). Strategies no longer perform serialization on their own, eliminating duplication of effort and using chosen mapper. [#363]

  • Add: RubyEventStore::Client#deserialize(event_type:, event_id:, data:, metadata:) [#363]

    For existing asynchronous handlers you need to perform following change from:

    class SendOrderEmail < ActiveJob::Base
      def perform(payload)
        event = YAML.load(payload)
        email = event.data.fetch(:customer_email)
        OrderMailer.notify_customer(email).deliver_now!
      end
    end

    to:

    class SendOrderEmail < ActiveJob::Base
      def perform(payload)
        event = event_store.deserialize(payload)
        email = event.data.fetch(:customer_email)
        OrderMailer.notify_customer(email).deliver_now!
      end
    
      private
      def event_store
        Rails.configuration.event_store
      end
    end

    or you can use RailsEventStore::AsyncHandler

    class SendOrderEmail < ActiveJob::Base
      prepend RailsEventStore::AsyncHandler
    
      def perform(event)
        email = event.data.fetch(:customer_email)
        OrderMailer.notify_customer(email).deliver_now!
      end
    end
  • Add: Introduce RailsEventStore::LinkByMetadata, RailsEventStore::LinkByCorrelationId, RailsEventStore::LinkByCausationId, RailsEventStore::LinkByEventType. These event handlers allow to partition streams by particular quality. Streams formed by these handlers are made by linking events, therefore are cheap [#382, #346]

  • Change: Deprecate RailsEventStore::Client#publish_event and RailsEventStore::Client#publish_events. They're now just RailsEventStore::Client#publish [#366, #377]

  • Change: Deprecate RailsEventStore::Client#link_to_stream. This is now RailsEventStore::Client#link [#388]

  • Change: Deprecate RailsEventStore::Client#append_to_stream . This is now RailsEventStore::Client#append [#387]

  • Add: Introduce RailsEventStore::AsyncHandler and RailsEventStore::CorrelatedHandler to help with correlating events coming from async handlers [#379, #346]. You can read more about correlation and causation in our documentation.

  • Add: Introduce RailsEventStore::CorrelatedCommands to aid correlating commands going through command_bus with events [#375, #346]. You can read more about correlation and causation in our documentation.

  • Change: Breaking change of RailsEventStore::Client#initialize signature. Out is event_broker:, in subscriptions: and dispatcher:. Dispatcher is no longer an event broker dependency [#389, #265]

RubyEventStore

  • Remove: Deprecated RubyEventStore::Client#metadata_proc has been removed. Similar functionality available via RubyEventStore::Client#with_metadata [#373]

  • Add: Correlation between events in synchronous event handlers. When you publish events, their metadata will be enriched with correlation_id and causation_id [#374]

  • Change: Subtle change in metadata assignment disallowing overwriting key, once it is present. [#374]

  • Change: Signature change of RubyEventStore::PubSub::Dispatcher#call from (subscriber, event) to (subscriber, event, serialized_event). Dispatcher receives now also a serialized event (serialization happens via configured mapper, by default that is still YAML) [#363]

  • Change: Signature change of RubyEventStore:: PubSub::Broker#notify_subscribers from (event) to (event, serialized_event) [#346]

  • Add: RubyEventStore::Client#deserialize(event_type:, event_id:, data:, metadata:) [#346]

  • Add: Introduce RubyEventStore::LinkByMetadata, RubyEventStore::LinkByCorrelationId, RubyEventStore::LinkByCausationId, RubyEventStore::LinkByEventType. These event handlers allow to partition streams by particular quality. Streams formed by these handlers are made by linking events, therefore are cheap [#382, #346]

  • Change: Deprecate RubyEventStore::Client#publish_event and RubyEventStore::Client#publish_events. They're now just RubyEventStore::Client#publish [#366, #377]

  • Change: Deprecate RubyEventStore::Client#link_to_stream. This is now RubyEventStore::Client#link [#388]

  • Change: Deprecate RubyEventStore::Client#append_to_stream . This is now RubyEventStore::Client#append [#387]

  • Add: Introduce RubyEventStore::CorrelatedCommands to aid correlating commands going through command_bus with events [#375, #346]. You can read more about correlation and causation in our documentation.

  • Change: Breaking change of RubyEventStore::Client#initialize signature. Out is event_broker:, in subscriptions: and dispatcher:. Dispatcher is no longer an event broker dependency [#389, #265]

  • Add: Introduce RubyEventStore::AsyncDispatcher. Previously the only implementation of asynchronous dispatcher was present in form of RailsEventStore::ActiveJobDispatcher. This new class allows you to have all benefits of asynchronous dispatch while only requiring you to provide details of your background queue implementation [#381, #383]

    As an example this is howRailsEventStore::ActiveJobDispatcher can be implemented (and thus similar SidekiqDispatcher):

    require 'active_job'
    
    module RailsEventStore
    
      class ActiveJobDispatcher < AsyncDispatcher
        def initialize(proxy_strategy: AsyncProxyStrategy::Inline.new)
          super(proxy_strategy: proxy_strategy, scheduler: ActiveJobScheduler.new)
        end
    
        class ActiveJobScheduler
          def call(klass, serialized_event)
            klass.perform_later(serialized_event.to_h)
          end
    
          def async_handler?(klass)
            Class === klass && klass < ActiveJob::Base
          end
        end
      end
    end

RailsEventStoreActiveRecord

  • no changes

AggregateRoot

  • Change: Ensure publish does not incidentally receive an Enumerator (ade8f84)

RailsEventStore::RSpec

  • Add: publish matcher to verify expectation on given block of code. Disregards events published before expect { } block [#370]

    expect {
      MyService.new.call
    }.to publish(an_event(FooEvent)).in_stream("Foo$1234").in(event_store)

BoundedContext

  • no changes

RailsEventStore::Browser

  • no changes

RubyEventStore::ROM

  • Add: ROM Memory adapter implementation to allow easily adding alternate ROM implementations. This implements the ROM Memory adapter as an alternative to the ROM SQL adapter. Tests are structured to test ROM implementations easily. A new ROM adapter simply needs to implement the two relations required [#365]

RailsEventStoreActiveRecord::Legacy

  • no changes