![]() |
VOOZH | about |
Take a look at my self-paced, online bootcamp that teaches you how to use the Saga, API Composition, and CQRS patterns to design operations that span multiple services.
The regular price is $395/person but use coupon OFFEFKCW to sign up for $95 (valid until Sept 30th, 2025)
π ImageYou have applied the Database per Service pattern. Each service has its own database. Some business transactions, however, span multiple service so you need a mechanism to implement transactions that span services. For example, letβs imagine that you are building an e-commerce store where customers have a credit limit. The application must ensure that a new order will not exceed the customerβs credit limit. Since Orders and Customers are in different databases owned by different services the application cannot simply use a local ACID transaction.
How to implement transactions that span services?
Implement each business transaction that spans multiple services as a saga. A saga is a sequence of local transactions. Each local transaction updates the database and publishes a message or event to trigger the next local transaction in the saga. If a local transaction fails because it violates a business rule then the saga executes a series of compensating transactions that undo the changes that were made by the preceding local transactions.
There are two ways of coordination sagas:
An e-commerce application that uses this approach would create an order using a choreography-based saga that consists of the following steps:
Order Service receives the POST /orders request and creates an Order in a PENDING stateOrder Created eventCustomer Serviceβs event handler attempts to reserve creditOrderServiceβs event handler either approves or rejects the OrderTake a tour of an example saga
An e-commerce application that uses this approach would create an order using an orchestration-based saga that consists of the following steps:
Order Service receives the POST /orders request and creates the Create Order saga orchestratorOrder in the PENDING stateReserve Credit command to the Customer ServiceCustomer Service attempts to reserve creditOrderTake a tour of an example saga
This pattern has the following benefits:
This solution has the following drawbacks:
Lack of automatic rollback - a developer must design compensating transactions that explicitly undo changes made earlier in a saga rather than relying on the automatic rollback feature of ACID transactions
Lack of isolation (the βIβ in ACID) - the lack of isolation means that thereβs risk that the concurrent execution of multiple sagas and transactions can use data anomalies. consequently, a saga developer must typical use countermeasures, which are design techniques that implement isolation. Moreover, careful analysis is needed to select and correctly implement the countermeasures. See Chapter 4/section 4.3 of my book Microservices Patterns for more information.
There are also the following issues to address:
In order to be reliable, a service must atomically update its database and publish a message/event. It cannot use the traditional mechanism of a distributed transaction that spans the database and the message broker. Instead, it must use one of the patterns listed below.
A client that initiates the saga, which an asynchronous flow, using a synchronous request (e.g. HTTP POST /orders) needs to be able to determine its outcome.
There are several options, each with different trade-offs:
OrderApproved or OrderRejected event.orderID) after initiating the saga and the client periodically polls (e.g. GET /orders/{orderID}) to determine the outcomeorderID) after initiating the saga, and then sends an event (e.g. websocket, web hook, etc) to the client once the saga completes.The following examples implement the customers and orders example in different ways:
Order Service uses a saga orchestrator implemented using the Eventuate Tram Sagas frameworkMicroservices.io is created by Chris Richardson, software architect, creator of the original CloudFoundry.com, and author of Microservices Patterns. Chris advises organizations on modernization, architecture, and building systems that avoid becoming modern legacy systems.
Avoid the trap of creating a modern legacy system β a new architecture with the same old problems.
Contact me to discuss your modernization goals.
I am very excited to announce that the MEAP for the second edition of my book, Microservices Patterns is now available!
Learn moreGot a question about microservices?
Fill in this form. If I can, I'll write a blog post that answers your question.
I help organizations improve agility and competitiveness through better software architecture.
Learn more about my consulting engagements, and training workshops.
Chris offers numerous other resources for learning the microservice architecture.
Want to see an example? Check out Chris Richardson's example applications. See code
My virtual bootcamp, distributed data patterns in a microservice architecture, is now open for enrollment!
It covers the key distributed data management patterns including Saga, API Composition, and CQRS.
It consists of video lectures, code labs, and a weekly ask-me-anything video conference repeated in multiple timezones.
The regular price is $395/person but use coupon OFFEFKCW to sign up for $95 (valid until Sept 30th, 2025). There are deeper discounts for buying multiple seats.
Take a look at my Manning LiveProject that teaches you how to develop a service template and microservice chassis.
π ImageEngage Chris to create a microservices adoption roadmap and help you define your microservice architecture,
Use the Eventuate.io platform to tackle distributed data management challenges in your microservices architecture.
π ImageEventuate is Chris's latest startup. It makes it easy to use the Saga pattern to manage transactions and the CQRS pattern to implement queries.
Join the microservices google group