# Sharding-JDBC
Sharding-JDBC 是当当网研发的开源分布式数据库中间件,从3.0开始Sharding-JDBC被包含在Sharding-Sphere中,之后该项目进入进入Apache孵化器,4.0版本之后的版本为Apache版本。
Sharding-JDBC的核心功能为数据分片和读写分离,通过 Sharding-JDBC ,应用可以透明的使用 JDBC 访问已经分库分表、读写分离的多个数据源而不用送心数据源的数量以及数据如何分布。
- 适用于任何基于 Java 的 ORM 框架,如:Hibernate,Mybatis,Spring JDBC Template或直接使用 JDBC。
- 基于任何第三方的数据库连接池,如:DBCP,C3PO,BoneCP,Druid,HikariCP 等。
- 支持任意实现DBC规范的数据库。目前支持MySQL,Oracle,SQLServer和 PostgreSQL。
# 项目
- ShardingSphere-JDBC 轻量级Java框架
- ShardingSphere-Proxy 数据库代理
- ShardingSphere-Sidecar(规划中) Kubernetes的云原生数据库代理
# 分表方式
- 垂直分表
- 垂直分库
- 水平分表
- 水平分库
# 垂直分表
将一个表常用的字段和不常用的进行拆分(将常用的字段放到一个表,不常用的放到另一个表中),就是垂直分表
# 垂直分库
垂直分库是指按照业务将表进行分类,分布到不同的数据库上面,每个库可以放在不同的服务器上,它的核心理念是专库专用。
# 水平分库
水平分库是把同一个表的数据按一定规则拆到不同的数据库中,每个库可以放在不同的服务器上。
对比
垂直分库是把不同表拆到不同数据库中,它是对数据行的拆分,不影响表结构
# 水平分表
水平分表是在同一个数据库内,把同一个表的数据按一定规则拆到多个表中,将分库的多个表,按照一定规则插入,如id值为基数则插入1表,偶数插入2表
# 安装
# maven
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.28</version>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.0.0</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.1.16</version>
</dependency>
<dependency>
<groupId>org.apache.shardingsphere</groupId>
<artifactId>sharding-jdbc-spring-boot-starter</artifactId>
<version>4.0.0-RC1</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.1.0</version>
</dependency>
# 简单运行
# properties
mybatis.configuration.map-underscore-to-camel-case=true
spring.main.allow-bean-definition-overriding=true
logging.level.org.springframework.web=info
logging.level.com.g.shardingjdbc=debug
logging.level.druid.sql=debug
logging.level.org.springframework.boot=debug
#sharding-jdbc 配置
#数据源名称
spring.shardingsphere.datasource.names=m1
#连接池(上面名称叫啥这里就要写啥 m1 就写m1)
spring.shardingsphere.datasource.m1.type=com.alibaba.druid.pool.DruidDataSource
spring.shardingsphere.datasource.m1.driver-class-name=com.mysql.cj.jdbc.Driver
spring.shardingsphere.datasource.m1.url=jdbc:mysql://localhost:3306/order_db?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true&rewriteBatchedStatements=true
spring.shardingsphere.datasource.m1.username=root
spring.shardingsphere.datasource.m1.password=root
#数据分布情况,数据节点
#t_order可以任意,但是在SQL插入的时候就要跟这里对应
spring.shardingsphere.sharding.tables.t_order.actual-data-nodes=m1.t_order_$->{1..2}
#指定t_order表的主键生成策略为SNOWFLAKE
spring.shardingsphere.sharding.tables.t_order.key-generator.column=order_id
spring.shardingsphere.sharding.tables.t_order.key-generator.type=SNOWFLAKE
# 指定t_order表的分片策略,分片策略包括分片和分片算法
spring.shardingsphere.sharding.tables.t_order.table-strategy.inline.sharding-column=order_id
spring.shardingsphere.sharding.tables.t_order.table-strategy.inline.algorithm-expression=t_order_$->{order_id % 2 + 1}
# yaml
spring:
main:
allow-bean-definition-overriding: true
shardingsphere:
datasource:
names: m1
m1:
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/order_db?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true&rewriteBatchedStatements=true
username: root
password: root
sharding:
tables:
t_order:
actual-data-nodes: m1.t_order_$->{1..2}
key-generator:
column: order_id
type: SNOWFLAKE
table-strategy:
inline:
sharding-column: order_id
algorithm-expression: t_order_$->{order_id % 2 + 1}
mybatis:
configuration:
map-underscore-to-camel-case: true
mapper-locations: mapper/*.xml
# 表
DROP TABLE IF EXISTS `t_order_1`;
CREATE TABLE `t_order_1` (
`order_id` bigint NOT NULL COMMENT '订单id',
`price` decimal(10, 2) NOT NULL COMMENT '订单价格',
`user_id` bigint NOT NULL COMMENT '下单用户id',
`status` varchar(50) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '订单状态',
PRIMARY KEY (`order_id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = DYNAMIC;
# 执行sql
@Repository
@Mapper
public interface TOrderMapper {
@Insert("insert into t_order(price,user_id,status) values(1,1,1)")
int insert();
}
# 总结
最终这个数据会进入t_order_2中,因为他取模+1后的数值是偶数