设计方法论
系统设计不是灵感创作,是有章可循的工程过程。
1. 系统设计四步法
txt
1. 需求澄清 → 明确功能和非功能需求
2. 高层设计 → 画架构图,确定核心组件
3. 详细设计 → 深入关键组件的技术方案
4. 权衡讨论 → 讨论设计决策的 trade-off2. 需求澄清
功能需求
- 核心功能是什么?
- 用户场景有哪些?
- API 接口怎么设计?
非功能需求
| 维度 | 需要问的问题 |
|---|---|
| 并发量 | QPS 是多少?峰值是多少? |
| 数据量 | 存储多少数据?增长速度? |
| 延迟 | P99 延迟要求? |
| 可用性 | 几个 9?能容忍多长停机? |
| 一致性 | 强一致还是最终一致? |
3. 高层设计
txt
同步读链路(常见读路径):Client → LB → App Server → Cache
缓存未命中 → DB(回源后回填 Cache)
异步处理链路:App Server → Message Queue → Worker核心步骤:
- 画数据流图
- 确定核心组件
- 定义组件间接口
- 估算容量
4. 容量估算
容量估算用于在方案初期建立数量级直觉,结论是粗估而非精确值。
txt
假设:DAU = 1000万,每人每天 10 次操作
平均 QPS = 1000万 × 10 / 86400 ≈ 1200 QPS(全天请求均摊到 86400 秒)
峰值 QPS ≈ 3 × 1200 = 3600 QPS(峰值系数 3 只是示例假设)
存储:每条记录 1KB,每天 1亿条
日增量 = 1亿 × 1KB = 100GB/天
年增量 = 100GB × 365 = 36TB/年- 峰值系数 3 不是通用常数,实际峰值取决于活跃时段与业务事件,需用压测或历史流量标定。
- 1KB 是逻辑记录大小,实际存储占用还需计入索引、副本、日志与保留周期。
- 估算结果要回到单实例承载能力与压测数据,验证实例数量与冗余是否够用,方法见 高并发设计。
5. 常见设计模式
| 问题 | 方案 |
|---|---|
| 高并发读 | 缓存 + CDN + 读写分离 |
| 高并发写 | 消息队列 + 异步处理 |
| 大数据量 | 分库分表 + 冷热分离 |
| 高可用 | 主从 + 自动故障转移 |
| 低延迟 | 缓存 + 本地计算 |
上表是常见思路,不是一一对应的充分条件。消息队列能削峰解耦,却不会提升数据库的持续写入能力,消费速度长期低于生产速度时积压只会增长;主从加自动切换也不等于高可用,复制延迟、脑裂与切换期间的写入丢失仍需单独应对。选型要回到吞吐、延迟、一致性、运维复杂度与团队能力等维度综合判断,详见 高并发设计、高可用设计、高性能设计、可扩展设计。
6. 权衡讨论
每个设计决策都有 trade-off:
| 决策 | 选择 A | 选择 B |
|---|---|---|
| 数据库 | MySQL(成熟) | TiDB(分布式) |
| 缓存 | Redis(功能丰富) | Memcached(极简) |
| 消息队列 | RabbitMQ(低延迟) | Kafka(高吞吐) |
| 一致性 | 强一致 | 最终一致 |
表中标签只提示最突出的差异,不是选型的全部依据。强一致与最终一致不是「安全」与「性能」的对立,而是读写语义、故障模型与延迟预算的综合权衡;MySQL 与 TiDB 的取舍还要看数据规模、事务需求与运维成本。一致性模型见 CAP 理论与 BASE 理论。