Trade-off Framing
Key Points
- Senior decisions are trade-offs, not "the right answer".
- ADRs (Architecture Decision Records): short docs; context, decision, consequences. Live with the code.
- Frame options as comparable: same dimensions across alternatives.
- "Good / fast / cheap, pick two" template is overused but useful.
- Write decision in present tense ("we choose X because"); rationale survives.
ADR template
# ADR-N: [decision title]
## Status: Accepted | Proposed | Superseded by ADR-M
## Context
What problem are we solving? What constraints?
## Options considered
### Option A: [name]
- Pros: ...
- Cons: ...
### Option B: ...
### Option C: ...
## Decision
We choose Option B because [rationale].
## Consequences
- Positive: ...
- Negative: ...
- Reversibility: hard / easy. To unwind: ...
## References
- [Linked PRs / docs / discussions]
Live in docs/adr/000N-...md. Numbered. Short (1-3 pages).
Why ADRs
- Future-self / future-team understands "why this way".
- Onboarding tool.
- Avoids re-litigating decisions.
- Surfaces unstated assumptions.
When to write
- Technology choice (Postgres vs Cosmos).
- Architecture pattern (sagas vs workflow engine).
- Significant migration.
- Standard / convention adoption.
NOT for: implementation details, trivial choices.
Framing options
Bad:
"We should use Service Bus."
Good:
"We considered: - Service Bus (managed; rich features; cost X). - RabbitMQ (open-source; on-prem; ops cost Y). - Kafka (high-throughput; replay; ops cost Z).
For our 1000 msg/sec workload + Azure infra + business events, Service Bus's DLQ + sessions outweigh the cost. We'd revisit if RPS exceeds 100K (Kafka territory)."
Comparing across dimensions
| Option A | Option B | Option C
Cost | $ low | $$ mid | $$$ high
Latency p99 | 50ms | 30ms | 100ms
Ops effort | high | low | low
Lock-in | low | high | mid
Maturity | mature | new | mature
Apples-to-apples comparison.
"Good / Fast / Cheap"
Pick two. Often deployed too lazily; use as starting point, then refine.
Quality high + Speed high → Cost high.
Cost low + Speed high → Quality low.
Quality high + Cost low → Speed low.
For real decisions, more dimensions matter (lock-in, ops, team familiarity).
Decision triggers
Document why a decision is reversible:
Decision: use Postgres.
If we hit X RPS or Y data size, revisit (Cosmos for global; Spanner for scale).
Sets future self up for principled re-evaluation.
RFC vs ADR
| Doc type | When |
|---|---|
| RFC: proposal for discussion | Pre-decision |
| ADR: decision recorded | Post-decision |
RFCs become ADRs. RFCs invite changes; ADRs document settled.
Writing under pressure
- One paragraph context.
- Three options bullets.
- One sentence decision + reason.
- Three consequence bullets.
That's a 1-page ADR. Better than no ADR.
Common framing mistakes
- ❌ Single option: "we'll use X" (no comparison).
- ❌ Vague: "we'll see how it goes".
- ❌ All-pros, no-cons.
- ❌ Bias: pre-decided answer dressed as analysis.
- ❌ Verbosity: 20 pages no one reads.
Tone
Technical writing, not marketing.
Acknowledge cons honestly.
Future you will read this; speak to them.
Communicating decisions
After ADR: - Announce in team channel. - Link from relevant docs. - Reference in code comments where it directly informs ("see ADR-12").
Updating decisions
When a decision changes: - New ADR with status "Supersedes ADR-N". - Old ADR updated to "Superseded by ADR-M". - Don't delete history.
In code reviews
When questioned: "Why this approach?" - Reply: "See ADR-7" or "Worth a new ADR; let me write one." - Reduces re-debate.
Senior considerations
- Decisions worth recording: anything someone could reasonably re-question in 6 months.
- Brevity wins: short ADRs read; long ones don't.
- Acknowledge uncertainty: "we're uncertain about X; revisit when Y".
- Build the muscle: write an ADR when you'd otherwise have a long Slack thread.