MongoDB 4.2 首次支持分片集群事务,4.0 及之前仅支持单副本集内事务;4.2 引入两阶段提交与 config server 协调,但要求所有分片和 config server 均为 4.2+、启用 majority read concern、使用 WiredTiger 引擎且无仲裁节点,驱动也必须匹配协议。

MongoDB 4.2 之前根本不能对分片集合开启事务——不是“处理不好”,而是压根不支持。 4.0 版本的事务只在单个副本集内有效,一旦数据分布在多个分片上,session.startTransaction() 直接报错:Transaction is not supported on sharded clusters。这不是配置或驱动问题,是架构层面的硬限制。
4.0 的事务边界严格限定在单副本集内
哪怕你部署的是分片集群,只要事务操作涉及的数据落在同一个分片(即该分片本身是个副本集),4.0 仍可运行事务;但只要 mongos 路由到多个分片,事务就立即失败。关键判断依据是:sh.status() 显示有多个 shard,且操作命中了不止一个——此时 rs.status() 在每个 shard 上可能都正常,但事务 API 拒绝协调。
- 事务必须绑定
ClientSession,而 4.0 的 session 不具备跨分片上下文传播能力 - 没有 config server 参与事务状态跟踪,
config.transactions集合在 4.0 中不存在 - 驱动调用
startTransaction()时,mongos 会直接拦截并返回错误,不转发给任何 shard
4.2 是第一个真正支持分片事务的版本,但代价明确
4.2 引入两阶段提交(2PC)和 config server 协调机制,让跨分片事务成为可能,但所有参与节点必须满足硬性条件:
- 所有 shard 和 config server 必须运行 4.2+,且
featureCompatibilityVersion设为"4.2" - 必须使用 WiredTiger 引擎(MMAPv1 被彻底弃用)
-
replication.enableMajorityReadConcern必须开启,否则无法提供snapshot隔离级别 - 任意 shard 含仲裁器(arbiter)会导致事务中止——这是 4.2 明确禁止的拓扑
这些不是“建议”,而是服务端启动时校验失败就会拒绝服务的约束。
驱动版本不匹配会静默破坏事务语义
即使 MongoDB 服务端是 4.2,如果客户端用的是 4.0 驱动(比如老版 Node.js driver 3.x),事务行为会退化:事务可能看似成功,但实际未启用 2PC 协调,写操作被当作普通写入分散执行,丢失 ACID 保证。
- 错误现象:事务里更新两个分片的文档,其中一个成功、另一个失败,却没触发回滚
- 根本原因:4.0 驱动不识别 4.2 新增的事务协议字段,mongos 降级为逐分片执行,无协调
- 验证方式:连接 mongos 后执行
db.runCommand({getCmdLineOpts: 1})看parsed.sharding是否启用,再确认驱动日志是否输出Starting transaction on coordinator shard
分片事务从来不是“开个开关就行”的功能。4.2 的支持是架构重构的结果,而 4.0 及更早版本连事务协调的底层消息通道都没有。真正要落地,得同时过三关:服务端版本与配置、分片拓扑合规性、驱动协议兼容性——漏掉任何一个,事务就只是看起来像事务。

















