mysql怎么找二叉树 mysql查询树形结构( 二 )


5、从节点启动另外一个线程(sql Thread ),把 Relay log 中的事件读取出来,并在本地再执行一次 。
mysql默认的复制方式是异步的 , 并且复制的时候是有并行复制能力的 。主库把日志发送给从库后不管了,这样会产生一个问题就是假设主库挂了,从库处理失败了,这时候从库升为主库后,日志就丢失了 。由此产生两个概念 。
全同步复制
主库写入binlog后强制同步日志到从库,所有的从库都执行完成后才返回给客户端,但是很显然这个方式的话性能会受到严重影响 。
半同步复制
半同步复制的逻辑是这样,从库写入日志成功后返回ACK确认给主库,主库收到至少一个从库的确认就认为写操作完成 。
还可以延伸到由于主从配置不一样、主库大事务、从库压力过大、网络震荡等造成主备延迟 , 如何避免这个问题?主备切换的时候用可靠性优先原则还是可用性优先原则?如何判断主库Crash了?互为主备的情况下如何避免主备循环复制?被删库跑路了如何正确恢复?( o )… 感觉越来越扯到DBA的活儿上去了 。
RedoLog
可以先通过下面demo理解:
饭点记账可以把账单写在账本上也可以写在粉板上 。有人赊账或者还账的话,一般有两种做法:
1、直接把账本翻出来,把这次赊的账加上去或者扣除掉 。
2、先在粉板上记下这次的账,等打烊以后再把账本翻出来核算 。
生意忙时选后者,因为前者太麻烦了 。得在密密麻麻的记录中找到这个人的赊账总额信息,找到之后再拿出算盘计算,最后再将结果写回到账本上 。
同样在MySQL中如果每一次的更新操作都需要写进磁盘 , 然后磁盘也要找到对应的那条记录,然后再更新,整个过程IO成本、查找成本都很高 。而粉板和账本配合的整个过程就是MySQL用到的是Write-Ahead Logging 技术,它的关键点就是先写日志,再写磁盘 。此时账本 = BinLog,粉板 = RedoLog 。
1、 记录更新时,InnoDB引擎就会先把记录写到RedoLog(粉板)里面 , 并更新内存 。同时,InnoDB引擎会在空闲时将这个操作记录更新到磁盘里面 。
2、 如果更新太多RedoLog处理不了的时候,需先将RedoLog部分数据写到磁盘,然后擦除RedoLog部分数据 。RedoLog类似转盘 。
RedoLog有write pos 跟checkpoint
write pos :是当前记录的位置 , 一边写一边后移,写到第3号文件末尾后就回到0号文件开头 。
check point:是当前要擦除的位置,也是往后推移并且循环的,擦除记录前要把记录更新到数据文件 。
write pos和check point之间的是粉板上还空着的部分,可以用来记录新的操作 。如果write pos追上checkpoint,表示粉板满了,这时候不能再执行新的更新,得停下来先擦掉一些记录,把checkpoint推进一下 。
有了redo log,InnoDB就可以保证即使数据库发生异常重启,之前提交的记录都不会丢失,这个能力称为crash-safe 。redolog两阶段提交:为了让binlog跟redolog两份日志之间的逻辑一致 。提交流程大致如下:
1 prepare阶段 -- 2 写binlog -- 3 commit
当在2之前崩溃时,重启恢复后发现没有commit,回滚 。备份恢复:没有binlog。一致
当在3之前崩溃时,重启恢复发现虽没有commit,但满足prepare和binlog完整,所以重启后会自动commit 。备份:有binlog. 一致
binlog跟redolog区别:
redo log是InnoDB引擎特有的;binlog是MySQL的Server层实现的,所有引擎都可以使用 。
redo log是物理日志,记录的是在某个数据页上做了什么修改;binlog是逻辑日志,记录的是这个语句的原始逻辑 , 比如给ID=2这一行的c字段加1 。

推荐阅读