Akka Persistence | Event Sourcing

Embed Size (px)

Citation preview

Akka Persistence | Event Sourcing

Sidharth KhattriSenior Software ConsultantKnoldus Software

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

What is Event Sourcing?

storing all changes of a system as event log

changes here means Domain Events

changes are persisted in Event Store

event store is append only storage

no updates to Event Store, they're immutable

event log can be replayed to construct current state

In systems built around event sourcing, everything that happens (events) is persisted is a event log instead of just persisting the current state. An event log is a place which records all the events that happened in a system.

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

What are Domain Events?

something that already took place in a system

named as past-participle verbs

statement of facts

data transfer objects DTOs

immutable, because they're facts

represents state change in a system

Event is something that took place in a domain. These are always named with a past-participle verb, example EmailChanged. Since it is something that has already happened it can be considered as a statement of fact. Both Events and Commands are DTOs (Data transfer objects) and both are immutable. Events are immutable because they represent domain actions that happened in the past.

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

What are Commands?

something that triggers a Domain Event

named as imperative verbs

are requests but not statement of facts

data transfer objects DTOs

immutable, because they're are triggers

can be rejected

Command is something which makes the Event happen. It is used to request changes to the Domain. Since it is a request it can be rejected, it is not a statement of fact. It is a verb with imperative mood. Both Events and Commands are DTOs (Data transfer objects) and both are immutable. Commands are immutable because their only usage is to be sent from the client to server side to trigger and event.

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

What is CQRS?

CQRS stands for command query responsibility segregation

commands as write sides and query as read sides

commands involve domain model interaction

queries involve reporting module interaction

What is CQRS?

aggregate roots receives Commands and publish Events

aggregate is a group of associated objects

an aggregate has one root, which is an Entity

aggregate root is the only object accessible from outside world

Architecture Without CQRS

Architecture With CQRS

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

When to use Event Sourcing?

when keeping audit/event logs have great significance

for building scalable systems

for predicting future needs based on event logs

for better debugging

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

What is Akka Persistence?

provides reactive way of facilitating DDD/CQRS event sourced architecture

is implicitly event-driven

Agenda

What is Event Sourcing

What are Domain Events

What are Commands

What is CQRS

When to use Event Sourcing

What is Akka Persistence

Command side of Akka Persistence

What is PersistenceActor?

PersistenceActor is a trait which supports Event Sourcing

it can act as an Aggregate Root (AR) for DDD

its behavior is defined by receiveRecover and receiveCommand

receiveCommand acts as command handler

receiveRecover helps in replaying events

Command side of Akka Persistence

Command case class CreateUser(id: String, firstName: String, lastName: String, email: String)

Event case class UserCreated(id: String, firstName: String, lastName: String, email: String)

Imperative verb

Immutable

Past-participle verb

Immutable

object Protocols { case class Command(data: String) case class Event(data: String)}

final case class ExampleState(events: List[String] = Nil) { def updated(event: Event): ExampleState = copy(event.data :: events)

def size: Int = events.length

override def toString: String = events.reverse.toString()}

Persistence example protocols

For maintainingPersistence example state

class PersistenceExample extends PersistenceActor with ActorLogging { override def persistenceId: String = "persistence-example-1" var state = ExampleState()

def updateState(event: Event): Unit = state = state.updated(event)

def numEvents: Int = state.size val receiveRecover: Receive = { case event: Event => updateState(event) }

val receiveCommand: Receive = { case Command(data) => persist(Event(s"$data-${numEvents + 1}")) { event => updateState(event) } }}

Successfully persisted events are internally sent back to the persistent actor as individual messages that trigger event handler executions. An event handler may close over persistent actor state and mutate it. The sender of a persisted event is the sender of the corresponding command. This allows event handlers to reply to the sender of a command (not shown).

PersistenceActor Details

persistenceId method id of entity for which events should be replayed remains same across different actor incarnations

persist method

persists events asynchronously handler is only called on successful persistence between call to persist and execution of handler no new commands are received event handlers can update state, notify listeners and reply senders

PersistenceActor Details

override def recovery = Recovery(toSequenceNr = 457)

recovery method journals are automatically recovered on start and restart new messages sent to persistence actor during recovery do not interfere with replayed messages recovery can be disabled by using Recovery.none() initialization after recovery can be done can be done by handling RecoveryCompleted

References

http://doc.akka.io/docs/akka/2.4.0/scala/persistence.html

http://martinfowler.com/eaaDev/EventSourcing.html

http://cqrs.nu/faq

https://github.com/ironfish/akka-persistence-mongo-samples

http://pkaczor.blogspot.in/2014/04/reactive-ddd-with-akka.html

Thank You