Create your own
Lesson illustration

Choreography vs. Orchestration for Microservices

Hello! Let's dive into our second lesson in the "Distributed Transactions & Data Management" module.

In our last session, we established why the database-per-service pattern is fundamental to microservices, but also why it creates a major headache: maintaining data consistency across services without the safety net of traditional ACID transactions. We ended by identifying the core problem: how do you handle a business process that spans multiple services when any one of them could fail?

Today, we'll answer that question. This lesson directly addresses the learning outcome: Compare choreography vs. orchestration patterns for coordinating microservices, including their trade-offs. This is a classic topic in system design interviews, and being able to articulate the pros and cons of each approach demonstrates a mature understanding of distributed systems.

1. The Saga Pattern: A Framework for Distributed Transactions

When a single business transaction needs to update data across multiple services, we can't use a distributed transaction protocol like Two-Phase Commit (2PC) because it creates tight coupling and is often not supported by modern databases and message brokers.

Instead, we use the Saga pattern. A saga is a sequence of local transactions where each transaction updates data within a single service and then publishes an event or sends a command to trigger the next transaction in the sequence. If any transaction fails, the saga executes a series of compensating transactions to reverse the preceding transactions, thereby maintaining data consistency.

For example, if a customer's payment fails in an e-commerce order, a compensating transaction would cancel the order and release the reserved inventory.

There are two primary ways to coordinate the flow of a saga: Choreography and Orchestration. Let's explore each.

2. Choreography: A Decentralized, Event-Driven Dance

In the choreography pattern, there is no central coordinator. Each service involved in the saga knows its role and subscribes to events from other services. When a service completes its local transaction, it publishes an event to a message broker. Other services listen for these events and react accordingly.

Think of it like a choreographed dance performance where each dancer knows their cues based on the movements of the others, without a director shouting instructions from the sidelines. The communication is decentralized.

Saga pattern: Choreography and Orchestration - Medium

The following article provides an excellent overview of the choreography pattern, complete with diagrams illustrating its event-driven nature. This will help you visualize the flow of communication.

Please read the 'Choreography' section, focusing on the 'Overview' and the diagram under 'How Choreography Works'. Pay close attention to the role of the Event Broker and how services interact by publishing and subscribing to events.

As the article describes, the workflow is entirely event-based:

  1. Order Service creates an Order and publishes an OrderCreated event.
  2. Payment Service and Inventory Service both listen for the OrderCreated event.
  3. Payment Service processes the payment and publishes a PaymentProcessed event.
  4. Inventory Service reserves the stock and publishes an InventoryReserved event.
  5. Order Service listens for both PaymentProcessed and InventoryReserved and finally marks the order as APPROVED.

If the Payment Service had published a PaymentFailed event instead, the Order Service and Inventory Service would have to react by executing compensating transactions (e.g., cancelling the order and releasing the inventory).

3. Orchestration: A Centralized, Command-Driven Conductor

In the orchestration pattern, a central service—the orchestrator—is responsible for managing the entire transaction. The orchestrator tells each participant service what to do and when to do it, typically by sending commands. It acts as a conductor for an orchestra, explicitly directing each section.

The participant services don't need to know about each other or the overall workflow. They just need to know how to execute their operation when commanded by the orchestrator and how to report the outcome.

Saga pattern: Choreography and Orchestration - Medium

Now, let's look at the alternative approach. The same article provides a clear explanation of orchestration, highlighting its centralized control.

Please read the 'Orchestration' section's 'Overview'. Focus on the role of the central orchestrator and how it communicates with the other services to drive the workflow.

Using our e-commerce example, an orchestrated saga would look like this:

  1. A request comes to the Order Service, which creates an OrderSagaOrchestrator.
  2. The orchestrator saves the order as PENDING, then sends a ProcessPayment command to the Payment Service.
  3. The Payment Service attempts the payment and replies to the orchestrator with PaymentSuccessful or PaymentFailed.
  4. If successful, the orchestrator sends a ReserveInventory command to the Inventory Service.
  5. The Inventory Service replies, and if all is well, the orchestrator makes a final call to the Order Service to mark the order as APPROVED.

If any step fails, the orchestrator is responsible for sending compensating commands (e.g., RefundPayment, ReleaseInventory) to the relevant services in the reverse order.

4. The Trade-Offs: Choosing the Right Pattern

This is the most critical part for your interviews: understanding when and why to use one pattern over the other. There is no universally "better" pattern; the choice depends on the specific context and requirements of your system.

Saga pattern: Choreography and Orchestration - Medium

The article concludes with a direct comparison that summarizes the strengths and weaknesses of each approach. This is the key takeaway for this lesson.

Read the section 'Wrap up : Choreography vs Orchestration' and study the comparison table carefully. This table provides a concise summary of the trade-offs we're about to discuss.

Let's distill those points into the core trade-offs you'll be expected to discuss.

DimensionChoreographyOrchestration
CouplingLoosely Coupled: Services only know about the event broker, not each other. Adding new participants is easy—they just subscribe to an event.Coupled to Orchestrator: Participant services are dumb, but they are coupled to the orchestrator's API/commands. The orchestrator is tightly coupled to all participants.
ComplexitySimple Services, Complex Workflow: The business logic for each service is simple, but the overall workflow is implicit and distributed, making it hard to visualize and understand.Complex Orchestrator, Simple Services: The workflow logic is centralized and explicit in the orchestrator, making it easy to understand. However, the orchestrator itself can become a complex "god object".
Debugging & MonitoringDifficult: Tracking a transaction requires piecing together events across multiple services and logs. It's hard to know the current state of a saga without specialized tooling.Easier: The orchestrator provides a single place to monitor the state of a saga. You can query the orchestrator to see where a transaction is stuck.
Failure HandlingDecentralized: Each service is responsible for its own compensating transactions. No single point of failure. If one service is down, others might still process unrelated events.Centralized: The orchestrator is a single point of failure. If it goes down, no new transactions can proceed. It can also become a performance bottleneck.

When to choose Choreography:

  • For simple workflows involving only 2-4 services.
  • When you prioritize decentralization, loose coupling, and resilience above all else.
  • When you want to easily add new services to the workflow without modifying existing ones.

When to choose Orchestration:

  • For complex, long-running workflows involving many services.
  • When you need centralized control, error handling, and visibility over the entire process.
  • When the workflow involves complex logic like loops, conditional branching, or specific timeouts that are easier to manage in one place.
Test your understanding!

You are designing a user signup process for a new application. The process involves three services:

  1. AccountService: Creates the user account and credentials.
  2. EmailService: Sends a welcome email.
  3. ProfileService: Creates a default user profile.

The business requires that the welcome email is only sent after the account is successfully created. The profile can be created in parallel. If account creation fails, nothing else should happen.

Would you choose Choreography or Orchestration for this saga? Justify your decision based on the trade-offs.

Show answer

Orchestration is likely the better choice here, although a simple Choreography could also work.

Justification for Orchestration (Stronger argument):

  • Explicit Control Flow: The business logic has a clear sequence: AccountService must succeed before EmailService is triggered. An orchestrator makes this explicit: orchestrator.createAccount().then(orchestrator.sendWelcomeEmail()). This is much clearer and less error-prone than relying on event chains.
  • Centralized Logic & Visibility: While the flow is simple now, sign-up processes often grow in complexity (e.g., add fraud checks, provision analytics profiles, apply referral codes). Centralizing this logic in an orchestrator makes it easier to manage, modify, and monitor over time. The state of any user's signup process can be queried from a single place.
  • Low Number of Participants: With only three services, the "single point of failure" risk of an orchestrator is manageable and the complexity is low.

Argument for Choreography (A viable but weaker alternative):
One could implement this with choreography:

  1. AccountService creates the account and publishes AccountCreated.
  2. EmailService and ProfileService both subscribe to AccountCreated.
  3. Upon receiving the event, they perform their respective actions.

The main weakness here is the lack of explicit control. The EmailService is simply reacting to an event; the dependency on the AccountService is implicit. For a critical business rule like "email only after success," making that dependency explicit via orchestration is a safer, more maintainable design.

Conclusion

Today, we've broken down the two primary patterns for managing distributed transactions in microservices. You now have the vocabulary and mental models to compare and contrast them effectively.

Key Takeaways:

  • Sagas manage distributed transactions through a sequence of local transactions and compensating actions.
  • Choreography is a decentralized pattern where services communicate through events. It offers loose coupling and resilience but makes the overall workflow difficult to track.
  • Orchestration is a centralized pattern where an orchestrator directs participant services via commands. It provides visibility and control but introduces a single point of failure and tighter coupling to the orchestrator.
  • The choice between them is a classic trade-off between decentralization and simplicity (choreography) versus centralized control and visibility (orchestration).

Next Up

We've discussed the "what" and "why" of these patterns. In the next lesson, we'll get more practical. You will design a saga flow for a distributed transaction, outlining the specific events and compensation logic needed to ensure consistency. This will solidify your understanding by applying these concepts to a concrete problem.

Can't find a good explanation? Sign up and we'll make it for you

Sign up