SpringBoot 整合 ShardingSphere

前言

ShardingSphere是一套开源的分布式数据库中间件解决方案组成的生态圈,它由Sharding-JDBC、Sharding-Proxy和Sharding-Sidecar(计划中)这3款相互独立的产品组成。 他们均提供标准化的数据分片、分布式事务和数据库治理功能,可适用于如Java同构、异构语言、容器、云原生等各种多样化的应用场景。

POM依赖

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.7.4</version>
    </parent>
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>3.3.1</version>
        </dependency>
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>druid-spring-boot-starter</artifactId>
            <version>1.2.11</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/org.apache.com.xiaobai.shardingsphere/sharding-jdbc-spring-boot-starter -->
        <dependency>
            <groupId>org.apache.shardingsphere</groupId>
            <artifactId>sharding-jdbc-spring-boot-starter</artifactId>
            <version>4.1.1</version>
        </dependency>

移除Drud自动配置

@SpringBootApplication(exclude = DruidDataSourceAutoConfigure.class )
public class ShardingsphereApplication {
    public static void main(String[] args) {
        SpringApplication.run(ShardingsphereApplication.class, args);
    }
}

水平分表

创建数据库lg_order,建表语句

-- ----------------------------
-- Table structure for pay_order_1
-- ----------------------------
DROP TABLE IF EXISTS `pay_order_1`;
CREATE TABLE `pay_order_1`  (
  `order_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NULL DEFAULT NULL,
  `product_name` varchar(128) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  `count` int(11) NULL DEFAULT NULL,
  PRIMARY KEY (`order_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

-- ----------------------------
-- Table structure for pay_order_2
-- ----------------------------
DROP TABLE IF EXISTS `pay_order_2`;
CREATE TABLE `pay_order_2`  (
  `order_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NULL DEFAULT NULL,
  `product_name` varchar(128) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  `count` int(11) NULL DEFAULT NULL,
  PRIMARY KEY (`order_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

配置代码

mybatis:
  configuration:
    map-underscore-to-camel-case: true
server:
  servlet:
    context-path: /
    encoding:
      charset: UTF-8
      enabled: true
      force: true
spring:
  application:
    description: 水平分表 (单库)
    name: sharding-jdbc-one
  main:
    allow-bean-definition-overriding: true
  shardingsphere:
    datasource:
      db1:
        driver-class-name: com.mysql.cj.jdbc.Driver
        password: 123456;a
        type: com.alibaba.druid.pool.DruidDataSource
        url: jdbc:mysql://localhost:3306/lg_order?characterEncoding=UTF-8&useSSL=false
        username: root
      names: db1
    props:
      sql:
        show: true
    sharding:
      tables:
        pay_order:
          actual-data-nodes: db1.pay_order_$->{1..2}
          key-generator:
            type: SNOWFLAKE
            column: order_id
          tablestrategy:
            inline:
              algorithm-expression: pay_order_$->{order_id % 2 + 1}
              sharding-column: order_id

编写Mapper

@Component
@Mapper
public interface OrderMapper {
    @Insert("insert into pay_order(user_id,product_name,count) values(#{userId},#{productName},#{count})")
    Long insert(OrderVO orderVO);

    /**
     * 查询订单
     */
    @Select({"<script>" +
            "select * from pay_order p where p.order_id in " +
            "<foreach collection='orderIds' item='id' open='(' separator=',' close=')'>#{id}</foreach>" +
            "limit 1" +
            "</script>"})
    List<Map<String, Object>> findOrderByIds(@Param("orderIds") List<Long> orderIds);

    /**
     * 查询订单
     */
    @Select("select * from pay_order order by user_id asc")
    List<Map<String, Object>> list();
}

测试

@SpringBootTest()
public class OrderServiceTest {

    @Autowired
    private OrderMapper orderMapper;

    @Test
    public void test1() {
        for (long i = 11; i < 20; i++) {
            OrderVO orderVO = new OrderVO();
            orderVO.setCount(1);
            orderVO.setUserId(i);
            orderVO.setProductName("产品" + i);

            orderMapper.insert(orderVO);
        }
    }

    @Test
    public void test2() {
        List<Long> ids = List.of(786541544898297857L,786541545091235841L,786541544923463680L);
        System.out.println(JSON.toJSONString(orderMapper.findOrderByIds(ids)));
    }

    @Test
    public void test3() {
        System.out.println(JSON.toJSONString(orderMapper.list()));
    }
}

insert结果

水平分库

创建数据库lg_order1, lg_order2

-- ----------------------------
-- Table structure for pay_order_1
-- ----------------------------
DROP TABLE IF EXISTS `pay_order_1`;
CREATE TABLE `pay_order_1`  (
  `order_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NULL DEFAULT NULL,
  `product_name` varchar(128) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  `count` int(11) NULL DEFAULT NULL,
  PRIMARY KEY (`order_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

-- ----------------------------
-- Table structure for pay_order_2
-- ----------------------------
DROP TABLE IF EXISTS `pay_order_2`;
CREATE TABLE `pay_order_2`  (
  `order_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NULL DEFAULT NULL,
  `product_name` varchar(128) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL,
  `count` int(11) NULL DEFAULT NULL,
  PRIMARY KEY (`order_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

配置代码

mybatis:
  configuration:
    map-underscore-to-camel-case: true
server:
  servlet:
    context-path: /
    encoding:
      charset: UTF-8
      enabled: true
      force: true
spring:
  application:
    description: 水平分库
    name: sharding-jdbc-two
  main:
    allow-bean-definition-overriding: true
  shardingsphere:
    datasource:
      db1:
        driver-class-name: com.mysql.cj.jdbc.Driver
        password: 123456;a
        type: com.alibaba.druid.pool.DruidDataSource
        url: jdbc:mysql://localhost:3306/lg_order_1?characterEncoding=UTF-8&useSSL=false
        username: root
      db2:
        driver-class-name: com.mysql.cj.jdbc.Driver
        password: 123456;a
        type: com.alibaba.druid.pool.DruidDataSource
        url: jdbc:mysql://localhost:3306/lg_order_2?characterEncoding=UTF-8&useSSL=false
        username: root
      names: db1,db2
    props:
      sql:
        show: true
    sharding:
      tables:
        pay_order:
          databasestrategy:
            inline:
              algorithm-expression: db$->{user_id % 2 + 1}
              sharding-column: user_id
          actual-data-nodes: db$->{1..2}.pay_order_$->{1..2}
          key-generator:
            type: SNOWFLAKE
            column: order_id
          tablestrategy:
            inline:
              algorithm-expression: pay_order_$->{order_id % 2 + 1}
              sharding-column: order_id

测试

@SpringBootTest()
public class OrderServiceTest {

    @Autowired
    private OrderMapper orderMapper;

    @Test
    public void test1() {
        for (long i = 11; i < 20; i++) {
            OrderVO orderVO = new OrderVO();
            orderVO.setCount(1);
            orderVO.setUserId(i);
            orderVO.setProductName("产品" + i);

            orderMapper.insert(orderVO);
        }
    }

    @Test
    public void test2() {
        List<Long> ids = List.of(786541544898297857L,786541545091235841L,786541544923463680L);
        System.out.println(JSON.toJSONString(orderMapper.findOrderByIds(ids)));
    }

    @Test
    public void test3() {
        System.out.println(JSON.toJSONString(orderMapper.list()));
    }
}

insert 结果

写累了,,,后面再写

posted @ 2022-10-13 16:32  小白不爱  阅读(1749)  评论(0编辑  收藏  举报