在企业应用中,成熟的业务通常数据量都比较庞大,如果对 MySQL 数据库的读和写都在一台数据库服务器上操作,无论是在安全性、高可用性,还是高并发等各个方面都是不能满足实际需求的。因此,一般来说都是通过主从复制(Master-Slave)的方式来同步数据,再通过读写分离来提升数据库的并发负载能力这样的方案进行部署与实施。
一、主从复制1. 原理MySQL 的主从复制和 MySQL 的读写分离两者有着紧密联系,首先要部署主从复制,只有主从复制完成了,才能在此基础上进行数据的读写分离。
- 主从复制的核心:2个日志、3个线程
master 线程:bin log 二进制日志、dump 线程
master 上的 dump 线程会监控 bin log 二进制日志的更新,若有更新会通知 slave的 I/O 线程
slave:relay log 中继日志、I/O 线程、SQL 线程
线程1:
slave上的 I/O 线程会向 master 申请同步 bin log 二进制日志的更新内容,slave的 I/O 线程把更新内容写入自己的中继日志
线程2:
slave 的 SQL 线程把日志中的更新语句同步执行到内容,以达到和 master 数据库趋于一致
2. 支持的复制类型STATEMENT:基于语句的复制,在主服务器上执行的 SQL 语句,在从服务器上执行同样的语句;MySQL 默认采用基于语句的复制,效率比较高
ROW:基于行的复制,把改变的内容复制过去,而不是把命令在从服务器上执行一遍
MIXED:混合类型的复制,默认采用基于语句的复制,一旦发现基于语句无法精确复制时,就会采用基于行的复制
3. 复制的工作过程① 在每个事务更新数据完成之前,Master 都会在二进制日志记录这些改变;写入二进制日志完成后,Master 通知存储引擎提交事务;
② Slave 将 Master 的 Binary log 复制到其中继日志
首先,Slave 开始一个工作线程——I/O 线程,I/O 线程在 Master 上打开一个普通的连接,然后开始 Binlog dump process;Binlog dump process 从 Master 的二进制日志中读取时间,如果已经跟上 Master,它会睡眠并等待Master 产生新的时间;I/O 线程将做这些事件写入中继日志;
③ SQL slave thread(SQL 从线程)处理该过程的最后一步
SQL 线程从中继日志读取事件,并重放其中的事件而更新 Slave 的数据,使其与 Master 中的数据一致;只要该线程与 I/O 线程保持一致,中继日志通常会位于 OS 的缓存中,所以中继日志的开销很小;
④ 复制过程有一个很重要的限制,即复制在 Slave 上是串行化的,也就是说 Master 上的并行更新操作不能在 Slave 上并行操作。
4. MySQL主从复制延迟(1)master 服务器高并发,形成大量事务
(2)网络延迟
(3)主从硬件设备导致:cpu主频、内存IO、硬盘io
(4)本来就不是同步复制、而是异步复制
(5)从库优化 Mysql 参数,比如增大 innodb_buffer_pool_size,让更多操作在 Mysql 内存中完成,减少磁盘操作。
(6)从库使用高性能主机,包括 cpu 强悍、内存加大。避免使用虚拟云主机,使用物理主机,这样提升了I/O方面性能。
(7)从库使用SSD磁盘
(8)网络优化,避免跨机房实现同步
二、读写分离1. 原理- 读写分离就是只在主服务器上写,只在从服务器上读
- 基本的原理是让主数据库处理事务性查询,而从数据库处理 select 查询。数据库复制被用来把主数据库上事务性查询导致的变更同步到集群中的从数据库
为什么要读写分离呢?
因为数据库写 10000 条数据可能要 3 分钟,操作比较耗时,但是数据库读 10000 条数据可能只要5秒钟,所以读写分离,解决的是,数据库的写入,影响了查询的效率。
读写分离的过程如下图所示
2. 读写分离作用- 数据库不一定要读写分离,如果程序使用数据库较多时,而更新少,查询多的情况下会考虑使用。
- 利用数据库主从同步,再通过读写分离可以分担数据库压力,提高性能
- 读写分离分为以下两种∶
在代码中根据 select、insert,进行路由分类,这类方法也是目前生产环境应用最广泛的。
优点是性能较好,因为在程序代码中实现,不需要增加额外的设备为硬件开支; 缺点是需要开发人员来实现,运维人员无从下手。
但是并不是所有的应用都适合在程序代码中实现读写分离,像一些大型复杂的 Java 应用,如果在程序代码中实现读写分离对代码改动就较大。
3.2 基于中间代理层实现代理一般位于客户端和服务器之间, 代理服务器接到客户端请求后通过判断后转发到后端数据库, 有以下代表性程序:(1) MySQL-Proxy :MySQL-Proxy 为 MySOL开源项目, 通过其自带的 lua 脚本进行SOL 判断。
(2) Atlas :是由奇虎360的Web平台部基础架构团队开发维护的一个基于MySQL协议的数据中间层项目。它是在mysql-proxy0.8.2版本的基础上,对其进行了优化, 增加了一些新的功能特性。360内部使用Atlas运行的mysql业务,每天承载的读写请求数达几十亿条。支持事物以 及存储过程。
(3) Amoeba :由陈思儒开发,作者曾就职于阿里巴巴。该程序由Jaya语言进行开发,阿里巴巴将其用于生产环境。但是它不支持事务和存储过程。
由于使用 MySQL Proxy 需要写大量的 Lua 脚本,这些 Lua 并不是现成的,而是需要自己去写。这对于并不熟悉 MySQL Proxy 内置变量和 MySQL Protocol 的人来说是非常困难的。
Amoeba是一个非常容易使用、可移植性非常强的软件。因此它在生产环境中被广泛应用于数据库的代理层。
三、MySQL 主从复制架构搭建1. 服务器配置主机名 | 操作系统 | IP地址 | 所需软件 |
Master | CentOS 7 | 192.168.10.14 | mysql-5.7 |
Amoeba | CentOS 7 | 192.168.10.13 | jdk1.6、Amoeba |
Slave1 | CentOS 7 | 192.168.10.16 | mysql-5.7 |
Slave2 | CentOS 7 | 192.168.10.19 | mysql-5.7 |
client端 | CentOS 7 | 192.168.10.26 | mysql5.7 |
修改主机名