| |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
-> 大数据 -> 数据库读写分离与分库分表 -> 正文阅读 |
|
[大数据]数据库读写分离与分库分表 |
3.1 读写分离(主要是为了数据库读能力的水平扩展)3.1.1 读写分离概念单台mysql实例情况下不能支持短时间内大量的对数据库的读操作,所以会将数据库配置成集群,一个master(主库)、多个slave(从库),一般主库负责写,从库负责读,主从之间的同步方式为binlog日志方式。binlog日志可以有Statement(记录修改数据的sql,缺点slave和master执行结果可能不同)、Row(记录每一行数据的修改,缺点日志量大)、Mixed(Statement和Row两种方式的混合)三种方式。 3.1.2 读写分离好处
3.1.3 读写分离局限性
slave宕机或下线:如果其中某个slave节点挂了/或者下线了,应该对其进行隔离,那么之后的读请求,应用将其转发到正常工作的slave节点上。 master宕机:需要进行主从切换,将其中某个slave提升为master,应用之后将写操作转到新的master节点上。 3.1.4 Zebra与读写分离zebra团队提供了GroupDataSource来完成读写分离功能,解决了上述所有问题,且对业务方透明。开发人员可以像操作单个库那样,去访问mysql数据库集群,底层细节完全由zebra屏蔽。
3.2 分库分表(主要是为了写能力的水平扩展,如果只是为了读,那么读写分离,多几台slave机器,也可以解决)3.2.1 分库分表概念一旦业务表中的数据量大了,从维护和性能角度来看,无论是任何的 CRUD 操作,对于数据库而言都是一件极其耗费资源的事情。即便设置了索引,仍然无法掩盖因为数据量过大从而导致的数据库性能下降的事实 ,这个时候就该对数据库进行水平分区 (sharding,即分库分表 ).水平分区从具体表现上来看可以分为:只分表、只分库、分库分表三种。 3.2.1 分库分表好处分库好处:降低单台机器的负载压力,提高读写性能。 分表好处:比如原来一张表4000w行数据,经过分表后每张表1000w数据,当执行插入操作时,维护索引的时间缩短,提升了写的效率;读时候可以同时从多张表中读,提升了读的效率。所以读写性能都得到了提升。 3.2.3 分库分表局限性3.2.3.1 增删查改的功能变得复杂 原来的insert语句如下: insert into user(id,name) values (1,”tianshouzhi”),(2,”huhuamin”), (3,”wanghanao”),(4,”luyang”); 经过分库分表后,需要将sql语句改为如下形式,并分别到每个库去执行: insert into user_1(id,name) values (1,”tianshouzhi”) insert into user_2(id,name) values (2,”huhuamin”) insert into user_3(id,name) values (3,”wanghanao”) insert into user_0(id,name) values (4,”luyang”) 具体的流程可以用下图描述: ? 解释如下:
3.2.3.2 分布式id问题的解决 分库分表后,不能再使用mysql的自增主键。因为在插入记录的时候,不同库生成的自增id可能会发生冲突,因此要有一个全局的id生成器。
分配一个64bit的long型id,分配如下: ? 41bit用作时间戳,精确到ms,10bit用于工作机器id(5bit是数据中心id,5bit是机器id),12bit用作序列号,也就是说某一个数据中心的一台机器在1ms时间内可以分配4096个id,序列号的生成可以采用Synchornized加锁的方式,也可以采用AtomicInteger(底层采用CAS)的方式。当在1ms内向某台机器申请多于4096个id时,机器可以推到下一ms生成。这64bit也可以根据自己需要设置不同bit的用途。 缺点: 时间回拨问题、机器id的分配回收问题、机器id的上限问题。这里不再详细阐述。(待补充)
? ? ? ? ? ? ? ? ? ? ? ?? 注: DX、YF等表示数据中心名称、leaf表示该数据中心的某台机器、数据表中的biz_tag表示业务标识,该业务的id要保证唯一,不同业务的id不需要保证、max_id表示该业务当前申请的最大id、step表示该业务每次申请的id数量。申请完成后,该step数量的id被数据中心的某台机器所持有,然后机器可以通过Synchornized/AtomicInteger(底层采用CAS)的方式去分配。 申请sql语句如下(使用事务): Begin UPDATE table SET max_id=max_id+step WHERE tag=xxx SELECT tag, max_id, step FROM table WHERE tag=xxx Commit 优点:每次分配step数量的id,数据库读写压力很低 缺点:HA高可用性要求极高,采用主从部署+异地灾备的部署方案。 3.2.3.3 分布式事务 分库分表场景下,分布式事务涉及到对不同库、不同表的操作要么同时成功,要么同时失败。 分布式事务解决方案: XA事务 柔性事务:最大努力通知型、可靠消息最终一致性方案以及TCC两阶段提交 (待补充) 3.2.3.4 动态扩容 动态扩容是指增加分库分表的数量。动态扩容一般情况下伴随数据迁移。但使用everydb的方式进行数据库扩容时,不需要进行数据迁移。思路如下: ? 在id字段的后面额外加上几位数字。比如加上4位数据,2位表示分库编号,2位表示分表编号。这样一共便拥有了100*100=10000张表。原来的同一个分库分表数据后面加的数字一样即可,这样原来同一分库扩容后还在同一个分库,原来同一分表扩容后还在同一张分表。 3.2.3.5 数据迁移 对于新的应用,如果预估到未来数据量比较大,可以提前进行分库分表。对于老的应用,单表数据量已经比较大了,这时就涉及到数据迁移过程。美团使用Buffalo进行数据迁移。数据迁移流程如下:
|
|
|
上一篇文章 下一篇文章 查看所有文章 |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 | -2024/11/24 10:28:23- |
|
网站联系: qq:121756557 email:121756557@qq.com IT数码 |