花了2天時間研究了一下Sharding-JDBC的使用,這里簡單記錄一下。
代碼弄的比較亂,就沒放到git上,需要源碼的可以留下郵箱或者其他聯系方式,我看到了發你。
遺留問題:Druid無法監控2個數據源的sql。
應該需要通過編寫DataSourceConfig.java的方式解決。
目錄
1.POM文件的內容
2.分庫分表+分庫不分表
3.讀寫分離
4.ComplexKeysShardingAlgorithm實現
1.POM文件的內容
pom文件在引用Sharding-jdbc時有2張方式:
sharding-jdbc-spring-boot-starter(后面的描述用的是這種方式)
這種方式可以不用自己寫DataSourceConfig文件-
sharding-jdbc-core
這種方式的例子,基本都是要自己寫DataSourceConfig文件的
參考:http://www.lxweimin.com/p/3b2ab87b0de7
https://blog.csdn.net/a992795427/article/details/85102918
https://www.cnblogs.com/mr-yang-localhost/p/8280500.html#sharding-jdbc-spring-boot-starter方式的參考pom文件 <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId>mybatis-spring-boot-starter</artifactId> <version>2.1.0</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.21</version> </dependency> <dependency> <groupId>io.shardingsphere</groupId> <artifactId>sharding-jdbc-spring-boot-starter</artifactId> <version>3.1.0.M1</version> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid-spring-boot-starter</artifactId> <version>1.1.23</version> </dependency> </dependencies>
2.分庫分表+分庫不分表
用的的數據庫# 相關表結構
CREATE TABLE `order0` (
`id` bigint(11) NOT NULL COMMENT '主鍵ID',
`user_id` bigint(11) DEFAULT NULL COMMENT '用戶ID',
`order_id` bigint(11) DEFAULT NULL COMMENT '訂單ID',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `user_info` (
`user_id` bigint(19) NOT NULL,
`user_name` varchar(45) DEFAULT NULL,
`account` varchar(45) NOT NULL,
`password` varchar(45) DEFAULT NULL,
PRIMARY KEY (`user_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
application.properties文件參考
spring.application.name=sharding-jdbc
#mybatis
mybatis.configuration.map-underscore-to-camel-case=true
mybatis.type-aliases-package=com.lbc.demo.model
mybatis.mapper-locations=classpath:mapper/*Mapper.xml
#當注冊遇到相同名字是否允許被注冊,在配置中心無效
spring.main.allow-bean-definition-overriding=true
#所有主從庫
sharding.jdbc.datasource.names=user0,user1
#dsmaster0
sharding.jdbc.datasource.user0.type=com.alibaba.druid.pool.DruidDataSource
sharding.jdbc.datasource.user0.driver-class-name=com.mysql.jdbc.Driver
sharding.jdbc.datasource.user0.url=jdbc:mysql://localhost:3306/user0?useSSL=false
sharding.jdbc.datasource.user0.username=root
sharding.jdbc.datasource.user0.password=password
#slave for ds_master_0
sharding.jdbc.datasource.user1.type=com.alibaba.druid.pool.DruidDataSource
sharding.jdbc.datasource.user1.driver-class-name=com.mysql.jdbc.Driver
sharding.jdbc.datasource.user1.url=jdbc:mysql://localhost:3306/user1?useSSL=false
sharding.jdbc.datasource.user1.username=root
sharding.jdbc.datasource.user1.password=password
#分庫規則
sharding.jdbc.config.sharding.default-database-strategy.inline.sharding-column=user_id
sharding.jdbc.config.sharding.default-database-strategy.inline.algorithm-expression=user$->{user_id % 2}
# 綁定邏輯表
sharding.jdbc.config.sharding.binding-tables=order
# 設置分表規則
# sharding.jdbc.config.sharding.tables.邏輯表.actual-data-nodes:邏輯表對應的真實表
# sharding.jdbc.config.sharding.tables.邏輯表.table-strategy.inline.sharding-column:分表列
# sharding.jdbc.config.sharding.tables.邏輯表.table-strategy.inline.algorithm-expression:分表算法
# sharding.jdbc.config.sharding.tables.邏輯表.key-generator-column-name:主鍵列
# 分庫,也分表
sharding.jdbc.config.sharding.tables.order.actual-data-nodes=user$->{0..1}.order$->{0..1}
sharding.jdbc.config.sharding.tables.order.table-strategy.inline.sharding-column=order_id
sharding.jdbc.config.sharding.tables.order.table-strategy.inline.algorithm-expression=order$->{order_id % 2}
sharding.jdbc.config.sharding.tables.order.key-generator-column-name=id
# 只分庫,不分表
sharding.jdbc.config.sharding.tables.user_info.actual-data-nodes=user$->{0..1}.user_info
sharding.jdbc.config.sharding.tables.user_info.table-strategy.inline.sharding-column=user_id
sharding.jdbc.config.sharding.tables.user_info.table-strategy.inline.algorithm-expression=user_info
sharding.jdbc.config.sharding.tables.user_info.key-generator-column-name = user_id
#邏輯主從庫名和實際主從庫映射關系
#sharding.jdbc.config.sharding.master-slave-rules.ds0.master-data-source-name=dsmaster0
#用逗號分隔
#sharding.jdbc.config.sharding.master-slave-rules.ds0.slave-data-source-names=dsmaster0
#sharding.jdbc.config.sharding.master-slave-rules.dsmaster1.masterDataSourceName=dsmaster1
#sharding.jdbc.config.sharding.master-slave-rules.dsmaster1.slaveDataSourceNames=dsmaster1slave0
server.port=8080
3.讀寫分離
用到的數據庫和表機構同上
application.yml參考文件
sharding:
jdbc:
dataSource:
names: db-test0,db-test1
# 配置主庫
db-test0: #org.apache.tomcat.jdbc.pool.DataSource
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/user0?useUnicode=true&characterEncoding=utf8&tinyInt1isBit=false&useSSL=false&serverTimezone=GMT
username: root
password: password
#最大連接數
maxPoolSize: 3
db-test1: # 配置第一個從庫
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/user1?useUnicode=true&characterEncoding=UTF-8&allowMultiQueries=true&useSSL=false&serverTimezone=GMT
username: root
password: password
maxPoolSize: 3
config:
masterslave: # 配置讀寫分離
load-balance-algorithm-type: round_robin # 配置從庫選擇策略,提供輪詢與隨機,這里選擇用輪詢//random 隨機 //round_robin 輪詢
name: db1s2
master-data-source-name: db-test0
slave-data-source-names: db-test1
props:
sql: # 開啟SQL顯示,默認值: false,注意:僅配置讀寫分離時不會打印日志!!!
show: true
mybatis:
configuration:
map-underscore-to-camel-case: true
type-aliases-package: com.lbc.demo.model
mapper-locations: classpath:mapper/*Mapper.xml
4.ComplexKeysShardingAlgorithm實現
Complex方式的配置文件和2.分庫分表+分庫不分表的配置文件類似,只改了一個東西
分庫,也分表
sharding.jdbc.config.sharding.tables.order.actual-data-nodes=user$->{0..1}.order$->{0..1}
sharding.jdbc.config.sharding.tables.order.table-strategy.complex.sharding-columns=user_id,order_id
sharding.jdbc.config.sharding.tables.order.table-strategy.complex.algorithm-class-name=com.lbc.demo.config.ComplexShardingAlgorithm
然后,需要增加一個路由類ComplexShardingAlgorithm,這里最好debug一下。
public class ComplexShardingAlgorithm implements ComplexKeysShardingAlgorithm {
/**
* @param collection 在加載配置文件時,會解析表分片規則。將結果存儲到 collection中,doSharding()參數使用
* @param shardingValues SQL中對應的
* @return
*/
@Override
public Collection<String> doSharding(Collection<String> collection, Collection<ShardingValue> shardingValues) {
System.out.println("collection:" + collection + ",shardingValues:" + shardingValues);
Collection<Long> orderIdValues = getShardingValue(shardingValues, "order_id");
Collection<Long> userIdValues = getShardingValue(shardingValues, "user_id");
List<String> shardingSuffix = new ArrayList<>();
// user_id,order_id分片鍵進行分表
for (Long userId : userIdValues) {
for (Long orderId : orderIdValues) {
String suffix = userId % 2 + "_" + orderId % 2;
//寫死測試
suffix="0";
for (String s : collection) {
if (s.endsWith(suffix)) {
shardingSuffix.add(s);
}
}
}
}
return shardingSuffix;
}
private Collection<Long> getShardingValue(Collection<ShardingValue> shardingValues, final String key) {
Collection<Long> valueSet = new ArrayList<>();
Iterator<ShardingValue> iterator = shardingValues.iterator();
while (iterator.hasNext()) {
ShardingValue next = iterator.next();
if (next instanceof ListShardingValue) {
ListShardingValue value = (ListShardingValue) next;
// user_id,order_id分片鍵進行分表
if (value.getColumnName().equals(key)) {
return value.getValues();
}
}
}
return valueSet;
}
}
參考了太多了,記不清了:
http://www.lxweimin.com/p/3b2ab87b0de7
http://www.lxweimin.com/p/9eebfae039c9
https://segmentfault.com/a/1190000019906637
https://www.cnblogs.com/yixinjishu/p/10876071.html
https://www.cnblogs.com/mr-yang-localhost/p/8280500.html
[https://blog.csdn.net/hy245120020/article/details/85335446]
http://www.lxweimin.com/p/e4f291052c83
(https://blog.csdn.net/hy245120020/article/details/85335446)
https://blog.csdn.net/forezp/article/details/94343671
https://blog.csdn.net/a992795427/article/details/85102918
https://www.cnblogs.com/mr-yang-localhost/p/8280500.html