MySQL-主从复制:概述、原理、同步数据一致性问题、搭建流程
主从复制
1. 主从复制概述
1.1 如何提升数据库并发能力
一般应用对数据库而言都是“读多写少
”,也就说对数据库读取数据的压力比较大,有一个思路就是采用数据库集群的方案,做主从架构
、进行读写分离
,这样同样可以提升数据库的并发处理能力。但并不是所有的应用都需要对数据库进行主从架构的设置,毕竟设置架构本身是有成本的。
如果我们的目的在于提升数据库高并发访问的效率,那么首先考虑的是如何优化SQL和索引
,这种方式简单有效;其次才是采用缓存的策略
,比如使用 Redis将热点数据保存在内存数据库中,提升读取的效率;最后才是对数据库采用主从架构
,进行读写分离。
1.2 主从复制的作用
第1个作用:读写分离。
第2个作用就是数据备份。
第3个作用是具有高可用性。
2. 主从复制的原理
2.1 原理剖析
三个线程
实际上主从同步的原理就是基于 binlog 进行数据同步的。在主从复制过程中,会基于3 个线程
来操作,一个主库线程,两个从库线程。
二进制日志转储线程
(Binlog dump thread)是一个主库线程。当从库线程连接的时候, 主库可以将二进制日志发送给从库,当主库读取事件(Event)的时候,会在 Binlog 上加锁
,读取完成之后,再将锁释放掉。
从库 I/O 线程
会连接到主库,向主库发送请求更新 Binlog。这时从库的 I/O 线程就可以读取到主库的二进制日志转储线程发送的 Binlog 更新部分,并且拷贝到本地的中继日志 (Relay log)。
从库 SQL 线程
会读取从库中的中继日志,并且执行日志中的事件,将从库中的数据与主库保持同步。
复制三步骤
步骤1:Master
将写操作记录到二进制日志(binlog
)。
步骤2:Slave
将Master
的binary log events拷贝到它的中继日志(relay log
);
步骤3:Slave
重做中继日志中的事件,将改变应用到自己的数据库中。 MySQL复制是异步的且串行化的,而且重启后从接入点
开始复制。
复制的问题
复制的最大问题:延时
2.2 复制的基本原则
-
每个
Slave
只有一个Master
-
每个
Slave
只能有一个唯一的服务器ID -
每个
Master
可以有多个Slave
3. 同步数据一致性问题
主从同步的要求:
-
读库和写库的数据一致(最终一致);
-
写数据必须写到写库;
-
读数据必须到读库(不一定);
3.1 理解主从延迟问题
进行主从同步的内容是二进制日志,它是一个文件,在进行网络传输
的过程中就一定会存在主从延迟
(比如 500ms),这样就可能造成用户在从库上读取的数据不是最新的数据,也就是主从同步中的数据不一致性
问题。
3.2 主从延迟问题原因
在网络正常的时候,日志从主库传给从库所需的时间是很短的,即T2-T1的值是非常小的。即,网络正常情况下,主备延迟的主要来源是备库接收完binlog和执行完这个事务之间的时间差。
主备延迟最直接的表现是,从库消费中继日志(relay log)的速度,比主库生产binlog的速度要慢。造成原因:
1、从库的机器性能比主库要差
2、从库的压力大
3、大事务的执行
3.3 如何减少主从延迟
若想要减少主从延迟的时间,可以采取下面的办法:
-
降低多线程大事务并发的概率,优化业务逻辑
-
优化SQL,避免慢SQL,
减少批量操作
,建议写脚本以update-sleep这样的形式完成。 -
提高从库机器的配置
,减少主库写binlog和从库读binlog的效率差。 -
尽量采用
短的链路
,也就是主库和从库服务器的距离尽量要短,提升端口带宽,减少binlog传输的网络延时。 -
实时性要求的业务读强制走主库,从库只做灾备,备份。
3.4 如何解决一致性问题
读写分离情况下,解决主从同步中数据不一致的问题, 就是解决主从之间 数据复制方式 的问题,如果按照数据一致性 从弱到强 来进行划分,有以下 3 种复制方式。
方法 1:异步复制
MVSQL默认的复制方式,在异步复制的方式中主库在执行完事务操作以后,会立刻给客户端返回。他不需要关心从库是否完成该事务的执行。
这种方式会导致一个问题,那就是当主库出现故障时,主库虽然事务执行完了但是可能还没来得及把数据同步给从库,就挂了。那么当从库升级为主库之后,他会丢失了这次事务的变更内容。
方法 2:半同步复制
半同步复制是介于全同步复制和异步复制之间的一种方案。他再执行完一个事务之后,也不会立刻给客户端反馈,但是也不会等所有从库都完成事务,而是等其中一个从库完成接收到事件之后,再反馈给客户端。
在半同步复制这个方案中,会在事务提交的2阶段都完成之后,等待从库接收到binlog,然后再返回成功。
方法 3:组复制
首先我们将多个节点共同组成一个复制组,在执行读写(RW)事务
的时候,需要通过一致性协议层(Consensus 层)的同意,也就是读写事务想要进行提交,必须要经过组里“大多数人”(对应 Node 节点)的同意,大多数指的是同意的节点数量需要大于 (N/2+1),这样才可以进行提交,而不是原发起方一个说了算。而针对只读(RO)事务
则不需要经过组内同意,直接 COMMIT 即可。
方法 4:全同步复制
全同步复制的这个方式中,当主库执行完一个事务之后,他会等待所有的从库完成数据复制之后,才会给客户端反馈。这种方式安全性可以保障了,但是性能很差。如果从库比较多的话,会导致整个过程更加长。
4、主从复制-搭建流程
4.1 环境准备
一主一从,默认安装好了MySQL了,需要安装,可以参考
节点 | ip | 数据库 | 角色 |
---|---|---|---|
节点1 | 192.168.3.131 | Mysql | 主j节点 |
节点2 | 192.168.3.137 | Mysql | 从节点 |
4.2 主节点配置
主节点需要做的工作就是创建用户并赋予权限,然后开启binlog
日志。
首先创建给从节点登录用的账号和密码,如下
#查看主节点的登录名账号,没有用于从节点登录的账号密码
select Host,User from user;
create user 'slave01'@'192.168.3.137' identified by '123456';
select Host,User from user;
授予从节点登录主节点验证的权限
由于MySQL的版本问题,我这个是8.0版本的,在授权语句后面加上identified by '123456'
会报错,所以,我此处,没加
grant replication slave on *.* to 'slave01'@'192.168.157.137';
显示确认一下授予权限的情况
show grants for 'slave01'@'192.168.3.137';
修改mysql配置文件
vim /etc/my.cnf
#主从复制配置
log-bin=mysql-bin
server-id=131 #和从节点不一样即可
4.3 从节点配置
从服务器需要做的工作就是配置同步日志,指定主节点的ip,端口,用户,密码等,然后启动从节点
修改mysql配置文件
#主从复制配置
log-bin=mysql-bin
server-id=137
重启从节点mysql
先在主节点mysql上查看master信息
show master status;
在从节点的MySQL上指定主节点信息
change master to master_host='192.168.3.131',master_user='slave01',master_password='123456',master_log_file='master-a-bin.000001',master_log_pos=156;
- master_host 是主节点ip
- master_user 和 master_password 是主节点创建给从节点的账号和密码
- master_log_file 和master_log_pos 根据上一步查询出来的File和Position值自行更换。
启动从节点
start slave;
最终这两个参数都是yes就搭建完成了,但是也要注意是否有报错信息
判断是否成功主要看 Slave_IO_Running 和 Slave_SQL_Running 是否都为YES。
上面的两个yes,笔者也走过很多弯路,才走到的,并不是一下子就成功的,下面我归纳一下,我搭建过程中遇到的问题
4.4 遇到报错解决
情况1:Slave_IO_Running为No
由于有些同学为了方便,服务器都是克隆的,所以就会造成安装目录auto.cnf文件里对比server-uuid
是一样的,可以自行排查一下
解决办法:
首先安装目录auto.cnf文件里对比server-uuid 是否一样,如果一样修改了不一样就行,或者删了文件重启mysql服务。
cat /var/lib/mysql/auto.cnf
保持server-uuid不一样即可
情况2:Slave_IO_Running为Connecting
发生Slave_IO_Running为Connecting的情况很多,大家可以参考这篇文章:花开城南,这篇文章基本归纳了出现Connecting的情况,但是,我的遇到问题还不是这里面的
查看报错信息
发现是密码的认证方式有问题,上网查了一下,该博主 周杰伦的稻香的解决方法可以,我采用的是第一种方法,但是每次重启服务器或者MySQL服务,都需要现在从服务器节点的MySQL上,登录一下主节点的MySQL,请求服务器公钥
mysql -u slave01 -p -h 192.168.3.131 -P3306 --get-server-public-key
在这种情况下,服务器将RSA公钥发送给客户端,后者使用它来加密密码并将结果返回给服务器。插件使用服务器端的RSA私钥解密密码,并根据密码是否正确来接受或拒绝连接。
- 主从节点都重新停止主从复制,清空之前的主从复制配置信息
- 在从库配置change masrer to并且start slave,复制可以正常启动:
#主从节点都停止主从复制,在两个MySQL客户端中分别执行
#清空之前的主从复制配置信息
stop slave;
reset master;#从新配置主从复制
change master to master_host='192.168.3.131',master_user='slave01',master_password='123456',master_log_file='master-a-bin.000001',master_log_pos=156;
情况3:Slave_IO_Running为Connecting,报错:could not find first log file name in binary log index file
解决方法:
stop slave;
reset slave;
start slave;
情况4:主从服务器的MySQL的master状态不一致
重启过,配置信息会发生变化
因为之前已经创建过主节点服务器,需停掉之前的配置 再重新配置
stop slave;
reset master;
需要重新指定主节点服务器信息
change master to master_host='192.168.3.131',master_user='slave01',master_password='123456',master_log_file='master-a-bin.000002',master_log_pos=156;
主节点数据库备份操作
使用mysqldump命令,将test数据库备份下来
mysqldump -uroot -p'123456' -B test > /backup/mysql_bak.$(date +%F).sql.gz
远程发送到从节点上
scp /backup/mysql_bak.2024-04-01.sql.gz 192.168.3.137:/backup/
从库数据库还原操作
先创建数据库,否则没有数据库名,会报错
mysqldump -uroot -p'123456' -B test < /backup/mysql_bak.$(date +%F).sql.gz
从库已备份到主库的数据库
4.5 主从复制测试
在主节点创建数据库,名称为配置文件里需要同步的数据库名称,例如
create database db_test;
查看从节点,已经同步
创建一个表
CREATE TABLE `departments` (`department_id` int NOT NULL DEFAULT '0',`department_name` varchar(30) NOT NULL,`manager_id` int DEFAULT NULL,`location_id` int DEFAULT NULL,PRIMARY KEY (`department_id`),UNIQUE KEY `dept_id_pk` (`department_id`),KEY `dept_loc_fk` (`location_id`),KEY `dept_mgr_fk` (`manager_id`)
)
可以看到,从节点也已经同步。
插入数据
INSERT INTO `departments` VALUES ('10', 'Administration', '200', '1700');
可以看到,数据也已经同步。
相关文章:

MySQL-主从复制:概述、原理、同步数据一致性问题、搭建流程
主从复制 1. 主从复制概述 1.1 如何提升数据库并发能力 一般应用对数据库而言都是“读多写少”,也就说对数据库读取数据的压力比较大,有一个思路就是采用数据库集群的方案,做主从架构、进行读写分离,这样同样可以提升数据库的并…...

论文阅读《Semantic Prompt for Few-Shot Image Recognition》
论文地址:https://arxiv.org/pdf/2303.14123.pdf 论文代码:https://github.com/WentaoChen0813/SemanticPrompt 目录 1、存在的问题2、算法简介3、算法细节3.1、预训练阶段3.2、微调阶段3.3、空间交互机制3.4、通道交互机制 4、实验4.1、对比实验4.2、组…...
Linux初学(十七)docker
一、docker 1.1 简介 容器技术 容器其实就是虚拟机,每个容器可以运行不同的系统【系统以Linux为主的】 为什么要使用docker? docker容器之间互相隔离,可以提高安全性通过使用docker可以做靶场 1.2 安装配置docker 方法一:yum安装…...

Python---Numpy线性代数
1.数组和矩阵操作: 创建数组和矩阵:np.array, np.matrix 基本的数组操作:形状修改、大小调整、转置等 import numpy as np# 创建一个 2x3 的数组 A np.array([[1, 2, 3], [4, 5, 6]]) print("数组 A:\n", A)# 将数组 A 转换为矩阵…...

react+ echarts 轮播饼图
react echarts 轮播饼图 图片示例 代码 import * as echarts from echarts; import { useEffect } from react; import styles from ./styles.scss;const Student (props) > {const { dataList, title } props;// 过滤数据const visionList [{ value: 1048, name: Se…...

政安晨:【深度学习神经网络基础】(三)—— 激活函数
目录 线性激活函数 阶跃激活函数 S型激活函数 双曲正切激活函数 修正线性单元 Softmax激活函数 偏置扮演什么角色? 政安晨的个人主页:政安晨 欢迎 👍点赞✍评论⭐收藏 收录专栏: 政安晨的机器学习笔记 希望政安晨的博客能够对您有所裨…...

使用tomcat里的API - servlet 写动态网页
一、创建一个新的Maven空项目 首次创建maven项目的时候,会自动从maven网站上下载一些依赖组件(这个过程需要保证网络稳定,否则后续打包一些操作会出现一些问题) ps:校园网可能会屏蔽一些网站,可能会导致maven的依赖…...

从0到1搭建文档库——sphinx + git + read the docs
sphinx git read the docs 目录 一、sphinx 1 sphinx的安装 2 本地构建文件框架 1)创建基本框架(生成index.rst ;conf.py) conf.py默认内容 index.rst默认内容 2)生成页面(Windows系统下…...
EasyExcel 校验后导入
引入pom <dependency><groupId>com.alibaba</groupId><artifactId>easyexcel</artifactId><version>3.3.3</version></dependency>触发校验类 import com.baomidou.mybatisplus.extension.api.R; import lombok.experimental…...

【星计划★C语言】c语言初相识:探索编程之路
🌈个人主页:聆风吟_ 🔥系列专栏:星计划★C语言、Linux实践室 🔖少年有梦不应止于心动,更要付诸行动。 文章目录 📋前言一. ⛳️第一个c语言程序二. ⛳️数据类型2.1 🔔数据单位2.2 &…...
搜维尔科技:借助 ARVR 的力量缩小现代制造业的技能差距
借助ARVR的力量缩小现代制造业的技能差距 搜维尔科技:Senseglove案例-扩展机器人技术及其VR应用...

数据结构之栈和队列
1.前言 大家好久不见,这段时间由于忙去了。就没有即使维护我的博客,先给大家赔个不是。 我们还是规矩不乱,先赞后看~ 今天讲的内容是数据结构中非常重要的一个部分:栈和队列。它在今后的学习中也会再次出现(c&#…...

centos安装使用elasticsearch
1.首先可以在 Elasticsearch 官网 Download Elasticsearch | Elastic 下载安装包 2. 在指定的位置(我的是/opt/zhong/)解压安装包 tar -zxvf elasticsearch-7.12.1-linux-x86_64.tar.gz 3.启动es-这种方式启动会将日志全部打印在当前页面,一旦使用 ctrlc退出就会导…...

4.7学习总结
java学习 一.Stream流 (一.)概念: Stream将要处理的元素集合看作一种流,在流的过程中,借助Stream API对流中的元素进行操作,比如:筛选、排序、聚合等。Stream流是对集合(Collection)对象功能的增强&…...

自定义gitlog格式
git log命令非常强大而好用,在复杂系统的版本管理中扮演着重要的角色,但默认的git log命令显示出的东西实在太丑,不好好打扮一下根本没法见人,打扮好了用alias命令拍个照片,就正式出道了! 在使用git查看lo…...
Redission--分布式锁
Redission的锁的好处 Redission分布式锁的底层是setnx和lua脚本(保证原子性) 1.是可重入锁。 2.Redisson 锁支持自动续期功能,这可以帮助我们合理控制分布式锁的有效时长,当业务逻辑执行时间超出了锁的过期时间,锁会自动续期,避免…...

非关系型数据库(缓存数据库)redis的集群
目录 一.群集模式——Cluster 1.原理 2.作用 3.特点 4.工作机制 哈希槽 哈希槽的分配 哈希槽可按照集群主机数平均分配(默认分配) 根据主机的性能以及功能自定义分配 redis集群的分片 分片 如何找到给定key的分片 优势 二. 搭建Redis群集…...
MySQL:表的约束(上)
文章目录 空属性默认值列描述zerofill主键 本篇总结的是MySQL中关于表的约束部分的内容 空属性 在进行表的创建时,会有两个值,null和not null,而数据库默认的字段基本都是空,但是在实际的开发过程中要保证字段不能为空ÿ…...

树莓派5使用体验
原文地址:树莓派5使用体验 - Pleasure的博客 下面是正文内容: 前言 好久没有关于教程方面的博文了,由于最近打算入门嵌入式系统,所以就去购入了树莓派5开发板 树莓派5是2023年10月23日正式发售的,过去的时间不算太远吧…...

代码随想录算法训练营第42天| 背包问题、416. 分割等和子集
01 背包 题目描述:有n件物品和一个最多能背重量为w 的背包。第i件物品的重量是weight[i],得到的价值是value[i] 。每件物品只能用一次,求解将哪些物品装入背包里物品价值总和最大。 二维dp数组01背包: 确定dp数组以及下标的含义 …...
k8s从入门到放弃之Ingress七层负载
k8s从入门到放弃之Ingress七层负载 在Kubernetes(简称K8s)中,Ingress是一个API对象,它允许你定义如何从集群外部访问集群内部的服务。Ingress可以提供负载均衡、SSL终结和基于名称的虚拟主机等功能。通过Ingress,你可…...

ESP32读取DHT11温湿度数据
芯片:ESP32 环境:Arduino 一、安装DHT11传感器库 红框的库,别安装错了 二、代码 注意,DATA口要连接在D15上 #include "DHT.h" // 包含DHT库#define DHTPIN 15 // 定义DHT11数据引脚连接到ESP32的GPIO15 #define D…...

【机器视觉】单目测距——运动结构恢复
ps:图是随便找的,为了凑个封面 前言 在前面对光流法进行进一步改进,希望将2D光流推广至3D场景流时,发现2D转3D过程中存在尺度歧义问题,需要补全摄像头拍摄图像中缺失的深度信息,否则解空间不收敛…...
2023赣州旅游投资集团
单选题 1.“不登高山,不知天之高也;不临深溪,不知地之厚也。”这句话说明_____。 A、人的意识具有创造性 B、人的认识是独立于实践之外的 C、实践在认识过程中具有决定作用 D、人的一切知识都是从直接经验中获得的 参考答案: C 本题解…...

html css js网页制作成品——HTML+CSS榴莲商城网页设计(4页)附源码
目录 一、👨🎓网站题目 二、✍️网站描述 三、📚网站介绍 四、🌐网站效果 五、🪓 代码实现 🧱HTML 六、🥇 如何让学习不再盲目 七、🎁更多干货 一、👨…...

c++第七天 继承与派生2
这一篇文章主要内容是 派生类构造函数与析构函数 在派生类中重写基类成员 以及多继承 第一部分:派生类构造函数与析构函数 当创建一个派生类对象时,基类成员是如何初始化的? 1.当派生类对象创建的时候,基类成员的初始化顺序 …...
嵌入式常见 CPU 架构
架构类型架构厂商芯片厂商典型芯片特点与应用场景PICRISC (8/16 位)MicrochipMicrochipPIC16F877A、PIC18F4550简化指令集,单周期执行;低功耗、CIP 独立外设;用于家电、小电机控制、安防面板等嵌入式场景8051CISC (8 位)Intel(原始…...
华为OD最新机试真题-数组组成的最小数字-OD统一考试(B卷)
题目描述 给定一个整型数组,请从该数组中选择3个元素 组成最小数字并输出 (如果数组长度小于3,则选择数组中所有元素来组成最小数字)。 输入描述 行用半角逗号分割的字符串记录的整型数组,0<数组长度<= 100,0<整数的取值范围<= 10000。 输出描述 由3个元素组成…...

热烈祝贺埃文科技正式加入可信数据空间发展联盟
2025年4月29日,在福州举办的第八届数字中国建设峰会“可信数据空间分论坛”上,可信数据空间发展联盟正式宣告成立。国家数据局党组书记、局长刘烈宏出席并致辞,强调该联盟是推进全国一体化数据市场建设的关键抓手。 郑州埃文科技有限公司&am…...
深入浅出JavaScript中的ArrayBuffer:二进制数据的“瑞士军刀”
深入浅出JavaScript中的ArrayBuffer:二进制数据的“瑞士军刀” 在JavaScript中,我们经常需要处理文本、数组、对象等数据类型。但当我们需要处理文件上传、图像处理、网络通信等场景时,单纯依赖字符串或数组就显得力不从心了。这时ÿ…...