背景mongodb3.2
mongodb ACID 事物支持
事务类型 | MongoDB的支持 | MySQL的支持 |
Atomicity | 单行/文档级原子性 | 多行原子性 |
Consistency | 强一致或最终一致 | 强一致 |
Isolation | 提交读 | 可重复读 |
Durability | 日志及复制 | 日志 |
原子性:
db.users.update({username : “tj.tang”},
{$set :{
salary : 500000,
jobs: [{}, {}, {}],
hours: 18
});
多行,多文档,多语句 的原子性-尚不支持。
一致性:
如何处理多文档一致性
通过建模来避免(多文档 合成为一个文档)
二阶段提交
记录日志, 人工干预
一致性: 可调一致性(可配置一致性)
强一致 APP 在主节点上进行读写(默认行为);
最终一致APP (在从节点上进行读);应用场景 后台报表
隔离级别:
3.2版本 支持READ uncomitted; read committed (mongodb 默认隔离级别); read uncommit 会出现脏读
持久性:
journal 文件 : 先写到这样文件,再写数据库;进一步再同步到从节点
MongoDB部署模式:
单机模式; 高可用复制集; 可扩展分片集群;
单机只是 测试开发来做。
线上部署: 建立 最少是1主2从。
单节点写操作过程图:
复制集写操作过程图:
恢复日志/ Journal :
用于系统宕机时恢复内存数据
默认:异步刷盘
刷盘间隔:
MMAP(存储引擎) : 30-100ms
WiredTiger(存储引擎): 100MB or Checkpoint
可 使用 j: 1 来强制同步刷盘。
写关注机制 / Write Concern :
用来指定mongod 对写操作的回执行为;
可在connection level 或者 写 操作level 指定;
支持以下值 :
w :0 | 1 | n | majority | tag
J: 1
wtimeout : millis
w : 0 //含义 : unacknowledged/ 不确认
无任何回执; 2.2 及 之前 版本的默认行为; 网络丢包, 系统崩溃,无效数据, 早期版本丢数据之罪魁祸首。
w : 1 //含义 Acknowledged /确认
Mongod 在写完内存后发送确认
2.4 之后默认行为
能够处理网络故障, 无效数据等错误状态; 如 可以发现唯一键错误
系统崩溃时,可能会丢失最多100ms数据。
j:1 Journaled
Journal 刷盘之后再发送写回执
30ms 间隔 Group commit—单个请求可能会等最多30ms 才返回。
图六:
w: 2/n/majority Replica Acknowledged
等待数据复制到n 个节点再发送回执
图七:
场景A : 未使用写关注
重现:
使用MongoDB2.2 或者指定{w:0} 写关注。
插入一些无效数据,如 10个文档同一个_id
检查实际插入数据数目
原因分析:
解决方法: 代码 改为{writeConcern:{w:1}};
场景B : 系统崩溃导致数据丢失:
重现:
w:1 高速持续写入数据
Kill -9 mongod
检查程序汇报写入的数据和实际插入的数据。
不是百分之百发送,操作两三次会发生一次:
代码:
原因分析:
解决: 代码改为:{writeConcern:{j:1}};
场景c : 主备置换/主备切换 导致数据丢失
重现:
w:1, j:1 高速持续写入数据
kill -9 mongod 主节点
连接到新的 主节点
实际插入的数据少于程序汇报的插入数据。
场景过程:
主备置换时的写操作
回滚操作:
解决方法: 代码改为:{w:majority} //确认数据写到大部分节点再返回。