Architecture Decision Record (ADR) Guide¶
CIDM 6330/6395 — Student Reference¶
What Is an ADR?¶
An Architecture Decision Record captures a single design decision for your project: what you decided, why you decided it, and what the consequences are.
Think of it as a lab notebook entry for software design. Scientists don't just record results — they record what they tried, why they tried it, and what happened. ADRs do the same for architectural choices.
What Counts as an "Architecture Decision"?¶
Any choice that would be hard to reverse later or that affects how the whole system works:
| Decision | Why It's Architectural |
|---|---|
| "We'll use SQLite instead of PostgreSQL" | Changes how every database interaction works |
| "Authentication will use JWT tokens" | Affects every endpoint, frontend, and test |
| "The API will be REST, not GraphQL" | Determines how clients consume data |
| "We'll separate billing into its own service" | Changes deployment, testing, and data flow |
| "Course search will use a local index, not live queries" | Affects performance, freshness, and complexity |
Things that are not ADRs: bug fixes, code formatting choices, which IDE to use, variable naming conventions. These are important but reversible.
Why Write ADRs?¶
The Knowledge Loss Problem¶
You make a design decision today. Three months from now:
- You forget why you chose that approach
- A teammate joins and asks "why is it done this way?"
- You consider changing it but can't remember the tradeoffs
Without an ADR, you either:
- Waste time re-discovering the reasoning, or
- Make a change that re-introduces a problem you already solved
The Communication Problem¶
On a team (or with an AI coding assistant), decisions need to be shared and explicit. An ADR ensures everyone — including future-you — knows:
- What was decided
- What alternatives were considered
- What tradeoffs were accepted
The Accountability Problem¶
When working with AI coding assistants (Claude, Copilot, etc.), the human must remain the architect. ADRs are how you prove you made the design decisions, not the AI.
"The human is index zero — first in priority, final in authority." — gzkit Zero Doctrine
How to Write an ADR¶
Step 1: State the Intent (2-3 sentences)¶
What specific problem or capability does this decision address? Connect it back to your PRD.
Weak: "We need a database."
Strong: "Course registration requires persistent storage of student enrollments, schedule conflicts, and course metadata. The storage layer must support concurrent reads during peak registration periods and survive server restarts."
Step 2: Record the Decision¶
State what you decided as a numbered list of concrete commitments:
## Decision
1. Use SQLite as the persistence layer for v1
2. Store the database file at `data/courses.db`
3. Use the repository pattern to abstract database access
4. Support in-memory SQLite for testing
Each item should be specific enough to implement. If a teammate reads this list, they should know exactly what to build.
Step 3: Document Consequences¶
Every decision has tradeoffs. Be honest about both sides:
### Positive
- No external database server to install or manage
- SQLite is included in Python's standard library
- File-based storage simplifies backup and portability
### Negative
- SQLite has limited concurrent write support
- No built-in replication or high-availability
- Will need migration if we outgrow SQLite
Step 4: List Alternatives Considered¶
What else did you consider, and why didn't you choose it?
## Alternatives Considered
- **PostgreSQL** — Better concurrency, but requires server
setup that adds complexity for a class project
- **MongoDB** — Document model doesn't fit our relational
course/student data well
- **Plain JSON files** — Too fragile for concurrent access;
no query capability
This section is critical because it shows you thought through options rather than grabbing the first thing that came to mind.
Step 5: Create a Feature Checklist¶
Break the decision into observable outcomes — things you can demonstrate or test when the work is done:
## Feature Checklist
1. [ ] Database schema created with courses, students, enrollments tables
2. [ ] Repository class with find, save, delete operations
3. [ ] In-memory adapter for unit tests
4. [ ] Migration script for schema changes
5. [ ] CLI command to initialize the database
Each checklist item becomes a task (see Task Guide).
Anatomy of an ADR¶
ADR-NNN: Title
│
├── Metadata ...................... ID, status, date, author
├── Intent ........................ WHAT problem are we solving?
├── Decision ...................... WHAT did we decide?
├── Consequences .................. WHAT are the tradeoffs?
│ ├── Positive
│ └── Negative
├── Alternatives Considered ....... WHAT else did we consider?
├── Feature Checklist ............. WHAT are the observable outcomes?
└── Approval ...................... WHO reviewed and agreed?
ADR Lifecycle¶
An ADR moves through these states:
Draft ──→ Proposed ──→ Accepted ──→ Completed
│
└──→ Superseded (replaced by a newer ADR)
└──→ Abandoned (decision reversed)
| Status | Meaning |
|---|---|
| Draft | Still being written; not ready for review |
| Proposed | Ready for review by instructor/team |
| Accepted | Approved; implementation can begin |
| Completed | All checklist items done and verified |
| Superseded | Replaced by a newer ADR (link to it) |
| Abandoned | Decision was reversed; record why |
Common Mistakes¶
| Mistake | Why It Hurts | Fix |
|---|---|---|
| Too many decisions in one ADR | Hard to track status; partial completion is ambiguous | One decision per ADR |
| No alternatives section | Looks like you didn't think it through | Always list at least 2 alternatives |
| Vague decision statements | "Use a good database" — which one? How? | Numbered, specific commitments |
| Skipping consequences | You'll forget the tradeoffs you accepted | Be honest about negatives |
| Never updating status | ADRs rot; nobody knows what's current | Update status as work progresses |
| Writing ADRs after implementation | It becomes documentation, not a decision record | Write the ADR before you code |
ADRs in Practice: A Small Example¶
Suppose your PRD says: "Students need to search for courses by department, time slot, and instructor."
ADR-001: Course Search Implementation
- Intent: Enable students to search courses using multiple criteria without requiring a full-text search engine.
- Decision:
- Implement search as filtered SQL queries against the courses table
- Support filtering by department, time slot, and instructor name
- Return results sorted by course number
- Limit results to 50 per page
- Positive consequences: Simple, no external dependencies, fast for our data size (~500 courses)
- Negative consequences: Won't scale to full-text search; no fuzzy matching
- Alternatives: Elasticsearch (overkill), whoosh (extra dependency), in-memory filtering (slow for large datasets)
- Checklist:
- Search repository method with filter parameters
- Unit tests for each filter type
- CLI or API endpoint for search
- Results pagination
Creating an ADR in gzkit¶
gzkit provides both CLI commands and skills for ADR creation.
CLI (terminal):
Skill (Claude Code session):
The /gz-plan skill is strongly recommended — it runs 20+ design
forcing-function questions (pre-mortem analysis, constraint archaeology,
reversibility assessment) that the raw CLI skips entirely. These questions
surface risks and alternatives before you commit to a decision.
For design exploration before committing to an ADR:
The /gz-design skill runs a collaborative design dialogue that produces
ADR artifacts after structured brainstorming.
From ADR to Tasks¶
Once an ADR is accepted, each checklist item becomes a task (called an OBPI — One Brief Per Item — in gzkit):
ADR-001: Course Search Implementation
├── Task 1: Search repository method with filter parameters
├── Task 2: Unit tests for each filter type
├── Task 3: CLI or API endpoint for search
└── Task 4: Results pagination
In gzkit, decompose checklist items into OBPI briefs:
| CLI | Skill | What it does |
|---|---|---|
gz specify slug --parent ADR-0.1.0 --item 1 |
/gz-obpi-specify |
Create and semantically author the OBPI brief |
The /gz-obpi-specify skill performs lane resolution from the ADR's WBS
table and validates decomposition scorecard alignment — raw CLI generates
thin placeholder briefs that require manual authoring.
See: Task Guide for how to structure these.
Template¶
A ready-to-use ADR template is available at: templates/adr-template.md
Video Companion¶
See Part 3 of the video tutorial series for a narrated walkthrough of the ADR template, the decomposition scorecard, and the reading list example.
Further Reading¶
- Michael Nygard's original ADR proposal — The format that started it all
- adr.github.io — Community resources and tooling
- gzkit ADR examples — Real ADRs used to govern this tool
- PRD Guide — How PRDs feed into ADRs