ShardingSphere水平表实现

sharding-jdbc-core

pom.xml

		<!-- Spring data Jpa -->
        <dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-jpa</artifactId>
		</dependency>
	    <!-- shardingsphere-jdbc -->
		<dependency>
		    <groupId>org.apache.shardingsphere</groupId>
		    <artifactId>sharding-jdbc-core</artifactId>
		    <version>4.1.1</version>
		</dependency>
		<dependency>
			<groupId>mysql</groupId>
			<artifactId>mysql-connector-java</artifactId>
		</dependency>
		<!-- druid -->
		<dependency>
			<groupId>com.alibaba</groupId>
			<artifactId>druid</artifactId>
			<version>1.1.20</version>
		</dependency>
		<!-- lombok -->
		<dependency>
		    <groupId>org.projectlombok</groupId>
		    <artifactId>lombok</artifactId>
		    <optional>true</optional>
		</dependency>

application.yml 

server:
  port: 8081
  servlet: 
   context-path: /
# Jpa配置
spring: 
  jpa:
    database: mysql
    show-sql: true

sharding:
    driverClassName: com.mysql.jdbc.Driver
    url: jdbc:mysql://localhost:3306/db1?useSSL=false&useUnicode=true&characterEncoding=UTF-8&serverTimezone=GMT%2B8
    username: root
    password: root

ShardingSphereProperties.java

@Data
@ConfigurationProperties(prefix = "sharding")
public class ShardingSphereProperties {

    private String driverClassName;

    private String url;

    private String username;

    private String password;

}

ShardingSphereConfig.java

@Configuration
@EnableConfigurationProperties(ShardingSphereProperties.class)
public class ShardingSphereConfig {

    @Autowired
    private ShardingSphereProperties properties;

    @Bean
    public DataSource getDate() throws SQLException {

        // 配置数据源
        Map<String, DataSource> dataSourceMap = new HashMap<>();

        // 配置第一个数据源
        DruidDataSource ds1 = new DruidDataSource();
        ds1.setDriverClassName(properties.getDriverClassName());
        ds1.setUsername(properties.getUsername());
        ds1.setUrl(properties.getUrl());
        ds1.setPassword(properties.getPassword());

        dataSourceMap.put("db1", ds1);

        // 配置第二个数据源
//        BasicDataSource ds2 = new BasicDataSource();
//        ds2.setDriverClassName("com.mysql.jdbc.Driver");
//        ds2.setUrl("jdbc:mysql://localhost:3306/ds1");
//        ds2.setUsername("root");
//        ds2.setPassword("");
//        dataSourceMap.put("test1", ds2);

        // 配置表规则 id取模分表
        // TableRuleConfiguration orderTableRuleConfig = new TableRuleConfiguration("user","db1.user${0..2}");
        // 配置表规则 按月份分表
        TableRuleConfiguration orderTableRuleConfig = new TableRuleConfiguration("user","db1.user0$->{1..9},db1.user1$->{0..2}");

        // 配置分库策略
        // orderTableRuleConfig.setDatabaseShardingStrategyConfig(new InlineShardingStrategyConfiguration("user_id", "ds${user_id % 2}"));
        // 分表策略 id取模分表
        // orderTableRuleConfig.setTableShardingStrategyConfig(new InlineShardingStrategyConfiguration("id", "user${id % 3}"));
        // 分表策略 按月份分表
        orderTableRuleConfig.setTableShardingStrategyConfig(new StandardShardingStrategyConfiguration("opt_time", new TableShardingAlgorithm()));
        // 配置分片规则
        ShardingRuleConfiguration shardingRuleConfig = new ShardingRuleConfiguration();
        shardingRuleConfig.getTableRuleConfigs().add(orderTableRuleConfig);

        // 省略配置order_item表规则...
        // ...

        // 获取数据源对象
        DataSource dataSource = ShardingDataSourceFactory.createDataSource(dataSourceMap, shardingRuleConfig, new Properties());
        return dataSource;
    }

}
TableShardingAlgorithm.java
public class TableShardingAlgorithm implements PreciseShardingAlgorithm<Date> {
    @Override
    public String doSharding(Collection<String> availableTargetNames, PreciseShardingValue<Date> shardingValue) {

        // 真实节点
        availableTargetNames.stream().forEach((item) -> {
            System.out.printf("actual node table:%s\n", item);
        });

        //精确分片
        String tb_name = shardingValue.getLogicTableName() + "";

        // 根据当前日期 来 分库分表
        Date date = shardingValue.getValue();
//        String year = String.format("%tY", date);
        String mon =String.valueOf(Integer.parseInt(String.format("%tm", date))); // 去掉前缀0
//        String dat = String.format("%td", date);

        // 选择表
        tb_name = tb_name + mon;
        System.out.printf("插入表:%s\n", tb_name);

        for (String each : availableTargetNames) {
            if (each.equals(tb_name)) {
                return each;
            }
        }

        throw new IllegalArgumentException();
    }
}

测试:

@Entity
@Data
public class User implements Serializable {

    private static final long serialVersionUID = 3302718101440706557L;

    @Id
     // 将当前主键的值单独保存到数据库的一张表里去,主键的值每次都是从该表中查询获得,适用于任何数据库,不必担心兼容问题
    @TableGenerator(
        name = "id", // 生成器名称
        table = "hibernate_sequences", // 指定表名
        pkColumnName = "sequence_name", // primary key column name表示在持久化表中,该主键生成策略所对应键的名称
        valueColumnName="next_val", //表示在持久化表中,该主键当前所生成的值 整型
        pkColumnValue="id",    //主键名称,这里直接用了表名
        allocationSize=1            //每次主键值增加的大小
    )
    @Column(name = "id")
    @GeneratedValue(strategy = GenerationType.TABLE, generator = "id")
    private Integer id;

    private String name;

    private boolean sex;

    private Integer age;

    private String data;

    private Date optTime;

    /**
     * 虚拟列,不保存
     */
    @Transient
    private String hobby;
}


@RequestMapping(value="/user")
@RestController
public class UserController {

	@Autowired
	private UserRepository repository;
	
	@RequestMapping(value="/save")
	public User save(@RequestBody User user) {
	    user.setOptTime(new Date());
		return repository.save(user);
	}
	
	@GetMapping(value="/get/{id}")
	public User get(@PathVariable Integer id) {
		Optional<User> user = repository.findById(id);
		if(user.isPresent()) {
			return user.get();
		}
		return null;
	}
}

// Dao
public interface UserRepository extends CrudRepository<User, Integer> {
}

测试save  控制台打印 

Hibernate: select tbl.next_val from hibernate_sequences tbl where tbl.sequence_name=? for update
Hibernate: update hibernate_sequences set next_val=?  where next_val=? and sequence_name=?
Hibernate: insert into user (address, age, amount, data, name, opt_time, opt_user, sex, upd_time, upd_user, id) values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
actual node table:user01
actual node table:user02
actual node table:user03
actual node table:user04
actual node table:user05
actual node table:user06
actual node table:user07
actual node table:user08
actual node table:user09
actual node table:user10
actual node table:user11
actual node table:user12
插入表:user10

sharding-jdbc-spring-boot-starter

pom改为

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

yml文件配置:然后就可以啦,日期分表需要添加分表策略类

server.port=9082

spring.shardingsphere.datasource.names=db1

spring.shardingsphere.datasource.db1.type=com.alibaba.druid.pool.DruidDataSource
spring.shardingsphere.datasource.db1.driver-class-name=com.mysql.jdbc.Driver
spring.shardingsphere.datasource.db1.url=jdbc:mysql://localhost:3306/db1?zeroDateTimeBehavior=convertToNull&useUnicode=true&characterEncoding=utf-8
spring.shardingsphere.datasource.db1.username=root
spring.shardingsphere.datasource.db1.password=root

# 分表策略
spring.shardingsphere.sharding.tables.user.actual-data-nodes=db1.user0$->{1..9},db1.user1$->{0..2}
# 分库分片健      database-strategy 数据库策略
#spring.shardingsphere.sharding.tables.t_order.database-strategy.standard.sharding-column=order_id
#spring.shardingsphere.sharding.tables.t_order.database-strategy.standard.precise-algorithm-class-name=com.boke.order.sharding.time.DBShardingAlgorithm
# 分表
#spring.shardingsphere.sharding.tables.user.table-strategy.inline.sharding-column=opt_time
#spring.shardingsphere.sharding.tables.user.table-strategy.inline.algorithm-expression=user$->{opt_time[5..6]}
spring.shardingsphere.sharding.tables.user.table-strategy.standard.sharding-column=opt_time
spring.shardingsphere.sharding.tables.user.table-strategy.standard.preciseAlgorithmClassName=com.zhu.config.TableShardingAlgorithm


# 配置id生成策略
# spring.shardingsphere.sharding.tables.user.key-generator.column=id
# spring.shardingsphere.sharding.tables.user.key-generator.type=SNOWFLAKE
# spring.shardingsphere.sharding.binding-tables=user

#spring.jpa.database=mysql
#spring.jpa.show-sql=true





  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

xiha_zhu

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值