目录
[6.1 连接与驱动](#6.1 连接与驱动)
[6.2 事务处理](#6.2 事务处理)
[6.3 主键与自增ID](#6.3 主键与自增ID)
[6.4 SQL 编写与优化](#6.4 SQL 编写与优化)
1、概念
定位: 一个开源的、分布式、NewSQL 数据库。它不仅在处理海量数据和高并发请求时表现出色,还因其对 MySQL 生态的良好兼容性,吸引了大量开发者和企业。
-
对比 OldSQL (如 MySQL): 解决了单机容量瓶颈、性能瓶颈和高可用问题。
-
对比 NoSQL (如 MongoDB/Cassandra): 提供了完整的 ACID 事务支持(特别是跨行跨表事务)和熟悉的 SQL 接口。
2、核心特性
| 核心特性 | 具体描述 |
|---|---|
| 🔧 MySQL 兼容 | 高度兼容 MySQL 协议和常用功能,迁移成本低 |
| 🚀 水平扩缩容 | 存储与计算分离架构,支持在线、弹性扩缩容,对业务透明 |
| 💾 金融级高可用 | 数据多副本 + Multi-Raft 协议,保障数据强一致性与高可用 |
| 📊 实时 HTAP | 同时支持 OLTP (行存 TiKV) 与 OLAP (列存 TiFlash),一份数据两种体验 |
| ☁️ 云原生 | 通过 TiDB Operator 可在 Kubernetes 上实现自动化部署和管理 |
3、核心架构
TiDB 的强大能力源于其独特的模块化分布式架构,主要由三个核心组件协同工作:
| 组件名称 | 核心职责 | 角色比喻 |
|---|---|---|
| TiDB Server | 无状态的 SQL 计算层,负责接收 SQL 请求、进行解析、优化并生成分布式执行计划。 | 餐厅的 服务员,负责接收订单并翻译给后厨。 |
| TiKV Server | 分布式的 行式存储引擎 ,负责持久化存储数据本身。分布式、强一致的 Key-Value 存储引擎。数据以 Region 为单位自动分片和调度。它使用 Raft 协议保证数据的一致性和高可用。默认数据三副本,确保数据安全。 | 餐厅的 热菜区,高效处理点餐、加菜等即时操作。 |
| PD Server | 集群的 元信息管理模块 与 调度中枢。整个集群的"大脑"。负责元数据管理、调度 Region(如负载均衡、故障恢复),以及分配全局唯一且递增的 RowID。 | 餐厅的 经理,掌握所有资源信息,进行全局协调与调度。 |
| TiFlash Server | 列式存储引擎 ,它是 TiKV 的补充。它通过 Multi-Raft Learner 协议实时从 TiKV 复制数据,确保行存与列存之间的数据强一致,从而支持实时分析场景。 | 餐厅的 冷盘/数据分析区,专门处理复杂的统计报表类请求。 |
在功能上,TiDB 支持分布式事务 ,默认提供快照隔离(SI)级别,确保 ACID 特性。同时,它也支持在线 DDL,即对表结构进行变更时(如增加索引),不会阻塞数据的读写操作。在 SQL 支持方面,TiDB 兼容 MySQL 5.7 协议和常用的功能,包括常见的 DDL、DML 语句、视图以及分区表等。
4、主要限制
-
SQL 功能支持 :目前,TiDB 不支持存储过程、自定义函数和触发器。如果现有应用严重依赖这些功能,迁移到 TiDB 可能需要改造应用。
-
资源开销:由于是分布式架构,TiDB 自身的管理(如多副本数据同步、Raft 协议通信)会带来额外的资源开销。
-
适用数据规模 :TiDB 的设计初衷是解决大规模数据场景的问题。如果数据量在千万行以下,且没有高可用、强一致性或多数据中心复制等要求,使用 TiDB 可能无法充分发挥其优势,单机 MySQL 或许是更经济的选择。
-
其他限制:TiDB 中默认单行大小不超过 6 MB(可调整至最大 120 MB),用户名最长为 32 个字符。
5、应用场景
-
对数据一致性及高可用性要求极高的场景 :例如金融行业 的核心业务系统。TiDB 通过多副本和 Multi-Raft 协议,能够将数据调度到不同的机房、机架和机器,实现 RPO(恢复点目标)= 0 和 RTO(恢复时间目标)≤ 30 秒的金融级高可用。
-
数据量巨大和高并发的 OLTP 场景 :当业务快速增长,单机 MySQL 在容量或并发处理上遇到瓶颈,又不想忍受分库分表带来的开发复杂度时,TiDB 可以无缝替换,提供近乎无限的水平和伸缩能力 。只需要把它当成一个逻辑上的 MySQL 来用。数据会自动、均匀地分布在整个集群中。扩容?直接在集群里加新节点,TiDB 会自动完成数据重平衡,对业务完全透明,真正实现了弹性伸缩。
-
实时 HTAP 场景 :如果业务需要在同一份数据上同时进行实时交易和实时数据分析 ,TiDB 的 TiKV(行存)和 TiFlash(列存)组合可以提供一站式解决方案,省去传统的 ETL 过程,极大提升数据分析的实时性。借助 TiFlash,业务可以直接在同一个数据库上执行复杂的分析查询,而无需将数据异步同步到专用的分析系统(如 ClickHouse 或 Doris),实现了 T+0 的实时数据分析 。
-
数据汇聚和报表处理:当企业需要将分散在各个业务系统的数据汇聚起来,进行 T+0 或 T+1 的报表生成和二次加工时,TiDB 可以作为一个统一的数据平台,通过 SQL 直接生成报表,架构远比传统的 Hadoop 体系简单。
6、Java交互
6.1 连接与驱动
-
驱动选择: 直接使用 MySQL 官方 JDBC 驱动 (
mysql-connector-java) 即可。 -
连接字符串: 由于 TiDB Server 是无状态的,连接字符串应该配置多个 TiDB 节点的地址,以实现负载均衡和故障转移。
java
// 示例:在连接字符串中配置多个TiDB实例
String url = "jdbc:mysql://tidb-host1:4000,tidb-host2:4000/testdb?loadBalanceAutoCommitStatementThreshold=5&...";
- 连接池: 强烈推荐使用连接池,如 HikariCP。配置方式和连接 MySQL 时完全相同。
6.2 事务处理
-
乐观事务是主流: TiDB 默认使用乐观锁 机制。这意味着在事务提交时才会检测冲突。如果两个事务修改了同一行数据,后提交的事务会失败(返回
MySQLTransactionRollbackException)。 -
对代码的影响:
- 代码必须能够处理事务提交失败的情况,并准备好重试逻辑。
java
int maxRetries = 3;
for (int i = 0; i < maxRetries; i++) {
try {
// 执行你的业务逻辑
updateAccountBalance(connection, accountId, amount);
connection.commit();
break; // 成功则跳出循环
} catch (MySQLTransactionRollbackException e) {
if (i == maxRetries - 1) {
throw e; // 重试次数用尽,抛出异常
}
// 可选:回滚后等待一小段时间再重试
Thread.sleep(50);
} catch (Exception e) {
connection.rollback();
throw e; // 非乐观锁冲突异常,直接抛出
}
}
-
悲观事务(备选): 从 v4.0 开始,TiDB 支持了完整的悲观事务模式。如果业务逻辑严重依赖
SELECT ... FOR UPDATE或者难以处理乐观锁的重试,可以切换到悲观模式。- 在会话或全局级别设置:
SET tidb_txn_mode = 'pessimistic';
- 在会话或全局级别设置:
6.3 主键与自增ID
-
必须显式定义主键: TiDB 强烈建议为每张表都定义一个显式的主键。主键最好是单调递增的,这有利于数据在 TiKV 中顺序写入,避免写热点。
-
自增ID (
AUTO_INCREMENT):-
TiDB 保证自增ID的唯一性,但不保证连续性和单调递增(在高并发批量插入时,可能会一次性分配一个ID段,导致ID不连续)。
-
如果业务不能接受ID不连续,可以考虑使用
AUTO_RANDOM主键(适用于分布式场景)或者使用类似雪花算法的业务逻辑生成唯一ID。
-
6.4 SQL 编写与优化
虽然语法兼容,但因为底层是分布式架构,写 SQL 时需要有分布式思维。
-
避免或优化大事务: 一个事务修改的数据量过大会导致内存压力和性能问题。TiDB 对单个事务的大小有限制(默认
txn-total-size-limit为 100MB)。 -
使用索引: 和单机数据库一样,索引至关重要。Explain 是你的好朋友,一定要学会看 TiDB 的执行计划。
-
热点问题:
-
写入热点: 如果所有数据都集中在最新的一个 Region 上(比如使用
AUTO_INCREMENT主键且时间戳作为主键的一部分),会造成写入热点。使用SHARD_ROW_ID_BITS或AUTO_RANDOM可以打散热点。或者使用业务分片键(格式: {shard}{timestamp}{seq}) -
读取热点: 频繁查询少量数据也可能导致热点。
-
在TiDB中,数据被分割成多个Region(默认约96MB-144MB),每个Region负责一个连续的数据范围。数据根据主键的字典序排列分布到不同Region。
AUTO_INCREMENT生成的ID是严格递增的,由于数据按主键排序,所有新写入都集中在最后一个Region,形成"尾部热点"。
SHARD_ROW_ID_BITS:
用于没有显式定义主键的表,TiDB会自动生成一个
_tidb_rowid作为隐式主键
SHARD_ROW_ID_BITS将这个隐式RowID的高位进行分片
sql-- 创建表时启用分片 CREATE TABLE events ( content TEXT, created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ) SHARD_ROW_ID_BITS = 4; -- 使用4个bit进行分片,产生16个分片分片机制:
4个bit = 2⁴ = 16个分片
TiDB会在RowID的高位插入随机bit,将连续写入分散到16个不同的数据范围
效果:
写入压力从1个Region分散到16个Region
提升了写入并发能力
AUTO_RANDOM:
专门为解决自增主键热点问题设计的特性
在保证主键全局唯一的前提下,引入随机性分散写入
java-- 使用AUTO_RANDOM代替AUTO_INCREMENT CREATE TABLE order_events ( id BIGINT AUTO_RANDOM PRIMARY KEY, -- 使用AUTO_RANDOM event_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP, data VARCHAR(500) ); -- 或者对现有表修改 ALTER TABLE order_events MODIFY id BIGINT AUTO_RANDOM;AUTO_RANDOM的二进制结构:[随机位(5bit)][自增序列位(59bit)]
优势:
保持全局唯一性
写入分散到多个Region
向后兼容,应用几乎无需修改
业务分片键:
sql-- 使用业务分片键 CREATE TABLE orders ( order_id VARCHAR(64) PRIMARY KEY, -- 格式: {shard}_{timestamp}_{seq} user_id BIGINT, amount DECIMAL(10,2), created_at TIMESTAMP ); -- 示例订单ID: "U23_20240120120000_001", "U47_20240120120001_002" -- 其中U23、U47是用户ID的hash分片
7、生态与监控
-
监控与告警: TiDB 内置了基于 Grafana + Prometheus 的完整监控体系。需要能看懂监控大盘,比如 QPS、延迟、连接数、SQL 执行时间等,以便快速定位性能瓶颈。
-
数据迁移工具:
-
TiDB Data Migration (DM): 用于从 MySQL 等数据库实时同步数据到 TiDB。
-
Dumpling & Lightning: 全量数据导出和导入工具(逻辑备份/恢复)。
-
BR: 物理备份恢复工具,更快。
-
-
数据库管理工具:
-
TiUP: TiDB 的集群管理工具,用于部署、升级、扩缩容。
-
TiDB Dashboard: 内置于 TiDB 的 Web GUI,用于集群诊断和性能分析。
-