Skip to content

Zebra分库分表api介绍

junior_xin edited this page Jan 23, 2019 · 1 revision

zebra API是什么

zebra API是针对分库分表场景(ShardDataSource),提供的一套可以通过手动指定一些路由参数 的方式来改变zebra默认路由行为的API。通过API,用户可以手动指定SQL本身以外的列 或值 来实现将SQL路由到任意用户想要路由的表上。

zebra API依靠ShardDataSourceHelper类提供的static接口,来实现相关的功能。

zebra API功能有哪些

zebra API目前支持指定路由用的

指定用于路由的值

通过ShardDataSourceHelper.setShardParams(column, value)接口,可以设置某个shardKey的值为多少,然后这个值就可以参与到路由的计算当中。

用法场景

在我们的实际使用场景中,偶尔会有需要将某些sql(SQL不带shard key或者想指定shard key的值)发送到某张具体的表执行,这个时候就需要使用zebra的api接口,来虚拟分表值来达到这种目的。

下面我们就举例说明该功能怎么使用:

后面的例子都以下面规则为例

表名:table
分库规则:(#id#.toLong())%4   zebrasample[0-3]
分表规则:(#sid#.toLong())%2  alldb:[0,7]

批量写入

仅支持批量写入的SQL确定都在同一库同一张表上,不支持批量写入的SQL在不同的库上。

//这里指定一下shardKey和shardValue分别是多少
ShardDataSourceHelper.setShardParams(“id”, 0);
ShardDataSourceHelper.setShardParams(“sid”, "100");
// 上面两个配置,就指定了,接下来我们执行的SQL会以【id=0,sid="100"】这组规则来路由SQL,即zebrasample0库,table0表。
// **注:如果只设置了一个规则,比如id或者sid,那么这个设置会被忽略掉。

// 如果以上设置的参数需要用在同一个线程的多条SQL中,请执行以下代码,否则zebra内部会默认调用 ShardDataSourceHelper.clearAllThreadLocal() 清理
ShardDataSourceHelper.setGlobalParams(true);

//指定框架无需从SQL中获取shardKey和shardValue了,直接从用户的传入获得
ShardDataSourceHelper.setExtractParamsOnlyFromThreadLocal(true);
 
//业务调用batch insert
dao.batchInsert();
 
//调用完毕后,请清理一下threadlocal变量
ShardDataSourceHelper.clearAllThreadLocal();

自定义分表Key

有的时候,业务对某个表进行分表时,分表的键可以不存在SQL中,可以自定义一个分表键。举例来说,对于以下SQL

select * from table where name = "test"

其中在这个SQL中并没有分表键id和sid,跟上面的使用方式类型,此时可以调用zebra api来虚拟一组分表键,来指定SQL到哪个库表上执行:

//这里指定一下shardKey和shardValue分别是多少
ShardDataSourceHelper.setShardParams(“id”, 1);
ShardDataSourceHelper.setShardParams(“sid”, 1);
// 后面的SQL将在zebrasample1,table1上执行

// 如果以上设置的参数需要用在同一个线程的多条SQL中,请执行以下代码,否则zebra内部会默认调用 ShardDataSourceHelper.clearAllThreadLocal() 清理
ShardDataSourceHelper.setGlobalParams(true);

//如果dbRule或tbRule中所有的维度都是自定义传入,那么还需要调用以下API;如果还有其他数据从SQL中获得,那么无需调用。
ShardDataSourceHelper.setExtractParamsOnlyFromThreadLocal(true);
 
// 执行业务SQL
dao.execute();
 
//调用完毕后,请清理一下threadlocal变量
ShardDataSourceHelper.clearAllThreadLocal();

对于查询,除了上述用法外,还可以指定多组shardkey来执行:

//这里指定一下shardKey和shardValue分别是多少
ShardDataSourceHelper.setShardParams(“id”, Arrays.asList(1,2,3););
ShardDataSourceHelper.setShardParams(“sid”, Arrays.asList(4,5,6););
// 上面这种用法,zebra将解释为【id=1,sid=4】,【id=2,sid=5】,【id=3,sid=6】这样一一对应的三组路由规则,然后将SQL分别发送到
// zebrasample1.table2
// zebrasample2.table5
// zebrasample3.table6  这三张表里执行
// 两个分表键的值list长度不等,则以短的为准,其余的将被抛弃,比如id:[1,2,3,4], sid:[4,5],那么最后只有[1,4],[2,5]这两组值会生效

// 如果以上设置的参数需要用在同一个线程的多条SQL中,请执行以下代码,否则zebra内部会默认调用 ShardDataSourceHelper.clearAllThreadLocal() 清理
ShardDataSourceHelper.setGlobalParams(true);

//如果dbRule或tbRule中所有的维度都是自定义传入,那么还需要调用以下API;如果还有其他数据从SQL中获得,那么无需调用。
ShardDataSourceHelper.setExtractParamsOnlyFromThreadLocal(true);
 
// 执行业务SQL
dao.execute();
 
//调用完毕后,请清理一下threadlocal变量
ShardDataSourceHelper.clearAllThreadLocal();
Clone this wiki locally