Event-Sourcing basic example app
Aim: learn basics of event-sourcing pattern and its caveats.
This project builds on example from presentation from Mathias Verraes - Practical Event Sourcing.
Event Sourcing / DDD / CQRS
- Greg Young's Event sourcing class + Greg Yong's CQRS documents (circa overview of course)
- Greg Young's hi-level overview of CQRS/DDD
- Querying Event Streams (wow!)
- SzymonPobiega's DDD reading list
- Greg Young's full and up-to-date DDD/CQRS/EventSourcing class
- Mathias Verraes' elaborate on domain events - Domain Events allow you to segregate the models of different systems
- unknown's Domain Driven Design Through Onion Architecture
DDD in PHP
- William Durand: DDD with Symfony2:
- Jan Kuchar's second sanbox
Message Buses / libraries
-
Prooph (cool one!)
- super flexible
- library: ability to mix&match
- well designed
- support for snapshotting
- unfortunately does not support Sagas yet! (contribution?)
- up-casting is strange: why it is not JIT up-cast? http://getprooph.org/event-store/upcasting.html
- Nested transaction? http://getprooph.org/event-store-bus-bridge/transaction_manager.html
-
broadway
- looks like not that good architecture, feature richer
- more like a framework then library (overkill?)
- looks like a some's project by product
Process Managers / Sagas (the same thing!)
- Jonathan Oliver: Sagas with Event Sourcing - first part, second part
- Jonathan Oliver: Sagas, Event Sourcing, and Failed Commands
- Udi Dahan: Saga Persistence and Event-Driven Architectures
Examples
- Mathias Verraes: Buttercup.Protects is a PHP library for building Aggregates that protect business invariants, and that record Domain Events.
- EventSourcing at BlaBlaCar + Matthieu Moquet: CQRS & Event Sourcing
Notes / TODOs
- How to make proper relation between Product and Basket?
- How to access product name when product-related event occurs - aggregate does not expose any state?! (should I access read model from write model?)
- If aggregate produces event but it does not change state in any way, should it have empty apply() method for this event or should framework just skip this event. (this can lead into hard discoverable typo errors)
- Is there any point of adding events when loading from history into object "recoded events"?