mysql主从复制与读写分离!(代码片段)

龙少。 龙少。     2022-12-08     401

关键词:

一.前言

在企业应用中,成熟的业务通常数据量都比较大

单台MySQL在安全性、高可用性和高并发方面都无法满足实际的需求

配置多台主从数据库服务器以实现读写分离。

二.主从复制原理

1.mysql的复制类型

(1)STATEMENT(基于SQL语句):

每一条涉及到被修改的sql 都会记录在binlog中

缺点:日志量过大,如sleep()函数,last_insert_id()>,以及user-defined fuctions(udf)、主从复制等架构记录日志时会出现问题

(2)ROW(基于行)

只记录变动的记录,不记录sql的上下文环境

缺点:如果遇到update…set…where true 那么binlog的数据量会越来越大

(3)MIXED 推荐使用

一般的语句使用statement,函数使用ROW方式存储

2.主从复制的过程详解

(1)核心点

2个日志,3个线程
maser里面是二进制日志bin_log,dump线程

slave里面是中继日志relay_log。i/o线程和sql线程

(2)详细复制过程

① master上的dump线程会监听二进制日志bin_log的更新内容’,如果有更新会通知slave的i/o线程

② slave上的i/o线程会申请更新同步二进制的更新内容

③ dump线程会把日志的更新同步内容给slave,slave的i/o线程会把更新日志内容写入自己的中继日志

④ slave的sql线程会把日志中的更新语句同步执行到数据库内,达到会master数据库内容趋近一致

三.主从复制的策略

1.全同步

master请求服务时,等待slave全部同步之后才会回应client端

2.半同步

master请求服务时,只要任意一个slave同步

3.异步

master请求服务时,只要master同步即回应请求,不管slave的状态;默认的状态

因为主从复制的默认策略是异步,导致的结果就是主从二进制日志和中继日志的保存内存会越来越大

四.搭建主从复制

1.搭建准备

3台linux,centos7版本,一台做mysql主服务器,2台做mysql从服务器。关闭防火墙及核心防护
master:192.168.206.88
slave1:192.168.206.188
slave2:192.168.206.177

2.安装mysql服务器

3台主机同时手工编译安装mysql数据库,这里安装的都是5.7版本。

3.主从服务器时间同步

(1)master配置

① 安装ntp,修改配置文件

[root@master ~]# yum -y install ntp 

[root@master ~]# ntpdate ntp.aliyun.com
20 Jul 15:08:10 ntpdate[1651]: adjust time server 203.107.6.88 offset 0.003463 sec

[root@master ~]# vim /etc/ntp.conf

server 127.127.1.0				#设置本机为时间同步源
fudge 127.127.1.0 stratum 10	#设置本机的时间层级为10级,是向其他服务器提供时间同步源的意思,不可设置为0[root@master ~]# crontab -e
no crontab for root - using an empty one
crontab: installing new crontab
[root@master ~]# crontab -l
*/10 * * * *  /usr/sbin/ntpdate 192.168.206.88

② 重启ntp

[root@master ~]# systemctl start ntpd

(2)2台slave配置

[root@slave1 ~]# yum -y install ntp 

[root@slave1 ~]# ntpdate ntp.aliyun.com
20 Jul 15:08:10 ntpdate[1651]: adjust time server 203.107.6.88 offset 0.003463 sec

[root@slave2 ~]# yum -y install ntp 

[root@slave2 ~]# ntpdate ntp.aliyun.com
20 Jul 15:08:10 ntpdate[1651]: adjust time server 203.107.6.88 offset 0.003463 sec

[root@slave1 ~]# crontab -e
crontab: installing new crontab
[root@slave1 ~]# crontab -l
*/10 * * * * /usr/sbin/ntpdate 192.168.206.88
[root@slave1 ~]# systemctl start ntpd
[root@slave1 ~]# ntpdate 192.168.206.88
20 Jul 17:28:24,从ntpdate[16023]: the NTP socket is in use, exiting


[root@slave2 ~]#  crontab -e
no crontab for root - using an empty one
crontab: installing new crontab
[root@slave2 ~]#  crontab -l
*/10 * * * * /usr/sbin/ntpdate 192.168.206.88
[root@slave2 ~]# systemctl start ntpd
[root@slave2 ~]# ntpdate 192.168.206.88
20 Jul 17:28:47 ntpdate[44686]: the NTP socket is in use, exiting

4.主从分别开启各自日志文件

(1)master主要配置

启动二进制文件,从服务器

[root@master ~]# vim /etc/my.cnf

server-id = 11
log_bin=master-bin
log_slave_updates=true

[root@master ~]# systemctl restart mysqld

(2)slave1配置

[root@slave1 ~]# vim /etc/my.cnf		#给slave1开启中继日志

[mysqld]
server-id = 22
relay-log=relay-log-bin					#从主服务器上同步日志文件记录到本地
relay-log-index=slave-relay-bin.index	#定义中继日志的位置和名称

[root@slave1 ~]# systemctl restart mysqld


(3)slave2配置

[root@slave2 ~]# vim /etc/my.cnf		#给slave2开启中继日志

[mysqld]
server-id = 33
relay-log=relay-log-bin					#从主服务器上同步日志文件记录到本地
relay-log-index=slave-relay-bin.index	#定义中继日志的位置和名称

[root@slave2 ~]# systemctl restart mysqld

5.配置规则

(1)master设置

给从服务器提权grant;用于主从对接

[root@master ~]# mysql -uroot -p			#登录数据库

mysql> grant replication slave on *.* to 'myslave'@'192.168.206.%' identified by '123456';
Query OK, 0 rows affected, 1 warning (0.00 sec)

mysql> flush privileges;
Query OK, 0 rows affected (0.00 sec)

mysql> show master status;
+-------------------+----------+--------------+------------------+-------------------+
| File              | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |
+-------------------+----------+--------------+------------------+-------------------+
| master-bin.000003 |     1053 |              |                  |                   |
+-------------------+----------+--------------+------------------+-------------------+
1 row in set (0.00 sec)


mysql> quit
Bye

[root@master ~]# cd /usr/local/mysql/data

[root@master data]# ls
auto.cnf        ib_logfile0  master-bin.000001  master-bin.index    sys
ib_buffer_pool  ib_logfile1  master-bin.000002  mysql
ibdata1         ibtmp1       master-bin.000003  performance_schema

(2)slave1设置

[root@slave1 ~]# mysql -uroot -pqwer1234			#登录数据库

mysql> change master to master_host='192.168.206.88',master_user='myslave',master_password='123456',master_log_file='master-bin.000003',master_log_pos=1053;					#给从服务器提权,允许使用slave的身份复制msater所有数据库的所有表,并制定密码为123456
Query OK, 0 rows affected, 2 warnings (0.01 sec)

mysql> start slave;
Query OK, 0 rows affected (0.00 sec)

mysql> show slave status\\G							#查看从服务器状态

在这里插入图片描述

(3)slave2配置

[root@slave2 ~]# mysql -uroot -pqwer1234			#登录数据库

mysql> change master to master_host='192.168.206.88',master_user='myslave',master_password='123456',master_log_file='master-bin.000003',master_log_pos=1053;					#给从服务器提权,允许使用slave的身份复制msater所有数据库的所有表,并制定密码为123456
Query OK, 0 rows affected, 2 warnings (0.01 sec)

mysql> start slave;
Query OK, 0 rows affected (0.00 sec)

mysql> show slave status\\G							#查看从服务器状态

在这里插入图片描述

6.测试是否同步

(1)master创建一个库
在这里插入图片描述

(2)slave1上查看是否同步
在这里插入图片描述

(2)slave2上查看是否同步

在这里插入图片描述

五.读写分离

1.原理

读写分离就是只在主服务器上写,只在从服务器上读

基本的原理是让主数据库处理事务性查询,

而从数据库处理select查询。数据库复制被用来把主数据库上事务性查询导致的变更同步到集群中的从数据库

2.为何要读写分离

因为数据库的“写”(写10000条数据可能要3分钟)操作是比较耗时的。

但是数据库的“读”(读10000条数据可能只要5秒钟)

所以读写分离,解决的是,数据库的写入,影响了查询的效率

3.读写分离的好处

数据库不一定要读写分离,如果程序使用数据库较多时,而更新少,查询多的情况下会考虑使用。

利用数据库主从同步,再通过读写分离可以分担数据库压力,提高性能

4.实现方式方案

常见的MySQL读写分离分为以下两种:

(1)基于程序代码内部实现

在代码中根据select、insert 进行路由分类,这类方法也是目前生产环境应用最广泛的。

优点是性能较好,因为在程序代码中实现,不需要增加额外的设备为硬件开支;

缺点是需要开发人员来实现,运维人员无从下手。

但是并不是所有的应用都适合在程序代码中实现读写分离,像一些大型复杂的Java应用,如果在程序代码中实现读写分离对代码改动就较大。

(2)基于中间代理层实现

代理一般位于客户端和服务器之间,代理服务器接到客户端请求后通过判断后转发到后端数据库;

有以下代表性程序:
① MySQL-Proxy:MySQL-Proxy 为MySQL开源项目,通过其自带的lua脚本(脚本语言)进 行SQL判断。

② Atlas:由奇虎360的Web平台部基础架构团队开发维护的一个基于MySQL协议的数据中间层项目。它是在mysql-proxy0.8.2版本的基础上,对其进行了优化,增加了一些新的功能特性。360内部使用Atlas运行的mysql业务,每天承载的读写请求数达几十亿条。支持事物以及存储过程。

③ Amoeba:由陈思儒开发,作者曾就职于阿里巴巴。该程序由Java语言进行开发,阿里巴巴将其用于生产环境。但是它不支持事务和存储过程。

5.Amoeba介绍

Amoeba: 是一 个以MySQL为底层数据存储,并对应提供MySQL协议接口的proxy(代理),外号变形虫

读取请求发送给从服务器是,采用轮询调度算法

amoeba使用的java语言编写,配置文件为xml

amoeba主要负责对外的一个代理IP
访问这个IP时,发送的请求为“写"请求,则会转给主服务器
当发送的请求为“读"时,会通过调度转发给从服务器,使用轮询算法,轮流分配给两台从服务器

amoeba可以视为调度器,如果主服务器挂掉(单点故障),则会有MHA解决这个问题

六.搭建读写分离

读写分离的搭建是建立在主从复制的基础上的。

1.实验准备

5台linux,1台mysql数据库master,2台mysql数据库slave,1台amoeba,1台client端
mysql-master:192.168.206.88
mysql-slave1:192.168.206.188
mysql-slave2:192.168.206.177
amoeba:192.168.206.99
client端:192.168.206.

3台mysql做主从复制

2.安装ameoba

安装java环境,安装jdk(因为amoeba是基于jdk1.5开发的,所以官方推荐使用jkd1.5/jdk1.6,高版本不建议使用)

[root@ameoba ~]# cd /opt
[root@ameoba opt]# ls
anaconda-ks.cfg  rh
[root@ameoba opt]# ls											#本地上传执行文件和安装包
amoeba-mysql-binary-2.2.0.tar.gz  anaconda-ks.cfg  jdk-6u14-linux-x64.bin  rh
[root@ameoba opt]# cp jdk-6u14-linux-x64.bin /usr/local/
[root@ameoba opt]# cd /usr/local/
[root@ameoba local]# chmod +x jdk-6u14-linux-x64.bin			#给执行权限
[root@ameoba local]# ./jdk-6u14-linux-x64.bin					#执行

		#yes 回车

[root@ameoba local]# mv jdk1.6.0_14/ /usr/local/jdk1.6
[root@ameoba local]# vim /etc/profile							#添加变量
		

在这里插入图片描述

[root@ameoba local]# source /etc/profile						#刷新生效
[root@ameoba local]# java -version								#查看java版本
java version "1.6.0_14"
Java(TM) SE Runtime Environment (build 1.6.0_14-b08)
Java HotSpot(TM) 64-Bit Server VM (build 14.0-b16, mixed mode)


[root@ameoba local]# mkdir /usr/local/amoeba					#创建目录
[root@ameoba local]# tar zxvf /opt/amoeba-mysql-binary-2.2.0.tar.gz -C /usr/local/amoeba/
																#解压到创建的目录

[root@ameoba local]# chmod -R 755 /usr/local/amoeba/ 			#递归给权限
[root@ameoba local]# /usr/local/amoeba/bin/amoeba				#服务启动
amoeba start|stop

3.配置amoeba读写分离,2个slave读负载均衡,给数据库权限

在master、slave1、slave2的mysql上开放权限给amoeba

mysql> grant all on *.* to test @'192.168.206.%' identified by '123456';
Query OK, 0 rows affected, 1 warning (0.00 sec)

4.再配置amoeba

(1)修改主配置文件

[root@ameoba local]# cd /usr/local/amoeba/conf/
[root@ameoba conf]# ls
access_list.conf  dbserver.dtd   functionMap.xml  rule.dtd
amoeba.dtd        dbServers.xml  log4j.dtd        ruleFunctionMap.xml
amoeba.xml        function.dtd   log4j.xml        rule.xml
[root@ameoba conf]# cp amoeba.xml amoeba.xml.bak
[root@ameoba conf]# vim amoeba.xml

在这里插入图片描述
在这里插入图片描述

(2)修改数据库配置文件

[root@ameoba conf]# cp dbServers.xml dbServers.xml.bak
[root@ameoba conf]# vim dbServers.xml

在这里插入图片描述
在这里插入图片描述
紧接复制52-57行,粘贴,添加第二台服务器名
在这里插入图片描述
在这里插入图片描述

这时复制会话另开一个页面查看一下配置文件 (因为amoeba需要一直开启才能查询到端口)
在这里插入图片描述

5.开启amoeba


[root@ameoba conf]# /usr/local/amoeba/bin/amoeba start
log4j:WARN log4j config load completed from file:/usr/local/amoeba/conf/log4j.xml
2021-07-21 03:51:56,755 INFO  context.MysqlRuntimeContext - Amoeba for Mysql current versoin=5.1.45-mysql-amoeba-proxy-2.2.0
log4j:WARN ip access config load completed from file:/usr/local/amoeba/conf/access_list.conf
2021-07-21 03:52:07,034 INFO  net.ServerableConnectionManager - Amoeba for Mysql listening on 0.0.0.0/0.0.0.0:8066.
2021-07-21 03:52:07,038 INFO  net.ServerableConnectionManager - Amoeba Monitor Server listening on /127.0.0.1:6475.


[root@ameoba conf]# netstat -antp | grep java
tcp6       0      0 127.0.0.1:6475          :::*                    LISTEN      35067/java        
tcp6       0      0 :::8066                 :::*                    LISTEN      35067/java        
tcp6       0      0 192.168.206.99:39278    192.168.206.88:3306     ESTABLISHED 35067/java        
tcp6       0      0 192.168.206.99:39282    192.168.206.88:3306     ESTABLISHED 35067/java        
tcp6       0      0 192.168.206.99:46678    192.168.206.177:3306    ESTABLISHED 35067/java        
[root@ameoba conf]# netstat -antp | grep 8066
tcp6       0      0 :::8066                 :::*                    LISTEN      35067/java 

6.测试验证

(1)验证amoeba能否关联后端mysql

client端远程访问amoeba的地址,并进入数据库创建新的数据库,验证master和slaves是否同步
client端进入数据库创建表gg,发现master+slave1+slave2已同步创建数据表gg

① 客户端远程登录创建表gg

[root@client ~]# mysql -uamoeba -p123123 -h 192.168.206.99 -P 8066
mysql: [Warning] Using a password on the command line interface can be insecure.
Welcome to the MySQL monitor.  Commands end with ; or \\g.
Your MySQL connection id is 1342544436
Server version: 5.1.45-mysql-amoeba-proxy-2.2.0

Copyright (c) 2000, 2017, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\\h' for help. Type '\\c' to clear the current input statement.

mysql> create database zzz;
Query OK, 1 row affected (0.02 sec)

mysql> use zzz;
No connection. Trying to reconnect...
Connection id:    1342544436
Current database: *** NONE ***

Database changed
mysql> create table gg(id int);
Query OK, 0 rows affected (0.03 sec)

mysql> show tables;
+---------------+
| Tables_in_zzz |
+---------------+
| gg            |
+---------------+
1 row in set (0.00 sec)

② master查看
在这里插入图片描述

③ slave查看
在这里插入图片描述

(2)验证写

测试mysql的读写分离,2台从服务器关闭主

mysql主从复制与读写分离!(代码片段)

mysql主从复制与读写分离一.前言二.主从复制原理1.mysql的复制类型(1)STATEMENT(基于SQL语句):(2)ROW(基于行)(3)MIXED推荐使用2.主从复制的过程详解(1)核心点(2)详细复制过程... 查看详情

mysql主从复制及读写分离实际部署与验证(代码片段)

MySQL主从复制及读写分离前言:一、主从复制1.原理:2.准备来做主从复制和读写分离的服务器如下:3.主从复制具体步骤1.关闭所有服务器的防火墙2.Mysql主从服务器都进行时间同步3.主从服务器mysql配置4.从服务器的mysq... 查看详情

mysql主从复制与读写分离的理论+实操(配有详细图释)(代码片段)

主从复制与读写分离一、为什么需要主从复制与读写分离?二、主从复制原理2.1MySQL支持的复制类型2.2MySQL主从复制工作过程三、读写分离原理3.1MySQL读写分离工作过程四、搭建主从复制与读写分离4.1实验环境4.2时间同步(... 查看详情

mysql主从同步与读写分离(代码片段)

MySQL主从同步MySQLAB复制1.对指定库的异地同步。2.MySQL主-->从复制架构的实现。3.MySQL服务器的只读控制。主从:单向复制时,建议将从库设置为只读。主从复制的原理:Master,记录数据更改操作。-启动binlog日志-设置binlog日志格... 查看详情

mysql主从同步与读写分离(代码片段)

MySQL主从同步MySQLAB复制1.对指定库的异地同步。2.MySQL主-->从复制架构的实现。3.MySQL服务器的只读控制。主从:单向复制时,建议将从库设置为只读。主从复制的原理:Master,记录数据更改操作。-启动binlog日志-设置binlog日志格... 查看详情

mysql主从同步与读写分离(代码片段)

MySQL主从同步MySQLAB复制1.对指定库的异地同步。2.MySQL主-->从复制架构的实现。3.MySQL服务器的只读控制。主从:单向复制时,建议将从库设置为只读。主从复制的原理:Master,记录数据更改操作。-启动binlog日志-设置binlog日志格... 查看详情

mysql主从复制以及读写分离(❤❤❤❤含理论和实验❤❤❤❤大家中秋快乐!㊗)(代码片段)

文章目录一、MySQL主从复制的理论部分1.1、主从复制与读写分离的概述1.2、mysql支持的复制类型1.3、主从复制的工作过程(主写从复制❤❤❤❤)1.4、MySOL主从复制延迟的原因二、MySQL读写分离的理论部分2.1、MySQL读写分离... 查看详情

mysql主从复制以及读写分离(❤❤❤❤含理论和实验❤❤❤❤大家中秋快乐!㊗)(代码片段)

文章目录一、MySQL主从复制的理论部分1.1、主从复制与读写分离的概述1.2、mysql支持的复制类型1.3、主从复制的工作过程(主写从复制❤❤❤❤)1.4、MySOL主从复制延迟的原因二、MySQL读写分离的理论部分2.1、MySQL读写分离... 查看详情

主从复制和读写分离(代码片段)

主从复制和读写分离一.概述二.主从复制原理1.mysql复制类型2.mysql主从复制的工作过程三.Mysql读写分离1.读写分离原理2.读写分离方案3.读写分离存在的意义4.什么时候要读写分离四.Mysql主从复制和读写分离实验案例拓扑图:思... 查看详情

mysql主从复制与读写分离(代码片段)

一、主从复制1.MySQL支持的复制类型基于语句的复制在主服务器上执行的SQL语句,在从服务器上执行同样的语句基于行的复制把改变的内容复制过去,而不是把命令在从服务器上执行一遍混合类型的复制默认采用基于语句... 查看详情

mysql主从复制及读写分离实际部署与验证(代码片段)

MySQL主从复制及读写分离前言:一、主从复制1.原理:2.准备来做主从复制和读写分离的服务器如下:3.主从复制具体步骤1.关闭所有服务器的防火墙2.Mysql主从服务器都进行时间同步3.主从服务器mysql配置4.从服务器的mysq... 查看详情

mysql数据库--主从复制读写分离(代码片段)

文章目录一、主从复制1、原理2、二进制日志的保存方式3、主从复制策略4、搭建MySQL主从复制二、读写分离1、原理2、读写分离3、读写分离的好处4、实现方式4.1、Amoeba简介五、搭建MySQL读写分离1、实验准备2、amoeba(192.168.35.30)安... 查看详情

mysql数据库的主从复制和读写分离!(代码片段)

这里写目录标题一、主从复制1.1MySQL支持的复制类型1.2MySQL主从复制核心原理搭建MySQL的主从复制读写分离读写分离方法需要读写分离的原因及适用场景搭建读写分离一、主从复制在实际生产环境中,如果对数据库的读写都在... 查看详情

mysql数据库的主从复制和读写分离!(代码片段)

这里写目录标题一、主从复制1.1MySQL支持的复制类型1.2MySQL主从复制核心原理搭建MySQL的主从复制读写分离读写分离方法需要读写分离的原因及适用场景搭建读写分离一、主从复制在实际生产环境中,如果对数据库的读写都在... 查看详情

主从复制和读写分离(代码片段)

主从复制和读写分离一.概述二.主从复制原理1.mysql复制类型2.mysql主从复制的工作过程三.Mysql读写分离1.读写分离原理2.读写分离方案3.读写分离存在的意义4.什么时候要读写分离四.Mysql主从复制和读写分离实验案例拓扑图:思... 查看详情

mysql数据库mysql主从复制和sharding-jdbc实现读写分离(代码片段)

文章目录1.MySQL主从复制1.1MySQL主从复制介绍1.2MySQL主从复制配置2.数据库读写分离2.1读写分离介绍2.2Sharding-JDBC2.2.1Sharding-JDBC介绍2.2.2Sharding-JDBC实现读写分离1.MySQL主从复制1.1MySQL主从复制介绍MySQL主从复制是一个异步的复制过程ÿ... 查看详情

mysql数据库mysql主从复制和sharding-jdbc实现读写分离(代码片段)

文章目录1.MySQL主从复制1.1MySQL主从复制介绍1.2MySQL主从复制配置2.数据库读写分离2.1读写分离介绍2.2Sharding-JDBC2.2.1Sharding-JDBC介绍2.2.2Sharding-JDBC实现读写分离1.MySQL主从复制1.1MySQL主从复制介绍MySQL主从复制是一个异步的复制过程ÿ... 查看详情

mysql主从复制与读写分离

文章转自:MySQL主从复制与读写分离MySQL主从复制(Master-Slave)与读写分离(MySQL-Proxy)实践Mysql作为目前世界上使用最广泛的免费数据库,相信所有从事系统运维的工程师都一定接触过。但在实际的生产环境中,由单台Mysql作为独立的... 查看详情