文章目录
第13章 分片
1 简介
- 分片(sharding)是一种将数据分布到多台计算机上的方法。MongoDB 使用分片来支持具有非常大数据集和高吞吐量操作的部署
- MongoDB 支持自动分片,可使数据库架构对应用程序不可见,简化系统管理
- 从开发和运营的角度,分片都是最复杂的 MongoDB 配置
2 理解集群的组件
- 为隐藏数据库架构细节,分片前要先执行 mongos 进行一次路由过程
- 路由器维护这内容列表,指明每个分片包含什么数据内容
- 应用程序只需要连接到路由服务器就可进行正常请求
3 搭建分片集群
- 参考此博客
第14章 配置分片
1 何时分片
-
不必太早分片,因为分片会增加部署难度,还要求作出(难以再改的)设计决策
-
不能运行太久后分片,因为过载的系统上不停机分片很困难
-
通常分片用来
- 增加可用 RAM
- 增加可用磁盘空间
- 减轻单台服务器负载
- 处理单个 mongod 无法承受的吞吐量
2 启动服务器
-
MongoDB分片群集由以下组件组成:
- 分片:每个分片包含分片数据的子集。 每个分片都可以部署为副本集
- mongos:充当查询路由器,在客户端应用程序和分片群集之间提供接口。
- 配置服务器:存储群集元数据和配置设置
-
配置服务器
- 配置服务器必须启用日志功能
- 每个配置服务器应位于单独的物理机器上,最好分布于不同的地理位置
- mongos 需从配置服务器获取配置信息,所以应先于任何 mongos 进程启动
- 配置服务器是独立的 mongod 进程,可以命令行启动
-
mongos 进程
- 必须使用
--configdb
选项启动 mongos - 默认端口为 27017
- 必须使用
-
副本集转为分片
- 如果有一个使用中的副本集,则其会成为第一个分片
- 需告知 mongos 副本集的名称与成员列表
-
增加集群容量
- 可在 mongos 上运行
addShard( )
命令将副本集作为分片添加到集群中
- 可在 mongos 上运行
-
数据分片
- MongoDB 不会自动对数据进行拆分,除非明确指定规则
- 数据分片示例:
- 对数据库启用分片:
db.enableSharding(dbName)
- 对集合分片:
sh.shardCollection(db.collection, {keyName: 1})
shardCollection()
命令将集合拆分为多个数据块,这是迁移数据的基本单元
3 MongoDB 如何追踪集群数据
- MongoDB 将文档分组为块(chunk),每个块有给定片键特定范围内的文档组成
- 一个块只能存在于一个分片上,故可用一个较小的表维护块与分片的映射
- 当一个块增长到特定大小(拆分阈值点)时,MongoDB 会自动将其拆分为两个较小的块
- 一个文档属于且只属于一个块,不可使用数组字段作为片键
- 块信息保存在
config.chunks
集合中
4 均衡器
- 均衡器(balancer)负责数据的迁移,它会周期性的检查分片间是否存在不均衡,存在则开始块的迁移
- 均衡会不会影响 mongos 正常的路由操作
- 查看
config.locks
集合可以查看哪个 mongos 是均衡器 config.locks
集合会追踪所有集群范围的锁_id
为 balancer 的文档就是均衡器
第15章 选择片键
1 检查使用情况
-
片键:对集合分片时,选择用于拆分数据的字段
-
对集合分片前的思考:
- 计划做多少个分片?
- 分片是为了减少读写延迟吗?
- 分片是为了增加读写吞吐量吗?
- 分片是为了增加系统资源吗?
2 数据分片
-
拆分数据的最常用数据分发方式:升序片键、随机分发的片键、基于位置的片键
-
升序片键
- 类似
date
字段或ObjectId
,是会随时间稳定增长的字段 - 所有写请求都被路由到一个分片
- 因为新块都由同一个分片创建,导致数据均衡处理困难
- 类似
-
随机分发的片键
- 随机分发的键可以是用户名、UDID、MD5或其他没有规律的键
- 数据的随机性意味着新插入的数据会比较均衡地分布在不同的块中
- 唯一弊端是MongoDB随机访问超出RAM大小的数据时效率不高
-
基于位置的片键
- 基于位置的片键可以是用户的IP、经纬度或地址
- 不一定与实际地理位置字段相关,是抽象的位置
- 数据会依据位置分组,可方便地将数据与相应的用户及相关联的数据保存在一起
3 片键策略
-
hash 片键
- hash 片键可使其他任何键随机分发,加载速度极佳
- 弊端是无法指定目标的范围查询
- hash 片键不能使用 unique 选项,不能使用数组字段,浮点数会被取整后再hash化
-
GridFS 的 hash 片键
- 对 GridFS 集合在
files_id
字段创建hash索引,则每个文件将会随机分发到集群中 - fs.files 集合比 fs.chunks 小得多
- 对 GridFS 集合在
-
流水策略
- 希望强大的服务器处理更多的负载,可以强制将所有新数据插入到高性能服务器
- 实现:将最大范围的块分布在SSD上
- 为SSD指定一个标签:
sh.addShaedTag("shardName": "ssd")
- 指定标签范围:
sh.addTagRange("dbName.colName", {"_id": ObjectId()}, {"_id": MaxKey}, "ssd")
-
多热点
- 复合片键的第一个值是比较粗略的随机值,势较低,第二个值是一个升序键
- 单个 mongod 处理升序写请求最有效
- 写请求分布在集群中时,分片最高效
4 片键规则和指导方针
-
片键限制
- 不可以是数组
- 向片键插入数组值也不被允许
- 文档一旦插入,其片键值就无法修改。要修改,必须删除文档
-
片键的势
- 键拥有的值比较少时,意味着该键作为片键时的势比较低
- 低势的键可与拥有多个值的键一起创建一个复合片键