Skip to content

RubyEventStore::Projection does not yield events in deterministic order when using multiple streams #1550

@Bertg

Description

@Bertg

Given I have some events in my database:

{id: 1, data: {...}, timestamp: "2023-01-19Z01:01:01"} on stream "A"
{id: 2, data: {...}, timestamp: "2023-01-19Z01:01:02"} on stream "B"
{id: 3, data: {...}, timestamp: "2023-01-19Z01:01:03"} on stream "A"

When I run a projection like so: RubyEventStore::Projection.from_stream(%w(A B)) the events will be returned in order: 1,3,2.
However, if I switch the order of the streams: RubyEventStore::Projection.from_stream(%w(B A)) the events will be returned in order: 2,1,3.

My expectation is that the order of the events should be in the order of the data, regardless of streams. In other words, the order of the stream names in the array should not affect the order in which the events are returned.

Example test in test is added here: Bertg@bcc2cab, and included as example here:

specify "reduce events from many streams in order" do
  event_store.with_metadata(timestamp: Time.utc(2018, 1, 1, 1, 1, 1)) {
    event_store.append(MoneyDeposited.new(data: { order: 1 }), stream_name: "Customer$1")
  }
  event_store.with_metadata(timestamp: Time.utc(2018, 1, 1, 1, 1, 2)) {
    event_store.append(MoneyDeposited.new(data: { order: 2 }), stream_name: "Customer$1")
  }
  event_store.with_metadata(timestamp: Time.utc(2018, 1, 1, 1, 1, 3)) {
    event_store.append(MoneyDeposited.new(data: { order: 3 }), stream_name: "Customer$2")
  }

  account_balance =
    Projection
      .from_stream(%w[Customer$2 Customer$1])
      .init(-> { { order: nil } })
      .when(MoneyDeposited, ->(state, event) {
        puts event.timestamp
        state[:order] = event.data[:order]
      })
      .run(event_store)
  expect(account_balance).to eq(order: 3)
end

This fails with:

  1) RubyEventStore::Projection reduce events from many streams in order
     Failure/Error:

       expected: {:order=>3}
            got: {:order=>2}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions