hi,考虑在三,我决定还是写一下自己看到了解到的mysql,redis, mongodb集群的内容,以下基本是理论为主,具体的操作配置,可自行百度!
mysql 应该说是我们使用最为频繁的数据库,首先我们先介绍一下分库分表的概念:
百度到解释还可以话:数据库中的数据量不一定是可控的,在未进行分库分表的情况下,随着时间和业务的发展,库中的表会越来越多,表中的数据量也会越来越大,相应地,数据操作,增删改查的开销也会越来越大;另外,由于无法进行分布式式部署,而一台服务器的资源(CPU、磁盘、内存、IO等)是有限的,最终数据库所能承载的数据量、数据处理能力都将遭遇瓶颈。
说的很好了已经,但我觉得还是没有说清楚,我的理解是当单个表的数据量多到一定的地步的时候,这时候即便是我们的数据库有使用索引,索引占用的空间也会因为数据量的增加而增加,数据库就无法缓存全量的索引信息,那么就需要从磁盘上读取索引数据,就会影响到查询的性能了。其实分表很好理解就是将单一的表拆成多个,提高数据库的处理能力,为啥要进行分库,我看网上有说:全都存储在一个主库中,一旦主库发生故障,所有的模块都会受到影响,我的理解应该更多的是为了业务吧,根据业务的划分将表放在不用的库中,将业务耦合度比较高的表拆分到单独的库中,使得数据存放更加的规整和合理。 至于如何分库分表,网上给出的策略很详细了,数据库分库分表的方式有两种:一种是垂直拆分,另一种是水平拆分, 说我之前项目接触到的就是垂直拆分就是用户相关的表,有和内容相关的表,有和关系相关的表,用户相关的表分拆到用户库中,内容相关的表分拆到内容库中,关系相关的表分拆到关系库中,水平拆分,有按照用户id的后两位进行拆分的如user_info_list_XX,还有按照时间进行拆分的如按照年分进行表的拆分comment_list_XXXX。其他具体的一些方法可以自行百度。
以上我介绍的分库分表是在以下任何的架构中都可以使用:
单机架构
这个应该是最简单的架构了,应该是在学校学习mysql的时候用的,没有主从,读写都是连接该服务,当mysql的服务异常时,数据就获取不到了。
集群架构
mysql replication 主从这样的结构,能够实现数据的多点备份,实现数据的读写分离,数据读从从库,写入主库同步到从库中,但注意主库与从库之间会存在数据的延迟更新,并且没有故障自动转移和负载均衡,单一的主节点挂了,也无法对外提供写服务了。
实现原理:
1.master将改变记录到二进制日志(binary log)中(这些记录叫做二进制日志事件,binary log events)
2.slave将master的binary log events拷贝到它的中继日志(relay log);
3.slave重做中继日志中的事件,将改变反映它自己的数据。
![](https://i-blog.csdnimg.cn/blog_migrate/a0f99981f1f9c2ca3d9ff4a8d84aceae.png)
mysql主从复制需要三个线程,master(binlog dump thread)、slave(I/O thread 、SQL thread)。
master
(1)binlog dump线程:当主库中有数据更新时,那么主库就会根据按照设置的binlog格式,将此次更新的事件类型写入到主库的binlog文件中,此时主库会创建log dump线程通知slave有数据更新,当I/O线程请求日志内容时,会将此时的binlog名称和当前更新的位置同时传给slave的I/O线程。
slave
(2)I/O线程:该线程会连接到master,向log dump线程请求一份指定binlog文件位置的副本,并将请求回来的binlog存到本地的relay log中,relay log和binlog日志一样也是记录了数据更新的事件,它也是按照递增后缀名的方式,产生多个relay log( host_name-relay-bin.000001)文件,slave会使用一个index文件( host_name-relay-bin.index)来追踪当前正在使用的relay log文件。
(3)SQL线程:该线程检测到relay log有更新后,会读取并在本地做redo操作,将发生在主库的事件在本地重新执行一遍,来保证主从数据同步。此外,如果一个relay log文件中的全部事件都执行完毕,那么SQL线程会自动将该relay log 文件删除掉。
MySQL Fabirc
,是
mysql
官方提供的。这是在
MySQL Replication
的基础上,
增加了故障检测与转移,自动数据分片功能
。不过依旧是一主多从的结构,MySQL Fabirc
只有一个主节点,区别是当该主节点挂了以后,会从从节点中选择一个来当主节点。
其优势:
1. mysql
官方提供的工具,无需第三方插件。
2.
数据被删除,可以从
binlog
日志中恢复。
3.
主节点挂了以后,能够自动从从节点中选择一个来当主节点,不影响持续对外提供写服
务。
其劣势:
1.
从库要从
binlog
获取数据并重放,这肯定与主库写入数据存在时间延迟,因此从库的数
据总是要滞后主库。
2.
对主库与从库之间的网络延迟要求较高,若网络延迟太高,将加重上述的滞后,造成最
终数据的不一致。
3. 2014
年
5
月推出的产品,数据库资历较浅,应用案例不多,网上各种资料相对较少。
4.
事务及查询只支持在同一个分片内,事务中更新的数据不能跨分片,查询语句返回的数
据也不能跨分片。
5.
节点故障恢复
30
秒或更长(采用
InnoDB
存储引擎的都这样)。
MySQL
集群(
MySQL Cluster
)也是
mysql
官方提供的。
MySQL Cluster
是多主多从结构的
就各个集群方案来说,其优势为:
1. mysql
官方提供的工具,无需第三方插件。
2.
高可用性优秀,
99.999%
的可用性,可以自动切分数据,能跨节点冗余数据(其数据集并不是存储某个特定的 MySQL
实例上,而是被分布在多个
Data Nodes
中,即一个
table
的数据可能被分散在多个物理节点上,任何数据都会在多个 Data Nodes
上冗余备份。任何一个数据变更操作,都将在一组 Data Nodes
上同步,以保证数据的一致性)。
3.
可伸缩性优秀,能自动切分数据,方便数据库的水平拓展。
4.
负载均衡优秀,可同时用于读操作、写操作都都密集的应用,也可以使用
SQL
和
NOSQL接口访问数据。
5.
多个主节点,没有单点故障的问题,节点故障恢复通常小于
1
秒。
其劣势为:
1.
架构模式和原理很复杂。
2.
只能使用存储引擎
NDB
,与平常使用的
InnoDB
有很多明显的差距。比如在事务(其事务隔离级别只支持 Read Committed
,即一个事务在提交前,查询不到在事务内所做的修改),外键(虽然最新的 NDB
存储引擎已经支持外键,但性能有问题,因为外键所关联的记录可能在别的分片节点),表限制上的不同,可能会导致日常开发出现意外。
3.
作为分布式的数据库系统,各个节点之间存在大量的数据通讯,比如所有访问都是需要经过超过一个节点(至少有一个 SQL Node
和一个
NDB Node
)才能完成,因此对节点之间的内部互联网络带宽要求高。
4. Data Node
数据会被尽量放在内存中,对内存要求大,而且重启的时候,数据节点将数据 load
到内存需要很长时间。
MMM
(
Master Replication Manager for MySQL
)是双主多从结构,
MMM
是在
MySQL Replication的基础上,对其进行优化。这是 Google
的开源项目,使用
Perl
语言来对
MySQL Replication做扩展,提供一套支持双主故障切换和双主日常管理的脚本程序,主要用来监控 mysql
主主复制并做失败转移。
注意:这里的双主节点,虽然叫做双主复制,但是业务上同一时刻只允许对一个主进行写入,另一台备选主上提供部分读服务,以加速在主主切换时刻备选主的预热。就各个集群方案来说,其优势为:
1.
自动的主主
Failover
切换,一般
3s
以内切换备机。
2.
多个从节点读的负载均衡。
其劣势为:
1.
无法完全保证数据的一致性。如主
1
挂了,
MMM monitor
已经切换到主
2
上来了,而若此时双主复制中,主 2
数据落后于主
1
(即还未完全复制完毕),那么此时的主
2
已经成为主节点,对外提供写服务,从而导致数据不一。
2.
由于是使用虚拟
IP
浮动技术,类似
Keepalived
,故
RIP
(真实
IP
)要和
VIP
(虚拟
IP
)在同一网段。如果是在不同网段也可以,需要用到虚拟路由技术。但是绝对要在同一个 IDC机房,不可跨 IDC
机房组建集群。
MHA
(
Master High Availability
)是多主多从结构,
MHA
是在
MySQL Replication
的基础上,对其进行优化。这是日本 DeNA
公司的
youshimaton
开发,主要提供更多的主节点,但是缺少VIP(虚拟
IP
),需要配合
keepalived
等一起使用。要搭建 MHA
,要求一个复制集群中必须最少有三台数据库服务器,一主二从,即一台充当master,一台充当备用
master
,另外一台充当从库。
就各个集群方案来说,其优势为:
1.
可以进行故障的自动检测和转移
2.
具备自动数据补偿能力,在主库异常崩溃时能够最大程度的保证数据的一致性。
其劣势为:
1. MHA
架构实现读写分离,最佳实践是在应用开发设计时提前规划读写分离事宜,在使用时设置两个连接池,即读连接池与写连接池,也可以选择折中方案即引入 SQL Proxy
。但无论如何都需要改动代码;
2.
关于读负载均衡可以使用
F5
、
LVS
、
HAPROXY
或者
SQL Proxy
等工具,只要能实现负载均衡、故障检查及备升级为主后的读写剥离功能即可,建议使用 LVS
Galera Cluster
是由
Codership
开发的
MySQL
多主结构集群,这些主节点互为其它节点的从节点。不同于 MySQL
原生的主从异步复制,
Galera
采用的是多主同步复制,并针对同步复制过程中,会大概率出现的事务冲突和死锁进行优化,就是复制不基于官方 binlog
而是
Galera复制插件,重写了 wsrep api。异步复制中,主库将数据更新传播给从库后立即提交事务,而不论从库是否成功读取或重放数据变化。这种情况下,在主库事务提交后的短时间内,主从库数据并不一致。同步复制时,主库的单个更新事务需要在所有从库上同步 更新。换句话说,当主库提交事务时,集群中所有节点的数据保持一致。对于读操作,从每个节点读取到的数据都是相同的。对于写操作,当数据写入某一节点后,集群会将其同步到其它节点。
就各个集群方案来说,其优势为:
1.
多主多活下,可对任一节点进行读写操作,就算某个节点挂了,也不影响其它的节点的读写,都不需要做故障切换操作,也不会中断整个集群对外提供的服务。
2.
拓展性优秀,新增节点会自动拉取在线节点的数据(当有新节点加入时,集群会选择出一个 Donor Node
为新节点提供数据),最终集群所有节点数据一致,而不需要手动备份恢复。
其劣势为:
1.
能做到数据的强一致性,毫无疑问,也是以牺牲性能为代价