Skip to content

0.29.0

Compare
Choose a tag to compare
@oskardudycz oskardudycz released this 14 Feb 08:48
· 53 commits to main since this release

🚀 What's New

1.Added first EventStoreDB consumer

You can set it up as:

const consumer = eventStoreDBEventStoreConsumer({ connectionString });

consumer.processor({ 
  eachMessage: (event: YourEventType) => {
    // do your handling here
  } 
});

await consumer.start();

by @oskardudycz in 189, 190

2. BREAKING: Renamed consumer subscriptions to processors.

Initially, I came up with the following split:

  • Consumers - primarily responsible for pushing messages to multiple handlers/subscribers.
  • Subscribers - diverse roles: Some store data, some trigger workflows, and some forward to other systems. Checkpointing is subscriber-specific, meaning each subscriber manages its own message state independently.

Still, after discussion, it appeared that Subscription in this context may be wrong or confusing. This could work to describe the relationship between the consumer and its individual subscribers. However, "subscription" often implies pub/sub semantics, where the subscriber initiates the relationship.

Here they just process messages they get passed by consumer. Also, since Emmetts’s subscribers also checkpoint and process messages independently, I decided to name them Processors.

Processor term is also common in event-processing frameworks, especially when the focus is on message handling or transformation. Processor is an independent unit that receives messages and performs an action (e.g., running a workflow, updating projections, forwarding to another service).

I was thinking about naming Consumer a Consumer Group, and Subscription Consumer. That would also work, but could confuse when I add Kafka support, as Emmett processing works differently in Kafka (it’s more fan out, so each processor gets the same batch of messages). That could create nasty confusion.

by @oskardudycz in 191

3. Added default event type to consumers

Thanks to that, processors will be automatically typed. This can be useful if we have multiple processors for the same stream subscription.

It's optional and falls back to the event, so each processor can still have its own event type (e.g. when subscribing to all events).

Another option is to put a union of all events in consumer and then use just a subset of those types in processors.

Added a deadline for consumer tests to stop them in case of some transient issue.

by @oskardudycz in 193

4. Added possibility to create consumers from directly from event stores

This will allow the PostgreSQL pool or EventStoreDB client to be reused, simplifying the potential setup and increasing performance.

For PostgreSQL event store this will look as:

const eventStore = getPostgreSQLEventStore(connectionString);

const consumer = eventStore.consumer();

consumer.processor({ 
  eachMessage: (event: YourEventType) => {
    // do your handling here
  } 
});

await consumer.start();

and from EventStoreDB:

const eventStore = getEventStoreDBEventStore(eventStoreDBClient);

const consumer = eventStore.consumer();

consumer.processor({ 
  eachMessage: (event: YourEventType) => {
    // do your handling here
  } 
});

await consumer.start();

by @oskardudycz in 194

📝 What's Changed

  • Enabled PostgreSQL consumer tests. They were not run by accidentally missing .spec in the file name 🤦‍♂️ by @oskardudycz in 192

Thanks also go to @mbirkegaard for the inspiration to make those changes.

Full Changelog: 0.28.0...0.29.0