The Rule, Precisely
each service owns its data store EXCLUSIVELY:
[orders]──►[orders-db] no other service connects.
[inventory]─►[inventory-db] cross-service data access:
APIs and EVENTS. never tables.
the forbidden topology (tragically common):
[orders] ─┐
├─► [shared-postgres: orders, inventory, users]
[inventory]┘ ▲
└─ all services' schemas mingled
why it's fatal to the architecture:
- schema change for orders breaks inventory's queries
- inventory's slow query = orders' connection pool starved
- deployments couple (migrations shared)
- you built distributed MONOLITH with extra network hops
What Replaces the Join
the #1 objection: "but I need orders JOIN users!"
old reflex: SELECT ... FROM orders o JOIN users u ...
new options:
1. API COMPOSITION: call both services, stitch in memory
(fine for low-fan-out UI queries)
2. EVENT-CARRIED STATE: user basics shipped IN order events;
local replica table → local joins ✓
3. READ-MODEL service: dedicated query service consuming
events from both; owns its denormalized
store (CQRS read-models lesson!)
4. DATA MESH/warehouse for analytics joins (not OLTP)
joins move from QUERY-TIME to SYNC-TIME.
that's the entire paradigm shift in one sentence.
The Costs You Accept
honest ledger of the rule:
- CROSS-SERVICE TRANSACTIONS die → sagas/outbox machinery
- CONSISTENCY becomes eventual across services
- N databases to operate (managed offerings blunt this)
- REPORTING needs aggregation pipelines (warehouse/CDC)
- DUPLICATED reference data (country codes everywhere —
acceptable! replicate stable references deliberately)
each cost has an established pattern (sagas, outbox,
CDC, CQRS). microservices = signing up for THAT PATTERN
LIBRARY, not just small deployment units.
Pragmatic Gradations
| Approach | When defensible |
|---|---|
| Separate SCHEMAS in one cluster | early stage; strict access rules |
| Separate DATABASES, one engine | standard case ✓ |
| Different ENGINE per need | polyglot persistence (search/cache) |
schema-separation is a migration path, not a destination —
treat it as explicit debt with a date attached,
or coupling will calcify permanently.
Interview Framing
“Orders and inventory both need product data — share the DB?” scored refusal: name the rule and WHY (coupling via schema/pools/deploy), present replacement patterns ranked by fan-out (API-compose → event-carried replicas → read-model service), accept the eventual-consistency consequence explicitly, note stable-reference replication as fine. Defending this rule under pressure is THE microservices interview test — it separates architects from distributed-monolith builders.
Premium Content
Unlock Database per Service and all premium lessons with a subscription.
All premium lessons
Ad-free experience
Priority support
From ₹199.99/year — See plans