定位
作为非关系型数据库
经常与mysql对比
优点
- 扩展方便, 没有表结构的概念,随意增加字段(可以随意 但是不要随意)
- 单集合事务性能 + 非事务增删改性能均优于mysql
- 天生支持横向扩容 sharding(分片)
缺点
- 跨集合事务性能低。官方推荐使用嵌套文档,代替关系型数据库中的关联设计。但是设计时要注意不要把增长空间比较大的数据设计为嵌套文档, 首先设计上可能不合理,其次增长空间比较大的嵌套文档,优化和统计查询起来都比较麻烦。
搭建与配置
搭建参照官方文档
生产使用注意事项:
- 优先使用云服务
- 自建的话正式环境需要创建副本集,避免单节点崩溃
- mogno 默认无密码, 未配置授权时不要绑定外网ip
-
副本集
- 如果少数成员发生故障,则副本集仍然可以同时执行写操作和读操作。
但是,如果拥有大多数成员的数据中心发生故障,则副本集将变为只读。
- 如果少数成员发生故障,则副本集仍然可以同时执行写操作和读操作。
-
分片
分片至少需要两个分片才能分发分片的数据。如果您计划在不久的将来启用分片,但是在部署时不需要,则单个分片集群可能会很有用。
- 配置
- 将配置服务器部署为3个成员副本集
- 将每个碎片作为3个成员副本集进行部署
- 部署一个或多个mongos路由器
- 启动顺序
- configsvr 必须是副本集 配置服务 元数据
- shardsvr 必须是副本集
- mongos 网关
- 配置
注意事项
- 索引
- mongo 不只是mongo, 查询一定要命中索引
- 注意要有效的使用索引, 命中索引的同时,要控制索引的命中范围,范围过大等于没有索引
- 创建索引时要指定 background:true, 避免表数据量大卡住数据库
# 查看user_mobile_info表索引创建 进度 db.currentOp({"command.createIndexes":"user_mobile_info"})
- mongo的查询不会像mysql一样自动做类型转换, 查询时一定要使用对应类型(字符|数字)
- 一个字段可以同时存在字符类型和数字类型,使用时增改要特别注意
- 合理利用索引的expireAfterSeconds参数
- 所有索引都通过spring-data 注解创建,在编程时查看比较直观
- 事物
- 4.2版本之后事务支持比较完整,但跨集合事务有性能问题
- 磁盘释放
- remove 不会释放磁盘空间(继续占用会重复利用)
- drop 会释放部分磁盘空间
- repairDatabase 会重建空间和索引但是!
- 会锁住整个库
- 需要50%+ 的额外空间
- 时间较长
- 其他同类操作也会锁住库 或 表
库表内存占用比较大时空间释放会很麻烦、所以建立数据库时一定要做副本集!
逐个副本 repairDatabase 就没有什么问题了
mongodDB故障排查
- mongodDB崩溃
- 检查日志文件排查具体问题(文件路径在启动时指定)
- 重新启动,注意指定配置文件
- 优先考虑机器内存问题
- mognoDB卡顿
- 优先考虑索引问题, 以及网络问题
- 可以先从整体来看是写入还是读问题,使用mongostat 类似于UNIX / Linux文件系统实用程序vmstat,位于安装 目录/bin 目录下
- 通过慢日志查看具体问题,查看慢日志
- 常用命令
# 查看慢日志是否开启,以及级别和时间(毫秒) PRIMARY> db.getProfilingStatus() { "was" : 1, "slowms" : 200 } #查看级别 0 – 不开启 1 – 记录慢命令 (默认为>100ms) 2 – 记录所有命令 PRIMARY> db.getProfilingLevel() 1 # 设置级别和时间 PRIMARY> db.setProfilingLevel(1,200) { "was" : 2, "slowms" : 100, "ok" : 1 } # 案例(排除了某些表的慢日志结果,并按耗时大小排序(毫秒)) db.system.profile.find( { millis : { $gt : 100 }, ns:{$nin:["imoney.accountCheck","imoney.accountPay"]} } ).sort({millis:-1})
- 通过mongo日志查看有无异常
- 排查系统 网络 cpu 磁盘 内存 是否存在异常