模块化单体到微服务:什么时候应该拆?
拆成多个服务后,每个服务可以独立发布,但本地调用也变成了可能超时的网络调用。先看独立扩容、团队协作或隔离需求是否真实存在,再决定是否拆分;仅仅目录多、代码多,并不足以支持这个决定。
版本与资料依据
last_verified:2026-08-24version_scope:stable architecture decision frameworksource_type:architecture literature + engineering synthesisstability:stable-concept
| 选择 | 判断条件 | 主要成本 |
|---|---|---|
| Stay monolith | 团队小、同一发布节奏、共享事务重要、运维能力有限 | 需控制耦合与构建规模 |
| Modular monolith | 业务边界可划分,但无需独立部署/扩缩;希望强制依赖 | 模块纪律、内部 API 与事件治理 |
| Split service | 明确团队所有权、独立部署/扩缩、数据所有权、故障隔离收益 | 网络失败、最终一致、平台、观察与安全成本 |
拆分前证据
- 模块 API 已稳定并有 contract tests;
- 该模块拥有数据,其他模块不直连其表;
- trace/metrics 证明独立扩缩或故障隔离有价值;
- 团队可运营 deploy、SLO、on-call、secret、migration;
- 事件/outbox/idempotency 已在单体内验证;
- 延迟与一致性变化得到业务接受。
“代码很多”不是充分理由。若拆分只增加 HTTP 而数据库仍共享,通常得到分布式单体。
用一个问题检验拆分收益
假设报表计算占用大量 CPU,拖慢了下单。先收集两类请求的耗时与资源使用,再比较进程内隔离、单独工作进程和独立服务三种方案。只有当独立部署或资源隔离的收益足够明确时,拆分才有可说明的理由。
还要做反向实验:报表服务断开后,下单能否继续?调用方等待多久?失败如何呈现?如果拆出服务以后每次下单仍同步等待它,原来的耦合可能只是变成了网络耦合。
本节的核验依据
2026-10-25 查阅。下面的链接支持本节的机制说明;练习场景和选型建议是本教程的教学设计。