mysql事务提交

举报
宁谷花雨 发表于 2022/01/12 20:05:59 2022/01/12
【摘要】 1、当事务commit时,需要将事务状态设置为COMMIT状态,这里同样通过Undo来实现的入口函数:trx_commit_low-->trx_write_serialisation_history  trx_undo_set_state_at_finish2、 二阶段提交流程时间点1prepare 阶段时间点2commit 阶段时间点3 时间点1出现问题这个时候redo log 和 bin...

1

当事务commit时,需要将事务状态设置为COMMIT状态,这里同样通过Undo来实现的

入口函数:trx_commit_low-->trx_write_serialisation_history

  trx_undo_set_state_at_finish

2

 二阶段提交流程

时间点1

prepare 阶段

时间点2

commit 阶段

时间点3

 

时间点1出现问题

这个时候redo log 和 binlog都在内存中,所以本次事务的相关操作都会消失,相对于事务回滚了,不影响数据的一致性。

时间点2出现问题

这个时候redo log已经到磁盘了。binlog没有刷到磁盘所以会消失。服务器从故障中恢复时,读取磁盘中的redo log ,但是由于对应的redo log项还是prepare状态,就要判断binlog 是否完整,如果binlog完整则提交事务,如果binlog不完整则回滚事务。

时间点3出现问题。

这个时候redo log 和 binlog都已经存磁盘,服务器从redo log恢复就好了。

binlog怎么判断完整性:

  • statement 格式的 binlog,最后会有 COMMIT;
  • row 格式的 binlog,最后会有一个 XID event

redolog 和binlog怎么联系起来:

它们有一个共同的数据字段,叫 XID。

崩溃恢复的时候,会按顺序扫描 redo log:如果碰到既有 prepare、又有 commit 的 redo log,就直接提交;如果碰到只有 parepare、而没有 commit 的 redo log,就拿着 XID 去 binlog 找对应的事务。

 来自 <https://www.cnblogs.com/wsw-seu/p/13215980.html>

 

3

redo日志仅记录对页的物理修改,不包含事务信息,因此在崩溃恢复时单纯依靠redo日志只能进行前滚,即恢复到崩溃前的内存状态。但是这个时候有些事务还没有提交(活跃事务)需要回滚,这就需要依赖undoundo中记录了未提交事务及修改行的原始版本,崩溃恢复时找到这些活跃事务将原始版本还原完成回滚。因此事务是否提交信息保存在undo里。

链接:https://www.zhihu.com/question/362498822/answer/951351986

 4

这些都是由事务性存储引擎来完成的,但 binlog 不在事务存储引擎范围内,而是由 MySQL Server 来记录的。

 那么就必须保证 binlog 数据和 redo log 之间的一致性,所以开启了 binlog 后实际的事务执行就多了一步,如下:

 

先记录 undo/redo log,确保日志刷到磁盘上持久存储。

更新数据记录,缓存操作并异步刷盘。

将事务日志持久化到 binlog。

提交事务,在 redo log 中写入commit记录。

这样的话,只要 binlog 没写成功,整个事务是需要回滚的,而 binlog 写成功后即使 MySQL Crash 了都可以恢复事务并完成提交。

 

要做到这点,就需要把 binlog 和事务关联起来,而只有保证了 binlog 和事务数据的一致性,才能保证主从数据的一致性。

 所以 binlog 的写入过程不得不嵌入到纯粹的事务存储引擎执行过程中,并以内部分布式事务(xa 事务)的方式完成两阶段提交。

5

疑问:事务的顺序提交问题,备机回放时怎么保证顺序提交的(相关信息是怎么通过redo传递的)?

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。