Event Sourcing
01 / 02

Event Sourcing: Projections, Schema Evolution & CQRS

Event Sourcing: Projections, Schema Evolution & CQRS

Projections: Fast Reads Without Full Replay

Replaying the full event history on every read request would be prohibitively slow. A projection pre-computes and maintains a ready-to-query view (e.g. 'total orders this month'), updated incrementally as new events arrive -- reads query the fast projection instead of the raw event log.

Event Sourcing + CQRS

Distinct, complementary patterns often paired together -- the natural event stream Event Sourcing produces is an excellent source for building a CQRS read-side projection. Each can be used without the other, since they address genuinely different concerns.

Schema Evolution

# Adding a new required field to a widely-used event type is
# genuinely tricky, since past events can't be retroactively edited

Strategies:
- Version the event type -- handle both old and new schema shapes
  in the code that processes/replays events, with sensible defaults
  for missing fields on older versions
- "Upcasting" -- transform old-format events into the new format
  ON READ, without altering the actual stored historical events

Why It Fits Domain-Driven Design

PaymentDeclined { orderId, reason: 'insufficient_funds' } directly captures a meaningful business occurrence in the domain's own language -- more expressive than a raw UPDATE payments SET status = 'declined'. This alignment with genuine domain concepts is a commonly cited reason Event Sourcing pairs naturally with Domain-Driven Design.

When to Reach for Event Sourcing

  • Domains where the full audit trail is itself valuable (finance, insurance claims, healthcare) -- compliance/auditability comes for free rather than as a bolted-on afterthought.

  • Ability to reconstruct exact past state supports debugging ('what did this order look like last Tuesday').

  • Full historical event data supports building new, unanticipated analytics/projections later without having re-instrumented the system in advance.

  • Best justified by an actual identified need (real audit requirement, real historical-reconstruction use case) rather than adopted speculatively.

  • Apply selectively -- a financial ledger might benefit while a low-stakes settings feature doesn't need the added complexity.

Keep your own version of these notes — editable, searchable, and organised by your stack.

Start free