Skip to content

概念卡片:MongoDB副本集与分片集群

一句话机制:MongoDB 用副本集(Replica Set)解决单点高可用——主节点写、从节点通过 oplog 异步复制,主挂掉靠选举自动切换;用**分片集群(Sharded Cluster)**解决水平扩展——数据按 shard key 切成 chunk 分散到多个 Shard,由 mongos 路由 + config server 元数据协同。

副本集(Replica Set)

复制原理(oplog)

  • 主节点记录所有操作到 oploglocal.oplog.rs),从节点轮询读取并重放到自己的数据副本。
  • 从节点同步三步:① 查自己 oplog 最新时间戳 → ② 查主节点 oplog 大于该时间戳的记录 → ③ 插入自己 oplog 并执行。
  • oplog 幂等:同一操作执行多次效果等同一次(复制是「先复制数据、再写 oplog」,可能重复)。
  • 从节点宕机重启后,自动从 oplog 最后位置续传。

构成与选举

  • 最小构成:1 primary + 1 secondary + 1 arbiter;生产常见 primary + 2 secondary
  • 成员数应保持奇数(偶数加 arbiter);arbiter 只投票、不存数据。
  • 主节点故障 → 备份节点选举(多数票)成新主,自动故障转移;切换约 10~30 秒,期间写操作与强一致读失败,但可在从节点做最终一致读。

特殊成员类型

类型说明
Priority 0优先级 0,不能升主,用于多数据中心
Hidden对客户端隐藏,作备份/统计
Delayed数据延迟,作滚动备份/历史快照
Vote(arbiter)仅投票不存数据

分片集群(Sharded Cluster)

架构三组件

组件职责
Shard存储实际数据块;生产一个 shard 常是一个副本集(防单点)
Config Server存集群元数据(chunk 信息)
Query Router(mongos)前端路由,客户端接入,让集群看起来像单库

分片策略(shard key 划分)

策略原理取舍
范围(Range)shard key 按值域切成 chunk范围查询高效;但易数据不均
散列(Hash)按 hash 值建 chunk分布均匀;牺牲范围查询
自定义标签(Zone)打标签关联 shard key 范围,均衡器按标签迁移灵活控制数据分布
  • chunk 默认 64MB;集合数据只有超过一个 chunk 才会分散到多分片。
  • 范围 vs 散列:范围对范围查询友好但易倾斜;散列均匀但牺牲高效范围查询。

数据平衡(拆分 + 平衡)

  • 拆分(split):后台进程,chunk 涨到阈值一分为二,纯元数据操作不迁移数据。
  • 平衡器(balancer):后台进程,把块多的分片迁移到块少的分片,直到均衡;迁移过程源分片把文档发到目标分片、目标应用变更、更新 config server 元数据。
  • 迁移期间:更新立即在旧分片发生,然后复制到新分片;失败自动重试、数据只在新分片出现。

副本集 vs 分片集群(易混)

  • 副本集不是为读性能设计的——oplog 复制时读可能被阻塞;它是数据冗余 + 高可用
  • 提高读性能应该用分片 + 索引(读写分散到各 Shard)。
  • 副本集局限(分片集群解决的):所有写集中主节点、单副本集上限 12 节点、请求量大内存/磁盘不足、垂直扩展贵。

备份恢复

方式说明
文件快照需文件系统支持快照 + 开启 journal;恢复时 mongod 重放 journal
复制数据文件直接拷数据目录(需先加锁阻止写入);恢复时清空目录拷回
mongodump / mongorestore逻辑备份,导出/导入到指定目录

不变量(必须成立的约束)

  • 写操作只在 primary;从节点只读(且默认不对外)。
  • 副本集成员数应为奇数,偶数靠 arbiter 补齐投票。
  • 分片基于集合级别 + shard key,不是库级别。

常见误解

  • 以为副本集能提升读性能 → 副本集是冗余/高可用,读性能靠分片 + 索引。
  • 以为分片和副本是二选一 → 通常叠加:每个 shard 内部又是一个副本集(分片解决扩展,副本解决单点)。
  • 以为 MongoDB 写立即落盘 → 默认延迟写(syncPeriodSecs,默认 60s 内),靠 journal 兜底。

关联

最近更新