Skip to content

Commit 5120886

Browse files
tangentasre-bot
authored andcommitted
cherry pick pingcap#3193 to release-3.0
Signed-off-by: sre-bot <sre-bot@pingcap.com>
1 parent 7cfa2ed commit 5120886

File tree

2 files changed

+273
-86
lines changed

2 files changed

+273
-86
lines changed

auto-random.md

Lines changed: 152 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,152 @@
1+
---
2+
title: AUTO_RANDOM
3+
category: reference
4+
summary: 本文介绍了 TiDB 的 `AUTO_RANDOM` 列属性。
5+
aliases: ['/docs-cn/dev/reference/sql/attributes/auto-random/']
6+
---
7+
8+
# AUTO_RANDOM <span class="version-mark">从 v3.1.0 版本开始引入</span>
9+
10+
> **警告:**
11+
>
12+
> 当前 `AUTO_RANDOM` 属性为实验功能,**不建议在生产环境中使用**。在后续版本中,`AUTO_RANDOM` 的语法或语义可能会变化。
13+
14+
使用 `AUTO_RANDOM` 功能前,须在 TiDB 配置文件 `experimental` 部分设置 `allow-auto-random = true`。该参数详情可参见 [`allow-auto-random`](/tidb-configuration-file.md#allow-auto-random)
15+
16+
## 使用场景
17+
18+
`AUTO_RANDOM` 用于解决大批量写数据入 TiDB 时因含有**整型自增主键列**的表而产生的热点问题。详情参阅 [TiDB 高并发写入场景最佳实践](/best-practices/high-concurrency-best-practices.md)
19+
20+
以下面语句建立的表为例:
21+
22+
```sql
23+
create table t (a bigint primary key auto_increment, b varchar(255))
24+
```
25+
26+
在以上语句所建的表上执行大量未指定主键值的 `INSERT` 语句,示例如下:
27+
28+
```sql
29+
insert into t(b) values ('a'), ('b'), ('c')
30+
```
31+
32+
如以上语句,由于未指定主键列的值(`a` 列),TiDB 会使用连续自增的行值作为行 ID,可能导致单个 TiKV 节点上产生写入热点,进而影响对外提供服务的性能。要避免这种性能下降,可以在执行建表语句时为 `a` 列指定 `AUTO_RANDOM` 属性而不是 `AUTO_INCREMENT` 属性。示例如下:
33+
34+
{{< copyable "sql" >}}
35+
36+
```sql
37+
create table t (a bigint primary key auto_random, b varchar(255))
38+
```
39+
40+
或者
41+
42+
{{< copyable "sql" >}}
43+
44+
```sql
45+
create table t (a bigint auto_random, b varchar(255), primary key (a))
46+
```
47+
48+
此时再执行形如 `INSERT INTO t(b) values...``INSERT` 语句。
49+
50+
+ 隐式分配:如果该 `INSERT` 语句没有指定整型主键列(`a` 列)的值,或者指定为 `NULL`,TiDB 会为该列自动分配值。该值不保证自增,不保证连续,只保证唯一,避免了连续的行 ID 带来的热点问题。
51+
+ 显式插入:如果该 `INSERT` 语句显式指定了整型主键列的值,和 `AUTO_INCREMENT` 属性类似,TiDB 会保存该值。注意,如果未在系统变量 `@@sql_mode` 中设置 `NO_AUTO_VALUE_ON_ZERO`, 即使显式指定整型主键列的值为 `0`,TiDB 也会为该列自动分配值。
52+
53+
自动分配值的计算方式如下:
54+
55+
该行值在二进制形式下,除去符号位的最高五位(称为 shard bits)由当前事务的开始时间决定,剩下的位数按照自增的顺序分配。
56+
57+
若要使用一个不同的 shard bits 的数量,可以在 `AUTO_RANDOM` 后面加一对括号,并在括号中指定想要的 shard bits 数量。示例如下:
58+
59+
{{< copyable "sql" >}}
60+
61+
```sql
62+
create table t (a bigint primary key auto_random(3), b varchar(255))
63+
```
64+
65+
以上建表语句中,shard bits 的数量为 `3`。shard bits 的数量的取值范围是 `[1, field_max_bits)`,其中 `field_max_bits` 为整型主键列类型占用的位长度。
66+
67+
创建完表后,使用 `SHOW WARNINGS` 可以查看当前表可支持的最大隐式分配的次数:
68+
69+
{{< copyable "sql" >}}
70+
71+
```sql
72+
show warnings
73+
```
74+
75+
```
76+
+-------+------+----------------------------------------------------------+
77+
| Level | Code | Message |
78+
+-------+------+----------------------------------------------------------+
79+
| Note | 1105 | Available implicit allocation times: 1152921504606846976 |
80+
+-------+------+----------------------------------------------------------+
81+
82+
```
83+
84+
> **警告:**
85+
>
86+
> 建议用户使用 `bigint` 作为 `AUTO_RANDOM` 列类型,以获得最大的可隐式分配次数。
87+
88+
另外,要查看某张含有 `AUTO_RANDOM` 属性的表的 shard bits 数量,可以在系统表 `information_schema.tables``TIDB_ROW_ID_SHARDING_INFO` 一列看到模式为 `PK_AUTO_RANDOM_BITS=x` 的值,其中 `x` 为 shard bits 的数量。
89+
90+
`AUTO RANDOM` 列隐式分配的值会影响 `last_insert_id()`。可以使用 `select last_insert_id()` 获取上一次 TiDB 隐式分配的 ID,例如:
91+
92+
{{< copyable "sql" >}}
93+
94+
```sql
95+
insert into t (b) values ("b")
96+
select * from t;
97+
select last_insert_id()
98+
```
99+
100+
可能得到的结果如下:
101+
102+
```
103+
+------------+---+
104+
| a | b |
105+
+------------+---+
106+
| 1073741825 | b |
107+
+------------+---+
108+
109+
+------------------+
110+
| last_insert_id() |
111+
+------------------+
112+
| 1073741825 |
113+
+------------------+
114+
```
115+
116+
## 兼容性
117+
118+
TiDB 支持解析版本注释语法。示例如下:
119+
120+
{{< copyable "sql" >}}
121+
122+
```sql
123+
create table t (a bigint primary key /*T![auto_rand] auto_random */)
124+
```
125+
126+
{{< copyable "sql" >}}
127+
128+
```sql
129+
create table t (a bigint primary key auto_random)
130+
```
131+
132+
以上两个语句含义相同。
133+
134+
`show create table` 的结果中,`AUTO_RANDOM` 属性会被注释掉。注释会附带一个特性标识符,例如 `/*T![auto_rand] auto_random */`。其中 `auto_rand` 表示 `AUTO_RANDOM` 的特性标识符,只有实现了该标识符对应特性的 TiDB 版本才能够正常解析 SQL 语句片段。
135+
136+
该功能支持向前兼容,即降级兼容。没有实现对应特性的 TiDB 版本则会忽略表(带有上述注释)的 `AUTO_RANDOM` 属性,因此能够使用含有该属性的表。
137+
138+
## 使用限制
139+
140+
目前在 TiDB 中使用 `AUTO_RANDOM` 有以下限制:
141+
142+
- 该属性必须指定在整数类型的主键列上,否则会报错。例外情况见[关于 `alter-primary-key` 配置项的说明](#关于-alter-primary-key-配置项的说明)
143+
- 不支持使用 `ALTER TABLE` 来修改 `AUTO_RANDOM` 属性,包括添加或移除该属性。
144+
- 不支持修改含有 `AUTO_RANDOM` 属性的主键列的列类型。
145+
- 不支持与 `AUTO_INCREMENT` 同时指定在同一列上。
146+
- 不支持与列的默认值 `DEFAULT` 同时指定在同一列上。
147+
- 插入数据时,不建议自行显式指定含有 `AUTO_RANDOM` 列的值。不恰当地显式赋值,可能会导致该表提前耗尽用于自动分配的数值。
148+
149+
### 关于 `alter-primary-key` 配置项的说明
150+
151+
-`alter-primary-key = true` 时,即使是整型主键列,也不支持使用 `AUTO_RANDOM`
152+
- 配置文件中的 `alter-primary-key``allow-auto-random` 两个配置项的值不允许同时为 `true`

comment-syntax.md

Lines changed: 121 additions & 86 deletions
Original file line numberDiff line numberDiff line change
@@ -1,105 +1,122 @@
11
---
22
title: 注释语法
33
category: reference
4+
<<<<<<< HEAD
45
aliases: ['/docs-cn/v3.0/reference/sql/language-structure/comment-syntax/','/docs-cn/sql/comment-syntax/']
6+
=======
7+
summary: 本文介绍 TiDB 支持的注释语法。
8+
aliases: ['/docs-cn/dev/reference/sql/language-structure/comment-syntax/']
9+
>>>>>>> cd61a4c... update comment-syntax.md (#3193)
510
---
611

712
# 注释语法
813

9-
TiDB 支持三种注释风格:
10-
11-
*`#` 注释一行
12-
*`--` 注释一行,用 `--` 注释必须要在其之后留出至少一个空格。
13-
*`/* */` 注释一块,可以注释多行。
14-
15-
例:
16-
17-
{{< copyable "sql" >}}
18-
19-
```sql
20-
SELECT 1+1; # 注释文字
21-
```
22-
23-
```
24-
+------+
25-
| 1+1 |
26-
+------+
27-
| 2 |
28-
+------+
29-
1 row in set (0.00 sec)
30-
```
31-
32-
{{< copyable "sql" >}}
33-
34-
```sql
35-
SELECT 1+1; -- 注释文字
36-
```
37-
38-
```
39-
+------+
40-
| 1+1 |
41-
+------+
42-
| 2 |
43-
+------+
44-
1 row in set (0.00 sec)
45-
```
46-
47-
{{< copyable "sql" >}}
48-
49-
```sql
50-
SELECT 1 /* 这是行内注释文字 */ + 1;
51-
```
52-
53-
```
54-
+--------+
55-
| 1 + 1 |
56-
+--------+
57-
| 2 |
58-
+--------+
59-
1 row in set (0.01 sec)
60-
```
61-
62-
{{< copyable "sql" >}}
14+
本文档介绍 TiDB 支持的注释语法。
6315

64-
```sql
65-
SELECT 1+
66-
-> /*
67-
/*> 这是一条
68-
/*> 多行注释
69-
/*> */
70-
-> 1;
71-
```
16+
TiDB 支持三种注释风格:
7217

73-
```
74-
+-------+
75-
| 1+
76-
77-
1 |
78-
+-------+
79-
| 2 |
80-
+-------+
81-
1 row in set (0.00 sec)
82-
```
18+
*`#` 注释一行:
19+
20+
{{< copyable "sql" >}}
21+
22+
```sql
23+
SELECT 1+1; # 注释文字
24+
```
25+
26+
```
27+
+------+
28+
| 1+1 |
29+
+------+
30+
| 2 |
31+
+------+
32+
1 row in set (0.00 sec)
33+
```
34+
35+
*`--` 注释一行:
36+
37+
{{< copyable "sql" >}}
38+
39+
```sql
40+
SELECT 1+1; -- 注释文字
41+
```
42+
43+
```
44+
+------+
45+
| 1+1 |
46+
+------+
47+
| 2 |
48+
+------+
49+
1 row in set (0.00 sec)
50+
```
51+
52+
`--` 注释时,必须要在其之后留出至少一个空格,否则注释不生效:
53+
54+
{{< copyable "sql" >}}
55+
56+
```sql
57+
SELECT 1+1--1;
58+
```
59+
60+
```
61+
+--------+
62+
| 1+1--1 |
63+
+--------+
64+
| 3 |
65+
+--------+
66+
1 row in set (0.01 sec)
67+
```
68+
69+
*`/* */` 注释一块,可以注释多行:
70+
71+
{{< copyable "sql" >}}
72+
73+
```sql
74+
SELECT 1 /* 这是行内注释文字 */ + 1;
75+
```
76+
77+
```
78+
+--------+
79+
| 1 + 1 |
80+
+--------+
81+
| 2 |
82+
+--------+
83+
1 row in set (0.01 sec)
84+
```
85+
86+
{{< copyable "sql" >}}
87+
88+
```sql
89+
SELECT 1+
90+
-> /*
91+
/*> 这是一条
92+
/*> 多行注释
93+
/*> */
94+
-> 1;
95+
```
96+
97+
```
98+
+-------+
99+
| 1+
100+
101+
1 |
102+
+-------+
103+
| 2 |
104+
+-------+
105+
1 row in set (0.00 sec)
106+
```
107+
108+
## MySQL 兼容的注释语法
83109

84-
{{< copyable "sql" >}}
85-
86-
```sql
87-
SELECT 1+1--1;
88-
```
110+
TiDB 也跟 MySQL 保持一致,支持一种 C 风格注释的变体:
89111

90112
```
91-
+--------+
92-
| 1+1--1 |
93-
+--------+
94-
| 3 |
95-
+--------+
96-
1 row in set (0.01 sec)
113+
/*! Specific code */
97114
```
98115
99-
TiDB 也跟 MySQL 保持一致,支持一种 C 风格注释的变体:
116+
或者
100117
101118
```
102-
/*! Specific code */
119+
/*!50110 Specific code */
103120
```
104121
105122
在这种格式中,TiDB 会执行注释中的语句,这个语法是为了让这些 SQL 在其他的数据库中被忽略,而在 TiDB 中被执行。
@@ -108,7 +125,17 @@ TiDB 也跟 MySQL 保持一致,支持一种 C 风格注释的变体:
108125
109126
在 TiDB 中,这种写法等价于 `SELECT STRAIGHT_JOIN col1 FROM table1,table2 WHERE ...`
110127
128+
<<<<<<< HEAD
111129
如果注释中指定了 Server 版本号,例如 `/*!50110 KEY_BLOCK_SIZE=1024 */`,在 MySQL 中表示只有 MySQL 的版本大于等于 5.1.10 才会处理这个 comment 中的内容。但是在 TiDB 中,这个版本号不会起作用,所有的 comment 都会处理。
130+
=======
131+
如果注释中指定了 Server 版本号,例如 `/*!50110 KEY_BLOCK_SIZE=1024 */`,在 MySQL 中表示只有 MySQL 的版本大于等于 5.1.10 才会处理这个 comment 中的内容。但是在 TiDB 中,这个 MySQL 版本号不会起作用,所有的 comment 都被会处理。
132+
133+
## TiDB 可执行的注释语法
134+
135+
TiDB 也有独立的注释语法,称为 TiDB 可执行注释语法,格式为 `/*T![feature_id] XXX */`。只有在当前版本中实现了 `feature_id` 对应的功能特性的 TiDB,才会试图解析该注释里的 SQL 片段。例如 v3.1.1 中引入了 `AUTO_RANDOM` 特性,该版本能够将 `/*T![auto_rand] auto_random */` 解析为 `auto_random`;而 v3.0.0 中没有实现 `AUTO_RANDOM` 特性,则上述 SQL 语句片段会被忽略。
136+
137+
## 优化器注释语法
138+
>>>>>>> cd61a4c... update comment-syntax.md (#3193)
112139
113140
还有一种注释会被当做是优化器 Hint 特殊对待:
114141
@@ -118,8 +145,16 @@ TiDB 也跟 MySQL 保持一致,支持一种 C 风格注释的变体:
118145
SELECT /*+ hint */ FROM ...;
119146
```
120147

148+
<<<<<<< HEAD
121149
由于 hint 包含在类似 /*+ xxx */ 的 comment 里,MySQL 客户端在 5.7.7 之前,会默认把 comment 清除掉,如果需要在旧的客户端使用 hint,需要在启动客户端时加上 --comments 选项,例如 mysql -h 127.0.0.1 -P 4000 -uroot --comments
122150

123151
TiDB 支持的相关优化器 hint 详见 [Optimizer Hints](/optimizer-hints.md)
152+
=======
153+
TiDB 支持的相关优化器 hint 详见 [Optimizer Hints](/optimizer-hints.md)
154+
>>>>>>> cd61a4c... update comment-syntax.md (#3193)
155+
156+
> **注意**
157+
>
158+
> 由于 TiDB 可执行注释语法和优化器注释语法在 MySQL 客户端 5.7.7 之前的版本中,会被默认当成 comment 清除掉,如果需要在旧的客户端使用这两种语法,需要在启动客户端时加上 --comments 选项,例如 `mysql -h 127.0.0.1 -P 4000 -uroot --comments`
124159
125-
更多[细节](https://dev.mysql.com/doc/refman/5.7/en/comments.html)
160+
更多细节,请参考 [MySQL 文档](https://dev.mysql.com/doc/refman/5.7/en/comments.html)

0 commit comments

Comments
 (0)