1.maven 引入依赖jar包
<dependency>
<groupId>io.shardingjdbc</groupId>
<artifactId>sharding-jdbc-core</artifactId>
<version>2.0.3</version>
</dependency>
2.配置数据源信息
databasesString=[{"name": "shading_jdbc1",\
"url": "jdbc:mysql://localhost:3306/shading_jdbc1?allowMultiQueries=true&useUnicode=true&characterEncoding=utf8&rewriteBatchedStatements=true",\
"username": "root",\
"password": "root",\
"driverClassName": "com.mysql.jdbc.Driver",\
"initialSize": "5",\
"minIdle": "5",\
"maxActive": "20",\
"maxWait": "60000",\
"validationQuery": "SELECT 1 FROM DUAL",\
"testOnBorrow": "false",\
"testOnReturn": "false",\
"testWhileIdle": "true",\
"timeBetweenEvictionRunsMillis": "60000",\
"minEvictableIdleTimeMillis": "300000",\
"filters": [\
"stat",\
"log4j"\
]\
},\
{\
"name": "shading_jdbc2",\
"url": "jdbc:mysql://localhost:3306/shading_jdbc2?allowMultiQueries=true&useUnicode=true&characterEncoding=utf8&rewriteBatchedStatements=true",\
"username": "root",\
"password": "root",\
"driverClassName": "com.mysql.jdbc.Driver",\
"initialSize": "5",\
"minIdle": "5",\
"maxActive": "20",\
"maxWait": "60000",\
"validationQuery": "SELECT 1 FROM DUAL",\
"testOnBorrow": "false",\
"testOnReturn": "false",\
"testWhileIdle": "true",\
"timeBetweenEvictionRunsMillis": "60000",\
"minEvictableIdleTimeMillis": "300000",\
"filters": [\
"stat",\
"log4j"\
]\
}\
]
tableString=shading_jdbc1.user1,shading_jdbc1.user2,shading_jdbc2.user1,shading_jdbc2.user2
//这里是配置的数据源信息
@Value("${databasesString}")
protected String databasesString;
//这里是分表的信息
@Value("#{'${tableString}'.split(',')}")
protected List<String> tableString;
@Bean
public Map<String, DataSource> dataSourceMap() {
Map<String, DataSource> dataSourceMap = new HashMap<>();
if (StringUtils.isEmpty(databasesString)){
log.error("数据库database配置数据为空,请查看配置参数:databasesString");
throw new BizException(-1L,"数据库database配置数据为空");
}
try {
List<DataSourceShading> databases = new Gson().fromJson(databasesString,
new TypeToken<List<DataSourceShading>>(){}.getType());
for (DataSourceShading dataSourceShading : databases) {
DruidDataSource dataSource = new DruidDataSource();
BeanUtils.copyProperties(dataSourceShading,dataSource);
dataSourceMap.put(dataSourceShading.getName(), dataSource);
}
}catch (Exception e){
e.printStackTrace();
log.error("数据库database配置数据异常,请查看配置参数:databasesString :{},error:{}",databasesString,e.getMessage(),e);
throw new BizException(-1L,"数据库database配置数据异常");
}
return dataSourceMap;
}
@Bean("shardingDataSource")
public DataSource shardingDataSource(HashMap<String, DataSource> dataSourceMap) throws SQLException{
//数据库shading策略
StandardShardingStrategy databaseShardingStrategy = new StandardShardingStrategy("user_id", new DataSourceShardingAlgorithm());
//数据表shading策略
StandardShardingStrategy tableShardingStrategy = new StandardShardingStrategy("user_id", new TableShardingAlgorithm());
//单个表的分库分表规则配置
TableRule userTableRule = new TableRule("user",tableString,dataSourceMap,databaseShardingStrategy,tableShardingStrategy,null,null,null);
//整体的分库分表规则配置
ShardingRule shardingRule = new ShardingRule(dataSourceMap,"shading_jdbc1", Lists.<TableRule>newArrayList(userTableRule),databaseShardingStrategy,tableShardingStrategy,null);
return new ShardingDataSource(shardingRule);
}
3.实现分库分表策略
private long getIndex(long id, int size) {
return (id & (size - 1)) + 1;
}
/**
* 根据分片值和SQL的=运算符计算分片结果名称集合.
*
* @param availableTargetNames 所有的可用目标名称集合, 一般是数据源
* @param preciseShardingValue 分片值 也就是分片规则的字段值
*
* @return 分片后指向的目标名称, 一般是数据源或表名称
*/
@Override
public String doSharding(Collection<String> availableTargetNames, PreciseShardingValue<Long> preciseShardingValue) {
long index = getIndex(preciseShardingValue.getValue(),availableTargetNames.size());
for (String targetName : availableTargetNames) {
if (targetName.endsWith(index+"")) {
log.debug("the target database name: {}", targetName);
return targetName;
}
}
throw new UnsupportedOperationException();
}