一、原理
当MySQL数据库执行数据的增、删、改操作时,会将这些事件记录到二进制日志中,这些日志会被发送到每台从服务器上。
从服务器上有两个线程:I/O线程和SQL线程,I/O线程用于接收日志并将其转换为中继日志;SQL线程将中继日志的内容进行应用。
MySQL的主从复制通过日志的传递和应用,实现从服务器与主服务器的数据一致。
应用程序客户端连接到一个主数据库,主数据库负责运行全部事务,并且负责在二进制日志中记录所有可能改变MySQL数据库状态的事件。
二、复制方法
MySQL的主从复制支持两种复制方法,一种是使用二进制日志文件名称和事件的位置,另一种是使用GTID。
(一)使用二进制日志文件名称和事件的位置来执行事件或应用更改,并同步主服务器和从服务器之间的数据。
(二)使用GTID(全局事务标识符)的方法具有事务性,不需要处理日志文件或这些文件中的位置,该特性大大简化了许多常见的复制任务。使用GTID进行复制可以保证主服务器和从服务器之间的一致性。
主从复制可以用于备份,分离读写工作负载,并在主服务器发生故障/宕机时创建冗余。MySQL没有提供内置的自动故障转移机制,用户需要手动切换并将从服务器变为活动状态。
三、分类
主从复制有两种类型:异步复制和半同步复制
1.异步复制
当用户将服务器配置为从服务器时,复制过程由从服务器发起,通过与主服务器通信,从服务器将请求主服务器提供自它接收到最后一次更新以来的更新事件,主服务器将在每次状态更改时记录事件,即使从服务器延迟增加或者无法通信,主服务器也将持续处理。这种方式被称为异步复制。
MySQL 复制的默认类型是异步复制。主服务器将事件写入二进制日志,从服务器请求这些更新的日志。主服务器无法确定从服务器是否已经接收并处理了事务,也不保证事件会送达从服务器。
在使用异步复制时,如果主服务器崩溃,则它提交的事务可能没有传输到任何一台从服务器。在这种情况下,如果主服务器执行故障转移到从服务器,可能会导致将故障转移到缺少事务的服务器上。
2.半同步复制
注意,主服务器上的事务已经写入二进制日志,但是在提交到存储引擎时需要等待,直到它收到至少一台从服务器返回的确认信息。
从服务器确认它已经接收一个事务的所有事件,并写入中继日志,保存到磁盘,但不需要在从服务器上应用更改。因此,半同步复制可以保证当主服务器崩溃或发生故障时,它提交的所有事务都已被传送到从服务器。
当从服务器连接到主服务器时,从服务器需要识别是否具有半同步能力,如果具有半同步能力,主服务器的线程执行一个事务提交将被阻挡并等待,直到至少有一台从服务器确认已收到所有事件的事务,或者发生等待超时,只有在事件被写入中继日志并保存到磁盘之后,从服务器才会确认接收事务的事件。
如果在没有任何从服务器确认事务的情况下发生超时,那么主服务器将改为异步复制,一旦有采用半同步复制的从服务器追赶上主服务器时,主服务器复制将恢复为半同步复制。与异步复制相比,半同步复制提供了更好的数据完整性,当提交成功返回时,用户可以确保数据至少存在于两台不同的服务器上。
半同步复制可以通过变量控制从服务器确认接收日志的时间点。该变量名称为rpl_semi_sync_master_wait_point,它有两个选项值:AFTER_SYNC和AFTER_ COMMIT。
1.AFTER_SYNC:默认值,主服务器将每个事务写入其二进制日志,并将二进制日志同步到磁盘。同步完成后,主服务器等待接收事务的从服务器确认。接收确认信息后,主服务器将事务提交给存储引擎,并将结果返回给客户端,然后客户端可以继续处理
2.AFTER_COMMIT:主服务器将每个事务写入其二进制日志,同步二进制日志,并将事务提交到存储引擎。提交后,主服务器等待接收事务的从服务器确认。接收确认信息后,主服务器将结果返回给客户端,然后客户端可以继续处理
在执行故障转移后,原来的主服务器不能重新启动,因为原来的主服务器会存在未提交的事务,如果重启,进行崩溃恢复,会与从服务器上面的数据产生冲突。