架构决策记录(ADR)
核心问题:如何记录和管理架构决策?ADR 的格式是什么?如何用 ADR 避免"决策失忆"?
1. 什么是 ADR
架构决策记录(Architecture Decision Record)是一种轻量级文档,记录项目中的重要技术决策及其上下文和理由。
2. ADR 模板
markdown
# ADR-{编号}: {标题}
## 状态
提议 | 已接受 | 已废弃 | 已替代(被 ADR-XXX 替代)
## 上下文
描述决策的背景:面临的问题、约束条件、相关因素。
## 决策
明确陈述做出的决策。
## 后果
分析决策带来的正面和负面影响。3. ADR 实战示例
markdown
# ADR-001: 选择 PostgreSQL 作为主数据库
## 状态
已接受
## 上下文
项目需要一个关系型数据库来存储核心业务数据。
团队对 MySQL 和 PostgreSQL 都有经验。
数据模型包含 JSON 字段和地理空间数据。
预计数据量在 3 年内增长到 1 亿条记录。
## 决策
选择 PostgreSQL 作为主数据库,备选方案为 MySQL 8.0。
理由(结合本项目约束):
1. 按地理坐标做距离检索是核心需求,PostGIS 的球面计算与空间函数比 MySQL 内置空间特性更完整,且后续可扩展路径分析等能力
2. JSON 字段以半结构化形式存储,JSONB 的二进制表示配合 GIN 索引可高效支持包含查询(字段等值过滤是否走索引取决于索引表达式与查询写法)
3. 许可证采用 PostgreSQL License,比 MySQL 的 GPL 更宽松,适合商业分发
## 备选方案
- MySQL 8.0:团队运维经验更多,但空间函数与 JSON 查询能力弱于 PostgreSQL,不能满足既定的空间分析需求。
## 后果
正面:
- JSONB 免去额外的文档数据库,空间查询可直接用 PostGIS
- 高级 SQL 特性减少应用层复杂度
负面:
- 团队部分成员需要学习 PostgreSQL 特性
- 运维工具链需要从 MySQL 生态切换
- 某些 ORM 的 PostgreSQL 方言可能有兼容性问题
## 重新评估条件
若地理空间查询与 JSON 半结构化存储这两项核心需求发生变化(如改用专门的地理数据引擎或文档数据库),或 MySQL 补齐空间查询能力且团队迁移成本可接受,可重新评估 MySQL 方案。4. 常见 ADR 分类
| 类别 | 示例决策 |
|---|---|
| 技术选型 | 数据库、消息队列、缓存方案 |
| 架构风格 | 单体 vs 微服务、同步 vs 异步 |
| 设计模式 | 认证方案、支付集成方式 |
| 编码规范 | 错误处理策略、日志规范 |
| 基础设施 | 部署方案、监控告警 |
5. 管理 ADR 的最佳实践
- 存储位置:
docs/adr/目录,与代码一起版本管理 - 命名规则:
ADR-{序号}-{简短标题}.md - 编号规则:递增编号,不重用已废弃的编号
- 状态管理:及时更新状态,常见状态为提议、已接受、已废弃、已替代
- 团队评审:重大决策需要团队讨论后记录
- 重新评估:关键约束变化、相关技术退役、运行结果偏离预期或出现重大事故时,重新评估相关 ADR;周期性盘点可作为补充机制
工具推荐:
- adr-tools:命令行工具(macOS 用
brew install adr-tools,Linux 可用 apt 或从源码安装) - adr-manager:VS Code 插件
- 简单方案:Markdown 文件 + Git 管理
决策发生变化时,优先新增一份 ADR 关联原记录并标记替代关系,而不是直接改写旧记录。
6. ADR 与 RFC 的区别
| 维度 | ADR | RFC |
|---|---|---|
| 主要目的 | 持久记录决策、依据与后果 | 提出方案并征求评审意见 |
| 典型状态 | 提议、已接受、已废弃、已替代 | 草拟、评审中、已采纳或已关闭 |
| 范围 | 架构和技术决策 | 任何重要变更 |
| 关系 | 可承载提议并记录最终决策 | 可作为 ADR 决策过程的一部分 |
核心原则:最好的架构决策是那些你能在 6 个月后仍然理解其理由的决策。ADR 就是帮你做到这一点的工具。不需要长篇大论,关键是记录"为什么"。