如何通过一条 SQL 变更多个分库分表?
数据库发展到今天,分库分表已经不是什么新鲜话题了,传统的单节点数据库架构在数据量和访问频次达到一定规模时,会出现性能瓶颈和扩展性问题,而分库分表技术通过将数据分散到多个数据库实例中来分担负载,从而提升系统的整体性能和稳定性。
当然,本文并不是教你怎么去做分库分表,也不是夸分库分表技术有多牛,而是想具体谈一谈很多企业在分库分表场景下的数据变更难题。
相信很多同学都有深刻体会,在分库分表的实际应用中,由于把一个库的数据分别存在了不同的库,因此一个 DDL 语句往往需要到多个数据库实例中去执行,这就带来了一系列让人挠头的难题。
难题一:变更需要在每一个分表中去执行,如果企业有 1024 个分表,那就需要执行 1024 次,异常耗时还容易出错。
难题二:如果编写脚本去批量执行,技术门槛比较高是一回事,还需要注意各种各样的细节:
挨个连接数据源:如果需要变更的库太多,有多少个库就得写多少个连接脚本,这对于开发者而言是一种负担。
错误捕获:SQL 语句并不是 100% 执行成功的,可能会有各种因素导致执行失败,因此脚本必须能够捕获执行过程中可能出现的各种错误,并在错误发生后妥善处理,以保证脚本执行完成后变更语句在所有表成功执行。
脚本维护成本高:由于变更场景的多样性,在耗费好大精力写完脚本后,只能对当次变更使用,下次有其他新的变更需求,可能无法直接套用脚本,又得重新对脚本做优化。
看到这里,可能已经有同学产生共鸣了,欢迎对号入座,因为大部分企业的分库变更事实上就是这么干的,想要摆脱这些痛点,肯定是有办法的,不做分库分表是不是就行了?当然不是,分库分表对于企业的重要性不言而喻,我们需要在保证分库分表的前提下,给出解决方案。
我们试想如下场景:把所有需要统一进行变更的分库划分到一个库分组中,然后只需要对该库分组提交一次 DDL 变更,那该 DDL 语句就会自动在该库分组下的所有库中完成自动执行。
看上去是不是很方便?下面我们就来看一下,怎么去实现上述的流程。
通过 NineData 的库分组功能实现批量分库变更
在 NineData 的数据库 DevOps 专业版以上版本中,支持库分组的创建,可以将不同数据源中的库添加到该库分组中,用来进行统一的变更与查询。
先简单介绍下配置流程:
基于上面这个流程,我们来演示一下配置方法。
步骤一:录入数据源
将分库所在的数据源全部录入到 NineData 平台。
步骤二:建立库分组
将处于不同数据源中的分库全部添加到库分组中,下图示例中,创建了名为 Poc_Shard_DB
的库分组,包含了 MySQL-POC1 和 MySQL-POC2 数据源中的 poc_test01
、poc_test02
、poc_test03
、poc_test04
4个分库。
步骤三:对库分组执行表结构变更
通过 NineData 的 SQL 任务功能,对库分组发起变更申请,经过系统(规范预审)和审批人员的双重审批后,DDL 语句将会在库分组中的所有分库中执行。
提交 SQL 任务,选择库分组,输入 DDL 语句。本示例给
Poc_Shard_DB
库分组增加一个 age 列。系统自动规划出 DDL 执行的目标库(见下表),然后基于规范对 DDL 语句进行评估,通过后就可以提交人工审批了。
提交审批,选择审批人,然后单击确定。
待审批通过后就可以执行了。在执行过程中,如果 DDL 在某个分库中没有执行成功,就会在任务列表中展示出来,非常方便。
执行完成后,可以查看这几个分组,发现所有分库的目标表中都增加了对应的 age 字段。
总结
本文的整个变更过程中,变更是围绕库分组进行的,库分组可以根据企业的实际业务场景自由添加,具有非常高的通用性,并且操作十分便利,因此可以适用于各种分库变更的场景。
而对于上文中提到的几个变更难题,NineData 的库分组解决方案都可以轻松化解,从此分库变更只需点几下鼠标就完事,不用再绞尽脑汁地写脚本了。
最后补充一个新手大礼包,如果企业的数据源数量不超过 10 个,那么就可以永久免费使用上述功能,不仅如此,所有专业版的高级功能也都可以永久免费使用,废话不多说,直接上手尝试吧。