谈谈数据库的高可用架构
前言
本篇文章讨论一下数据库高可用的相关架构。
1. 数据库的高可用
数据库的高可用从下面几点考虑
- 高可用
- 高性能
- 可拓展
- 一致性
1.1 水平切分
主要解决单数据库中数据量过多的问题。水平划分成多个库负载均衡。
1.1.1 如何划分数据
- 通过范围
- 时间或者主键id划分,缺点是各个库的压力不均
- 通过哈希 建议
- 存储查询时取模计算在那个库,缺点是当两个库拓展成三个库时麻烦,(数据需要迁移)
- 通过统一路由服务
- 业务与路由算法解耦
1.2 一主多从 读写分离
单个主数据库搭配多个从数据库来进行使用。主库负责写入,从库负责读取。同步主库和从库的数据。当水平切分遇到主从复制时,划分成的1库和2库分别进行读写分离。
1.2.1 遇到的问题
数据同步不一致 有一定时间差 (还未同步数据就去读取)
通常使用中间件或者强制读主的方式来解决中从数据不一致性问题
- 中间件
- 当某个key有写操作时,在不一致的时间窗口范围中关于这个key的读也路由到主库中去读。不再通过从库去读。
- 强制读主
- 也就是双主高可用的架构
单个主库也会成为单点,MHA可以在主库产生故障时进行切换,选举一个读库作为主库。一主在写多的场景下也会产生瓶颈,因而拓展主库也是某些场景需要的。
1.3 多主多从
单个写库还是不能保证写高可用,需要冗余写库。
1.3.1 多个写库写到那个库中?
- 通过多个写库不同的初始值,相同步长进行递增。
- 1写库的id为 0 2 4 8 ... 2写库的id为 1 3 5 7
- 通过业务层来生成唯一的id 保证数据不冲突
同时带来的问题也是数据需要同步的地方增多,数据延迟严重。
1.4 主备进行高可用
主备架构,只有主库提供读写服务,备库冗余作故障转移用
通过虚ip漂移,对业务层透明,不需要人工介入
优点是读写没有延时(写完就可以读),没有数据一致性问题。
不足的是不能通过加从库拓展读性能。资源利用率为50%,一台冗余主没有提供服务。但如果进行双主同时提供服务(负载均衡)可以解决这一点,但加了会有数据一致性问题如1.5中所说。
1.4.1 通过 Keepalived + MySQL 实现双主热备高可用方案
Keepalived 也就是通过虚拟ip,实现双主对外的统一接口,自动检查,失败切换机制,自动切换防止单点故障。
Keepalived基础是通过VRRP协议
- VRRP (Virtual Router Redundancy Protocol) 虚拟路由冗余协议。在VRRP中有两组重要的概念:VRRP路由器和虚拟路由器,主控路由器和备份路由器。
- VRRP路由器是指运行VRRP的路由器,是物理实体,虚拟路由器是指VRRP协议创建的,是逻辑概念。一组VRRP路由器协同工作,共同构成一台虚拟路由器。Vrrp中存在着一种选举机制,用以选出提供服务的路由即主控路由,其他的则成了备份路由。当主控路由失效后,备份路由中会重新选举出一个主控路由,来继续工作,来保障不间断服务。
1.5 双主架构 负载均衡
两个主库同时提供服务,负载均衡。
读写性能相对主备架构得到提升,资源利用率更高。
存在数据一致性问题,也可以水平拓展。但水平拓展会多一层数据同步,同步时间变长。
带来的问题是数据一致性问题以及主键冲突问题(可以通过分布式id解决)
1.6 从库中如何优化
- 为从库加入索引 索引可以不同。主库可以不使用索引,从库使用不同的索引(从库使用场景各不相同)。
- 增加从库
- 从库越多 同步也慢,同步慢 数据不一致窗口越大。
- 增加缓存
- 也会带来数据不一致性问题