Microservices · Sagas

Microservice Sagas

The idea of microservices is to have distinct applications that have specialised tasks. The tasks can be combined to satisfy the requirements of disparate requests.

When there is a combination of microservices combined to satisfy some requests there is a need to ensure that all steps complete successfully.

This is where the Saga pattern comes in. Its job is to ensure that if the request does not complete all subtasks correctly then any subtasks that have completed already can be “undone”.

Before going further, one thing needs to be clear, there are two basic ideas that are used for Sagas, one explicit, one implicit, but, there’s absolutely nothing preventing a mix of the two from happening, or for the saga itself to be broken up into smaller sagas.

Orchestrator

The explicit, and simpler, option. A service that calls/sends messages to, the services, in order, to satisfy the request.

  • Pros
    • Easier for maintainers to see all the steps that take place for given type of request.
    • If one subtask fails the orchestrator can implement the strategy appropriate to recover, or rollback (eg. make a call to a different service)
    • The orchestrator is the keeper of state.
  • Cons
    • Single point of failure lives in the orchestrator (although this can be mitigated by storing the state externally, etc)
    • Strong coupling between orchestrator and services used to satisfy subtasks.

Choreographer

The implicit option. Each service that performs a subtask listens for events/messages and emits messages/events when complete.

  • Pros
    • Decoupled services mean steps can be added or removed without adjustments to an orchestrator.
  • Cons
    • Logic for rolling forward (and backward) is distributed amongst the services.
    • The logic for a failure is difficult (no sub task knows that a timeout has occurred for a subsequent subtask [or even that they might exist!], so a silent failure is ignored).

Mixer

As stated, there’s no reason that “pure” systems need exist, a request can easily be broken up into multiple smaller tasks that each have an orchestrator, and allow for choreography between those or other sub tasks, or be choreographed with some of the subtasks managed by an orchestrator.

As always, it’s about knowing the options, the advantages, and the disadvantages, and knowing what fits for an individual use case.

Published:
comments powered by Disqus