Springboot 集成 Shardingsphere-JDBC

news2024/11/28 18:50:57

Springboot 集成 Shardingsphere-JDBC

  • Shardingsphere系列目录:
  • 背景
  • 前提
  • 新增依赖
  • 分表策略
    • 简单分库分表策略
      • 垂直分库
      • 广播表
      • 水平分库(单表)
      • 水平分库(多表)
      • 水平分表
    • HINT
      • 配置
      • 逻辑代码
    • 自定义分库分表(精准定位+范围查询)
      • 配置
      • 代码
        • 精准定位数据库
        • 精准定位+范围查询表
  • 特殊情况
  • 代码仓库地址

Shardingsphere系列目录:

【Springboot 集成 Shardingsphere-JDBC】
【Shardingsphere-Proxy 5.5.0部署】

背景

项目中,某数据库单表数据量已达到4000w+,查询和插入数据性能越来越差,跟踪发现这个表一个月有8w的新增数据量,所以需要进行分库分表减轻单库单表的压力。

前提

Shardingsphere不会为你自动建库建表,需要自行将分开的表以及对应数据库全部创建出来。

新增依赖

有两个依赖提供给大家

<dependency>
   <groupId>org.apache.shardingsphere</groupId>
    <artifactId>sharding-jdbc-spring-boot-starter</artifactId>
    <version>4.1.1</version>
</dependency>

<dependency>
    <groupId>org.apache.shardingsphere</groupId>
    <artifactId>shardingsphere-jdbc-core-spring-boot-starter</artifactId>
    <version>5.2.1</version>
</dependency>

以上两个依赖只能加一个,建议使用后者,因为毕竟差着1个大版本,并且,前者最高版本就是4.1.1,看样子好像是不会再维护了。

分表策略

简单分库分表策略

垂直分库

# 垂直分库
spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        url: jdbc:mysql://localhost:3306/sharding_payorder_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        username: root
      # 数据源别名
      db2:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        url: jdbc:mysql://localhost:3306/sharding_user_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        username: root
      # 数据源别名列表
      names: db1,db2
    props:
      # 展示执行sql
      sql-show: true
    rules:
      sharding:
        # 标准分片表配置,由数据源名 + 表名组成,以小数点分隔。多个表以逗号分隔,支持 inline 表达式。
        tables:
          pay_order:
            actual-data-nodes: db1.pay_order
          users:
            actual-data-nodes: db2.users

广播表

# 广播表
spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名
      db0:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db0?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db1?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名列表
      names: db0,db1,db
    props:
      sql-show: true
    rules:
      sharding:
        # 广播表配置
        broadcast-tables:
          - t_district
        tables:
          t_district:
            # 广播表设置,定位广播表所在数据源
            actual-data-nodes: db$->{0..1}.t_district,db.t_district

水平分库(单表)

# 水平分库(单表)
spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db0:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db0?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db1?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名列表
      names: db0,db1
    props:
      sql-show: true
    rules:
      sharding:
        # 主键生成算法定义
        key-generators:
          # 主键生成算法定义名称
          alg-snowflake:
            # 对应主键生成算法
            type: SNOWFLAKE
        # 分片算法定义
        sharding-algorithms:
          # 分片算法定义名称
          inline-hash-mod:
            props:
              # 分片算法表达式
              algorithm-expression: t_course_$->{Math.abs(cid.hashCode()) % 2}
            # 分片算法类型,行表达式分片算法
            type: INLINE
          # 分片算法定义名称
          table-inline:
            props:
              # 分片算法表达式
              algorithm-expression: db$->{user_id % 2}
            # 分片算法类型,行表达式分片算法
            type: INLINE
        tables:
          t_course:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.t_course_$->{0..1}
            # 数据库分片策略
            database-strategy:
              standard:
                # 数据库分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-inline
                # 数据库分片列名称
                sharding-column: user_id
            # t_course表主键生成策略
            key-generate-strategy:
              # 主键列名称
              column: cid
              # 主键生成算法名称,在上面的 key-generators 内容中配置
              key-generator-name: alg-snowflake
            # 表分片策略
            table-strategy:
              standard:
                # 表分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: inline-hash-mod
                # 表分片列名称
                sharding-column: cid

水平分库(多表)

# 水平分库(多表)
spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db0:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db0?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db1?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名列表
      names: db0,db1
    props:
      sql-show: true
    rules:
      sharding:
        # 绑定表配置
        binding-tables:
          - t_course,t_course_section
        # 主键生成算法定义
        key-generators:
          # 主键生成算法定义名称
          alg-snowflake:
            # 对应主键生成算法
            type: SNOWFLAKE
        # 分片算法定义
        sharding-algorithms:
          # 分片算法定义名称
          table-hash-mod:
            props:
              # 指定分片数量
              sharding-count: 2
            # 哈希取模分片算法
            type: HASH_MOD
          # 分片算法类型,分片算法定义名称
          table-mod:
            props:
              # 指定分片数量
              sharding-count: 2
            # 片算法类型,取模分片算法
            type: MOD
        tables:
          t_course:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.t_course_$->{0..1}
            # 数据库分片策略
            database-strategy:
              standard:
                # 数据库分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-mod
                # 数据库分片列名称
                sharding-column: user_id
            # t_course表主键生成策略
            key-generate-strategy:
              # 主键列名称
              column: cid
              # 主键生成算法名称,在上面的 key-generators 内容中配置
              key-generator-name: alg-snowflake
            # 表分片策略
            table-strategy:
              standard:
                # 表分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-mod
                # 表分片列名称
                sharding-column: corder_no
          t_course_section:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.t_course_section_$->{0..1}
            # 数据库分片策略
            database-strategy:
              standard:
                # 数据库分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-mod
                # 数据库分片列名称
                sharding-column: user_id
            # t_course_section表主键生成策略
            key-generate-strategy:
              # 主键列名称
              column: id
              # 主键生成算法名称,在上面的 key-generators 内容中配置
              key-generator-name: alg-snowflake
            # 表分片策略
            table-strategy:
              standard:
                # 表分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-mod
                # 表分片列名称
                sharding-column: corder_no

水平分表

# 水平分表
spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/sharding_course_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      tdms:
        driver-class-name: com.mysql.cj.jdbc.Driver
        type: com.alibaba.druid.pool.DruidDataSource
        url: jdbc:mysql://localhost:3306/jvs_tdms?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        username: root
        password: 1234
      # 数据源别名列表
      names: db1,tdms
    # 未分片数据库,如果分片数据库也有未分片的表,会优先查分片数据库的这个表,否则去查默认的未分片数据库
    sharding:
      default-data-source-name: tdms
    props:
      sql-show: true
    rules:
      sharding:
        # 主键生成算法定义
        key-generators:
          # 主键生成算法定义名称
          alg-snowflake:
            # 对应主键生成算法
            type: SNOWFLAKE
        # 分片算法定义
        sharding-algorithms:
          # 分片算法定义名称
          table-inline:
            props:
              # 分片算法表达式
              algorithm-expression: t_course_$->{cid % 2 + 1}
            # 分片算法类型,行表达式分片算法
            type: INLINE
        tables:
          t_course:
            # 配置表节点
            actual-data-nodes: db1.t_course_$->{1..2}
            # t_course表主键生成策略
            key-generate-strategy:
              # 主键列名称
              column: cid
              # 主键生成算法名称,在上面的 key-generators 内容中配置
              key-generator-name: alg-snowflake
            table-strategy:
              standard:
                # 表分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-inline
                # 表分片列名称
                sharding-column: cid

以上这些配置较简单,最后我会附上工程,大家可以拿去借鉴,只修改yml配置即可,不用修改逻辑代码:
在这里插入图片描述

HINT

该方式我单独拎出来,是因为这个是能实现精准定位表来更新数据的方式,但是数据库的分片逻辑需要配置。

配置

spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/tss_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名列表
      names: db1
#    props:
#      sql-show: true
    rules:
      sharding:
        # 分片算法定义
        sharding-algorithms:
          # 分片算法定义名称
          table-inline:
            type: HINT_INLINE
            props:
              algorithm-expression: tss_table_$->{value}
          # 分片算法定义名称
          table-tenant-inline:
            type: HINT_INLINE
            props:
              algorithm-expression: tss_tenant_table_$->{value}
        tables:
          tss_table:
            # 配置表节点
            actual-data-nodes: db1.tss_table_$->{1..31}
            table-strategy:
              hint:
                # 表分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-inline
          tss_tenant_table:
            # 配置表节点
            actual-data-nodes: db1.tss_tenant_table_$->{1..31}
            table-strategy:
              hint:
                # 表分片策略名称,在上面的 sharding-algorithms 内容中配置
                sharding-algorithm-name: table-tenant-inline

最后我附上的工程中也有相关配置。

逻辑代码

@SpringBootTest
class TssTests {

    @Resource
    private TssTableMapper tssTableMapper;

    /**
     * tss数据库batch insert语句测试
     */
    @Test
    public void testTssBatchInsert() {
        HintManager hintManager = HintManager.getInstance();
        // 指定插到的表名及配置里写明的后缀
        hintManager.addTableShardingValue("tss_table", 7);
        List<TssTable> tssTableList = tssTableMapper.selectList(null);
        hintManager.addTableShardingValue("tss_table", 6);
        for(TssTable item : tssTableList){
            tssTableMapper.insert(item.setId(null));
        }
        hintManager.close();

    }
}

自定义分库分表(精准定位+范围查询)

这个是最灵活的一种方式,既需要配置也需要修改逻辑代码,我以上面提供的5.2.1版本的依赖方式实现:

配置

# tss水平分库分表精准分片
spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 数据源别名
      db0:
        # 数据库连接信息
        driver-class-name: com.mysql.cj.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/tss_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.cj.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/tss_db_2?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名列表
      names: db0,db1
    rules:
      sharding:
        # 算法配置
        sharding-algorithms:
          # 数据库分片算法
          my-db-strategy:
            # 算法类型:自定义算法
            type: CLASS_BASED
            props:
              # 算法策略:标准算法
              strategy: standard
              # 自定义算法类路径
              algorithmClassName: com.shardingjdbc.config.upgrade.MyDbShardingAlgorithm
          # 表分片算法
          my-tss-table-strategy:
            # 算法类型:自定义算法
            type: CLASS_BASED
            props:
              # 算法策略:标准算法
              strategy: standard
              # 自定义算法类路径
              algorithmClassName: com.shardingjdbc.config.upgrade.TssTableShardingAlgorithm
          # 表分片算法
          my-tss-tenant-table-strategy:
            # 算法类型:自定义算法
            type: CLASS_BASED
            props:
              # 算法策略:标准算法
              strategy: standard
              # 自定义算法类路径
              algorithmClassName: com.shardingjdbc.config.upgrade.TssTenantTableShardingAlgorithm
        tables:
          tss_table:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.tss_table_$->{1..31}
            database-strategy:
              standard:
                sharding-algorithm-name: my-db-strategy
                sharding-column: tenant_id
            table-strategy:
              standard:
                sharding-column: opt_date
                sharding-algorithm-name: my-tss-table-strategy
          tss_tenant_table:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.tss_tenant_table_$->{1..31}
            database-strategy:
              standard:
                sharding-algorithm-name: my-db-strategy
                sharding-column: tenant_id
            table-strategy:
              standard:
                sharding-column: opt_date
                sharding-algorithm-name: my-tss-tenant-table-strategy

配置中一定要注意别忘了rules关键字。

代码

精准定位数据库

在插入数据的时候,这个类【有PreciseShardingValue传参的doSharding方法】可以根据配置中的数据库策略传来的字段值,然后进行逻辑操作之后【返回数据库名】直接定位插入的数据库。

package com.shardingjdbc.config.upgrade;

import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.shardingsphere.sharding.api.sharding.standard.PreciseShardingValue;
import org.apache.shardingsphere.sharding.api.sharding.standard.RangeShardingValue;
import org.apache.shardingsphere.sharding.api.sharding.standard.StandardShardingAlgorithm;

import java.util.Collection;
import java.util.List;
import java.util.Properties;
import java.util.stream.Collectors;

@Slf4j
public class MyDbShardingAlgorithm implements StandardShardingAlgorithm<String> {
    @Override
    public String doSharding(Collection<String> collection, PreciseShardingValue<String> preciseShardingValue) {
        // 获取分片键的值
        if(collection.isEmpty()){
            log.error("------- shardingsphere log database list is empty !!!");
            return "";
        }
        String value = preciseShardingValue.getValue();
        String logicTableName = preciseShardingValue.getLogicTableName();
        log.info("------- shardingsphere log database list:{}, value: {}, logicTableName: {}",collection,value,logicTableName);
        // 计算hash
        String dataSourceIndex = String.valueOf(Math.abs(value.hashCode()) % collection.size());
        log.info("------- shardingsphere log dataSourceIndex: {}",dataSourceIndex);
        // 排序,怕之后根据后缀定表会出现问题,2后缀有2,12,22,排序之后endWith筛选后选第一个就没有问题了
        List<String> sortedDbName = collection.stream().sorted().collect(Collectors.toList());
        // 查询对应数据库名
        String result = sortedDbName.stream().filter(item -> item.endsWith(dataSourceIndex)).findFirst().orElse(null);
        if(StringUtils.isBlank(result)){
            result = sortedDbName.get(0);
        }
        return result;
    }

    @Override
    public Collection<String> doSharding(Collection<String> collection, RangeShardingValue<String> rangeShardingValue) {
        return null;
    }

    @Override
    public Properties getProps() {
        return null;
    }

    @Override
    public void init(Properties properties) {

    }
}

精准定位+范围查询表
  1. 可以根据自己的逻辑确定要插入数据的表名
  2. 可以根据查询的范围来指定筛选的表范围,避免全库全表查询,仅查询部分表即可,提高查询效率。
package com.shardingjdbc.config.upgrade;

import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.google.common.collect.Range;
import lombok.extern.slf4j.Slf4j;
import org.apache.shardingsphere.sharding.api.sharding.standard.PreciseShardingValue;
import org.apache.shardingsphere.sharding.api.sharding.standard.RangeShardingValue;
import org.apache.shardingsphere.sharding.api.sharding.standard.StandardShardingAlgorithm;

import java.util.*;

@Slf4j
public class TssTenantTableShardingAlgorithm implements StandardShardingAlgorithm<Date> {
    @Override
    public String doSharding(Collection<String> collection, PreciseShardingValue<Date> preciseShardingValue) {
        log.info("------- shardingsphere log table name get in TssTenantTableShardingAlgorithm collection = {} , preciseShardingValue = {}",collection, preciseShardingValue);
        //可以获取三个值,也就是course逻辑表名,columnName id,value 获取的值
        String logicTableName = preciseShardingValue.getLogicTableName();
        Date value = preciseShardingValue.getValue();
        Calendar cal = Calendar.getInstance();
        cal.setTime(value);
        String key = logicTableName + "_" + cal.get(Calendar.DAY_OF_MONTH);
        log.info("------- shardingsphere log table name = {}",key);
        if (StringUtils.isNotBlank(key)) {
            return key;
        }
        return null;
    }

    @Override
    public Collection<String> doSharding(Collection<String> collection, RangeShardingValue<Date> rangeShardingValue) {
        log.info("------- shardingsphere log table name get in TssTenantTableShardingAlgorithm collection = {} , rangeShardingValue = {}",collection, rangeShardingValue);
        // 获取分片键值,时间类型的值(LocalDateTime等)会自动转为java.sql.Timestamp,可以直接用java.util.Date接收
        Range<Date> valueRange = rangeShardingValue.getValueRange();
        // 获取范围小值
        Date lowerEndpoint = valueRange.lowerEndpoint();
        // 获取范围大值
        Date upperEndpoint = valueRange.upperEndpoint();
        Calendar startTime = Calendar.getInstance();
        Calendar endTime = Calendar.getInstance();
        startTime.setTime(lowerEndpoint);
        endTime.setTime(upperEndpoint);
        // 逻辑表名
        String logicTableName = rangeShardingValue.getLogicTableName();
        Set<String> tables = new HashSet<>();
        // 比较两个时间
        while (startTime.compareTo(endTime) <= 0) {
            // 添加到集合
            tables.add(buildTable(logicTableName, startTime));
            // 往后加一个月
            startTime.add(Calendar.DAY_OF_MONTH,1);
        }
        if (tables.isEmpty()) {
            log.error("------- shardingsphere log table name is empty");
        }
        log.info("------- shardingsphere log table name list = {}", tables);
        return tables;
    }

    private String buildTable(String logicTableName, Calendar dateTime) {
        return logicTableName + "_" + dateTime.get(Calendar.DAY_OF_MONTH);
    }

    @Override
    public Properties getProps() {
        return null;
    }

    @Override
    public void init(Properties properties) {

    }
}

特殊情况

如果你的这个工程需要连接三个数据库,一个数据库中放的全是未分片的单表另两个数据库有实现分库的分片表,这种情况需要进行要怎么配置呢?配置如下:

spring:
  application:
    name: sharding-jdbc
  shardingsphere:
    datasource:
      # 单表数据源别名
      db:
        # 数据库连接信息
        driver-class-name: com.mysql.cj.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/tss_db?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 分库数据源别名
      db0:
        # 数据库连接信息
        driver-class-name: com.mysql.cj.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/tss_db1?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 分库数据源别名
      db1:
        # 数据库连接信息
        driver-class-name: com.mysql.cj.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/tss_db_2?allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai&characterEncoding=utf8&autoReconnect=true&useSSL=false&maxReconnects=666&failOverReadOnly=false&initialTimeout=10&zeroDateTimeBehavior=convertToNull&allowMultiQueries=true
        password: 1234
        type: com.zaxxer.hikari.HikariDataSource
        username: root
      # 数据源别名列表
      names: db,db0,db1
    rules:
      sharding:
        # 算法配置
        sharding-algorithms:
          # 数据库分片算法
          my-db-strategy:
            # 算法类型:自定义算法
            type: CLASS_BASED
            props:
              # 算法策略:标准算法
              strategy: standard
              # 自定义算法类路径
              algorithmClassName: com.shardingjdbc.config.upgrade.MyDbShardingAlgorithm
          # 表分片算法
          my-tss-table-strategy:
            # 算法类型:自定义算法
            type: CLASS_BASED
            props:
              # 算法策略:标准算法
              strategy: standard
              # 自定义算法类路径
              algorithmClassName: com.shardingjdbc.config.upgrade.TssTableShardingAlgorithm
          # 表分片算法
          my-tss-tenant-table-strategy:
            # 算法类型:自定义算法
            type: CLASS_BASED
            props:
              # 算法策略:标准算法
              strategy: standard
              # 自定义算法类路径
              algorithmClassName: com.shardingjdbc.config.upgrade.TssTenantTableShardingAlgorithm
        tables:
          tss_table:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.tss_table_$->{1..31}
            database-strategy:
              standard:
                sharding-algorithm-name: my-db-strategy
                sharding-column: tenant_id
            table-strategy:
              standard:
                sharding-column: opt_date
                sharding-algorithm-name: my-tss-table-strategy
          tss_tenant_table:
            # 配置表节点
            actual-data-nodes: db$->{0..1}.tss_tenant_table_$->{1..31}
            database-strategy:
              standard:
                sharding-algorithm-name: my-db-strategy
                sharding-column: tenant_id
            table-strategy:
              standard:
                sharding-column: opt_date
                sharding-algorithm-name: my-tss-tenant-table-strategy

与上面的【自定义分库分表】配置相比,差别就两个:

  1. 新增spring.application.shardingsphere.datasource.db单表数据源配置。
  2. 修改spring.application.shardingsphere.datasource.names数据源别名配置。

代码仓库地址

https://gitee.com/hepai123/shardingjdbc-demo.git

[develop-tss-upgrade]分支是上面说的【自定义分库分表(精准定位+范围查询)】源码,除此之外,其他的源码全在 [develop-tss]分支

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1851329.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

计算机系统基础实训七-MallocLab实验

实验目的与要求 1、让学生理解动态内存分配的工作原理&#xff1b; 2、让学生应用指针、系统级编程的相关知识&#xff1b; 3、让学生应用各种动态内存分配器的实现方法&#xff1b; 实验原理与内容 &#xff08;1&#xff09;动态内存分配器基本原理 动态内存分配器维护…

python入门基础知识(错误和异常)

本文部分内容来自菜鸟教程Python 基础教程 | 菜鸟教程 (runoob.com) 本人负责概括总结代码实现。 以此达到快速复习目的 目录 语法错误 异常 异常处理 try/except try/except...else try-finally 语句 抛出异常 用户自定义异常 内置异常类型 常见的标准异常类型 语法…

Java赋值运算符

Java赋值运算符分为以下&#xff1a; 符号 作用 说明 赋值 int a 10,把10赋值给变量a 加后赋值 ab,将ab的值赋值给变量a - 减后赋值 a-b,将a-b的值赋值给变量a* 乘后赋值 a*b,将a*b的值赋值给变量a / 除后赋值 a/b,将a/b的值赋值给变量a % 取余赋值 a%b,将a%b的值赋值给变量…

全面国产化之路-信创

概叙 信创&#xff0c;即信息技术应用创新产业&#xff0c;这个词儿最早来源于“信创工委会”&#xff08;全称是信息技术应用创新工作委员会&#xff09;&#xff0c;是在2016年由24家专业从事软硬件关键技术研究及应用的国内单位共同发起成立的一个非营利性社会组织。后…

qt+halcon实战

注意建QT工程项目用的是MSVC&#xff0c;如果选成MinGW,则会报错 INCLUDEPATH $$PWD/include INCLUDEPATH $$PWD/include/halconcppLIBS $$PWD/lib/x64-win64/halconcpp.lib LIBS $$PWD/lib/x64-win64/halcon.lib#include "halconcpp/HalconCpp.h" #include &quo…

一个漂亮的网站收藏函数

<!DOCTYPE html> <html lang="zh-CN"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>网站收藏</title><style>body …

会自动清除的文件——tempfile

原文链接&#xff1a;http://www.juzicode.com/python-tutorial-tempfile/ 在某些不需要持久保存文件的场景下&#xff0c;可以用tempfile模块生成临时文件或者文件夹&#xff0c;这些临时文件或者文件夹在使用完之后就会自动删除。 NamedTemporaryFile用来创建临时文件&…

Gradle学习-1

1、APK构建流程 2、Gradle的安装 &#xff08;1&#xff09;安装Java JDK JAVA JDK 下载地址下载安装后需要配置环境变量gradle是运行在Java虚拟机上的&#xff0c;所以需要配置Java JDK &#xff08;2&#xff09;安装 Gradle Gradle下载官网下载安装后需要配置环境变量 …

跨行业数据资产共享与协同:构建一体化数据共享平台,解锁数据资产潜力,促进多行业数据流通与深度应用,共创数字化转型新篇章,引领行业发展新趋势,开启智慧互联新纪元

一、引言 随着信息技术的飞速发展&#xff0c;数据已成为推动社会进步和经济发展的关键要素。然而&#xff0c;在传统行业领域&#xff0c;数据往往被限制在各自的“孤岛”中&#xff0c;难以实现跨行业的流通与共享。这不仅限制了数据的价值发挥&#xff0c;也阻碍了行业的创…

show/hide信号演示

代码&#xff1a; #include <gtk-2.0/gtk/gtk.h> #include <gtk-2.0/gdk/gdkkeysyms.h> #include <glib-2.0/glib.h> #include <stdio.h>gint delete_event(GtkWidget *window, GdkEvent *event, gpointer data) {gtk_widget_hide(window);return TRU…

Vue78-缓存路由组件

一、需求 路由切走的时候&#xff0c;组件会被销毁&#xff0c;路由切回来&#xff0c;组件被挂载&#xff01; 需要&#xff1a;路由切走的时候&#xff0c;组件不会被销毁。 二、代码实现 若是不加include属性&#xff0c;则在<router-view>里面展示的路由&#xff0c…

【一】【算法】经典树状数组和并查集,详细解析,初步认识,【模板】树状数组 1,树状数组并查集

【模板】树状数组 1 题目描述 如题&#xff0c;已知一个数列&#xff0c;你需要进行下面两种操作&#xff1a; 将某一个数加上 x x x 求出某区间每一个数的和 输入格式 第一行包含两个正整数 n , m n,m n,m&#xff0c;分别表示该数列数字的个数和操作的总个数。 第二…

webpack安装sass

package.json文件 {"devDependencies": {"sass-loader": "^7.2.0","sass": "^1.22.10","fibers": "^4.0.1"} }这个不用webpack.config.js module.exports {module: {rules: [{test: /\.s[ac]ss$/i,u…

日元预计明年开始上涨

被称为“日元先生”的前大藏省&#xff08;现财务省&#xff09;财务官榊原英资预测&#xff0c;美元兑日元汇率将在今年底或2025年初逐步升至130。他认为&#xff0c;通缩时代已经过去&#xff0c;通货膨胀即将来临。 《日本经济新闻》6月5日报道&#xff0c;日本财务省于5月3…

AI大眼萌探索 AI 新世界:Ollama 使用指南【1】

在人工智能的浪潮中&#xff0c;Ollama 的出现无疑为 Windows 用户带来了一场革命。这款工具平台以其开创性的功能&#xff0c;简化了 AI 模型的开发与应用&#xff0c;让每一位爱好者都能轻松驾驭 AI 的强大力量。大家好&#xff0c;我是AI大眼萌&#xff0c;今天我们将带大家…

全志 Android 11:实现响应全局按键

一、篇头 最近实现热键想功能&#xff0c;简单总结了下全志平台Android 11 的响应全局热键的方法。 二、需求 实现全局热键&#xff0c;响应F-、AF、F三个按键&#xff0c;AF只用于启动调焦界面&#xff0c;F-和F除了可以启动调焦界面外&#xff0c;还用于调整镜头的焦距&…

RN组件库 - Button 组件

从零构建 React Native 组件库&#xff0c;作为一个前端er~谁不想拥有一个自己的组件库呢 1、定义 Button 基本类型 type.ts import type {StyleProp, TextStyle, ViewProps} from react-native; import type {TouchableOpacityProps} from ../TouchableOpacity/type; import…

【活动】TSRC反爬虫专项正式启动!

活动时间 即日起 ~ 2024年7月5日 18:00 测试范围&#xff1a;微信公众号、腾讯新闻等 测试域名&#xff1a;mp.weixin.qq.com 微信公众号相关接口 1. 微信公众号文章列表 2. 历史文章 3. 文章详细内容 注&#xff1a;详情报名后公布。反爬虫专项将不定期上线新业务&#xf…

Java比较运算符

关系运算符和比较运算符适用于条件判断类型。 相当于布尔值&#xff0c;只有True和False两个 符号 说明ab,判断a的值是否等于b的值&#xff0c;条件成立为true,不成立为false ! a!b,判断a和b的值是否不相等&#xff0c;条件成立为true,不成立为false > …

【字符串 状态机动态规划】1320. 二指输入的的最小距离

本文涉及知识点 动态规划汇总 字符串 状态机动态规划 LeetCode1320. 二指输入的的最小距离 二指输入法定制键盘在 X-Y 平面上的布局如上图所示&#xff0c;其中每个大写英文字母都位于某个坐标处。 例如字母 A 位于坐标 (0,0)&#xff0c;字母 B 位于坐标 (0,1)&#xff0…