✅ Category: Distributed Transactions / Microservices
✅ Problem: How to maintain data consistency across multiple microservices without 2PC (two-phase commit).
✅ Solution: Break long transactions into a series of local transactions. Each has a compensating action (undo) if something fails.
🔑 Key Points
Orchestration Saga → Central coordinator tells services what to do.
Choreography Saga → Services listen to events and react accordingly.
Each step = Local transaction + Possible compensating action.
🖥️ C# Example – E-Commerce Order (Orchestration Saga)
Scenario:
Place Order
Reserve Payment
Update Inventory
If failure → rollback via compensating transactions
// Step definitions
public interface ISagaStep
{
Task ExecuteAsync();
Task CompensateAsync();
}
public class PaymentStep : ISagaStep
{
public async Task ExecuteAsync() => Console.WriteLine("✅ Payment Reserved");
public async Task CompensateAsync() => Console.WriteLine("❌ Payment Refunded");
}
public class InventoryStep : ISagaStep
{
public async Task ExecuteAsync() => Console.WriteLine("✅ Inventory Updated");
public async Task CompensateAsync() => Console.WriteLine("❌ Inventory Restored");
}
// Orchestrator
public class SagaOrchestrator
{
private readonly List<ISagaStep> _steps = new();
public void AddStep(ISagaStep step) => _steps.Add(step);
public async Task ExecuteAsync()
{
var executedSteps = new Stack<ISagaStep>();
try
{
foreach (var step in _steps)
{
await step.ExecuteAsync();
executedSteps.Push(step);
}
Console.WriteLine("🎉 Saga Completed Successfully!");
}
catch
{
Console.WriteLine("⚠️ Error! Starting Compensation...");
while (executedSteps.Count > 0)
await executedSteps.Pop().CompensateAsync();
}
}
}
Usage:
var saga = new SagaOrchestrator();
saga.AddStep(new PaymentStep());
saga.AddStep(new InventoryStep());
await saga.ExecuteAsync();
🌍 Real-World Example
📌 Remember in Interview
Saga = Long transaction broken into smaller steps.
Each step = do + undo (compensating action).
Two styles: Orchestration (central brain) vs Choreography (event-driven).
Prevents inconsistency in distributed microservices.