From e91cb070efec01bc77e2e4942690ee706ef2c7bb Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 24 Jun 2020 13:10:55 +0800 Subject: [PATCH 01/38] Create View.md --- View.md | 193 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 193 insertions(+) create mode 100644 View.md diff --git a/View.md b/View.md new file mode 100644 index 0000000000000..0e162e5a152d1 --- /dev/null +++ b/View.md @@ -0,0 +1,193 @@ +# view + +TiDB supports views, A view acts as a virtual table, It can be created from SELECT statements. On the one hand, Using the view can only expose safe columns and data to the user, to ensure the security of sensitive columns and data in the underlying table. On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. + +## query views + +You can query a view in a similar way as you query an actual table. When the query is actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. + +## view metadata + +To obtain metadata about views: + +### use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement + +example: + +```sql +show create view v; +``` + +This statement shows the `CREATE VIEW` statement that creates the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. + +```sql ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +| View | Create View | character_set_client | collation_connection | ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +| v | CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`127.0.0.1` SQL SECURITY DEFINER VIEW `v` (`a`) AS SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | utf8 | utf8_general_ci | ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +1 row in set (0.00 sec) +``` + +### query the `INFORMATION_SCHEMA.VIEWS` table + +example: + +```sql +select * from information_schema.views; +``` + +You can view the relevant meta information of the view by querying the table, Such as`TABLE_CATALOG`,`TABLE_SCHEMA`,`TABLE_NAME`,`VIEW_DEFINITION`,`CHECK_OPTION`,`IS_UPDATABLE`,`DEFINER`,`SECURITY_TYPE`,`CHARACTER_SET_CLIENT`,`COLLATION_CONNECTION` + +```sql ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +| TABLE_CATALOG | TABLE_SCHEMA | TABLE_NAME | VIEW_DEFINITION | CHECK_OPTION | IS_UPDATABLE | DEFINER | SECURITY_TYPE | CHARACTER_SET_CLIENT | COLLATION_CONNECTION | ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +| def | test | v | SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | CASCADED | NO | root@127.0.0.1 | DEFINER | utf8 | utf8_general_ci | ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +1 row in set (0.00 sec) +``` + +### use the HTTP API + +example: + +```shell +curl http://127.0.0.1:10080/schema/test/v +``` + +By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the meta-information for the view. + +```shell +{ + "id": 122, + "name": { + "O": "v", + "L": "v" + }, + "charset": "utf8", + "collate": "utf8_general_ci", + "cols": [ + { + "id": 1, + "name": { + "O": "a", + "L": "a" + }, + "offset": 0, + "origin_default": null, + "default": null, + "default_bit": null, + "default_is_expr": false, + "generated_expr_string": "", + "generated_stored": false, + "dependences": null, + "type": { + "Tp": 0, + "Flag": 0, + "Flen": 0, + "Decimal": 0, + "Charset": "", + "Collate": "", + "Elems": null + }, + "state": 5, + "comment": "", + "hidden": false, + "version": 0 + } + ], + "index_info": null, + "fk_info": null, + "state": 5, + "pk_is_handle": false, + "is_common_handle": false, + "comment": "", + "auto_inc_id": 0, + "auto_id_cache": 0, + "auto_rand_id": 0, + "max_col_id": 1, + "max_idx_id": 0, + "update_timestamp": 416801600091455490, + "ShardRowIDBits": 0, + "max_shard_row_id_bits": 0, + "auto_random_bits": 0, + "pre_split_regions": 0, + "partition": null, + "compression": "", + "view": { + "view_algorithm": 0, + "view_definer": { + "Username": "root", + "Hostname": "127.0.0.1", + "CurrentUser": false, + "AuthUsername": "root", + "AuthHostname": "%" + }, + "view_security": 0, + "view_select": "SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a`", + "view_checkoption": 1, + "view_cols": null + }, + "sequence": null, + "Lock": null, + "version": 3, + "tiflash_replica": null +} +``` + +## Example + +The following example will create a view, query the view, and finally delete the view. + +```sql +create table t(a int, b int); +Query OK, 0 rows affected (0.01 sec) +``` + +```sql +insert into t values(1, 1),(2,2),(3,3); +Query OK, 3 rows affected (0.00 sec) +Records: 3 Duplicates: 0 Warnings: 0 +``` + +```sql +create table s(a int); +Query OK, 0 rows affected (0.01 sec) +``` + +```sql +insert into s values(2),(3); +Query OK, 2 rows affected (0.01 sec) +Records: 2 Duplicates: 0 Warnings: 0 +``` + +```sql +create view v as select s.a from t left join s on t.a = s.a; +Query OK, 0 rows affected (0.01 sec) +``` + +```sql +select * from v; ++------+ +| a | ++------+ +| NULL | +| 2 | +| 3 | ++------+ +3 rows in set (0.00 sec) +``` + +```sql +drop view v; +Query OK, 0 rows affected (0.02 sec) +``` + +## View limitations + + Now views in TiDB are subject to the following limitations: + +* Materialized views are not supported yet. +* Views in TiDB are read-only, does not support write operations such as `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE`. +* For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]`. From c890d6e35d622ed71e0bc362fcb12c1b353e3db9 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 24 Jun 2020 13:14:14 +0800 Subject: [PATCH 02/38] Update View.md --- View.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/View.md b/View.md index 0e162e5a152d1..6f885f03a1265 100644 --- a/View.md +++ b/View.md @@ -37,7 +37,7 @@ example: select * from information_schema.views; ``` -You can view the relevant meta information of the view by querying the table, Such as`TABLE_CATALOG`,`TABLE_SCHEMA`,`TABLE_NAME`,`VIEW_DEFINITION`,`CHECK_OPTION`,`IS_UPDATABLE`,`DEFINER`,`SECURITY_TYPE`,`CHARACTER_SET_CLIENT`,`COLLATION_CONNECTION` +You can view the relevant meta information of the view by querying the table, Such as `TABLE_CATALOG`, `TABLE_SCHEMA`, `TABLE_NAME`, `VIEW_DEFINITION`, `CHECK_OPTION`, `IS_UPDATABLE`, `DEFINER`, `SECURITY_TYPE`, `CHARACTER_SET_CLIENT`, `COLLATION_CONNECTION` ```sql +---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ @@ -189,5 +189,5 @@ Query OK, 0 rows affected (0.02 sec)  Now views in TiDB are subject to the following limitations: * Materialized views are not supported yet. -* Views in TiDB are read-only, does not support write operations such as `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE`. +* Views in TiDB are read-only, does not support write operations such as `UPDATE`, `INSERT`, `DELETE`, `TRUNCATE`. * For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]`. From 240e1544e4e1f238c587548962101616ceae59a1 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 24 Jun 2020 13:21:16 +0800 Subject: [PATCH 03/38] Update View.md --- View.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/View.md b/View.md index 6f885f03a1265..1d9ce198d69b2 100644 --- a/View.md +++ b/View.md @@ -37,7 +37,7 @@ example: select * from information_schema.views; ``` -You can view the relevant meta information of the view by querying the table, Such as `TABLE_CATALOG`, `TABLE_SCHEMA`, `TABLE_NAME`, `VIEW_DEFINITION`, `CHECK_OPTION`, `IS_UPDATABLE`, `DEFINER`, `SECURITY_TYPE`, `CHARACTER_SET_CLIENT`, `COLLATION_CONNECTION` +You can view the relevant meta information of the view by querying the table, Including `TABLE_CATALOG`, `TABLE_SCHEMA`, `TABLE_NAME`, `VIEW_DEFINITION`, `CHECK_OPTION`, `IS_UPDATABLE`, `DEFINER`, `SECURITY_TYPE`, `CHARACTER_SET_CLIENT`, `COLLATION_CONNECTION` ```sql +---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ @@ -189,5 +189,5 @@ Query OK, 0 rows affected (0.02 sec)  Now views in TiDB are subject to the following limitations: * Materialized views are not supported yet. -* Views in TiDB are read-only, does not support write operations such as `UPDATE`, `INSERT`, `DELETE`, `TRUNCATE`. -* For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]`. +* Views in TiDB are read-only, does not support write DML such as `UPDATE`, `INSERT`, `DELETE`, `TRUNCATE`. +* For created views, the only supported DDL is `DROP`, i.e., `DROP [VIEW | TABLE]`. From 8cfe36c43dfb7ad7094c3ca236321b6593c66563 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 24 Jun 2020 13:23:56 +0800 Subject: [PATCH 04/38] Update View.md --- View.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/View.md b/View.md index 1d9ce198d69b2..90f14910f2c9c 100644 --- a/View.md +++ b/View.md @@ -18,7 +18,7 @@ example: show create view v; ``` -This statement shows the `CREATE VIEW` statement that creates the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. +This statement shows the `CREATE VIEW` statement that created the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. ```sql +------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ From 94fa431e5811c5cd0e7b2de0b854f9a680f970f3 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 24 Jun 2020 13:25:48 +0800 Subject: [PATCH 05/38] Update View.md --- View.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/View.md b/View.md index 90f14910f2c9c..1d41d7f5d0a52 100644 --- a/View.md +++ b/View.md @@ -4,7 +4,7 @@ TiDB supports views, A view acts as a virtual table, It can be created from SELE ## query views -You can query a view in a similar way as you query an actual table. When the query is actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. +You can query a view in a similar way as you query an actual table. When the query is going to be actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. ## view metadata From 196d8da52940bac6e24823919bd9afb6e84c9ede Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:43:01 +0800 Subject: [PATCH 06/38] Create view --- view | 195 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 195 insertions(+) create mode 100644 view diff --git a/view b/view new file mode 100644 index 0000000000000..8e1da9b1639d7 --- /dev/null +++ b/view @@ -0,0 +1,195 @@ +# view + +TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to the user, to ensure the security of sensitive columns and data in the underlying table. + +On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. + +## query views + +You can query a view in a similar way as you query an actual table. When the query is actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. + +## metadata of view + +To obtain metadata about views: + +### use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement + +example: + +```sql +show create view v; +``` + +This statement shows the `CREATE VIEW` statement that created the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. + +```sql ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +| View | Create View | character_set_client | collation_connection | ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +| v | CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`127.0.0.1` SQL SECURITY DEFINER VIEW `v` (`a`) AS SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | utf8 | utf8_general_ci | ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +1 row in set (0.00 sec) +``` + +### query the `INFORMATION_SCHEMA.VIEWS` table + +example: + +```sql +select * from information_schema.views; +``` + +You can view the relevant meta information of the view by querying the table, i.e., `TABLE_CATALOG`,`TABLE_SCHEMA`,`TABLE_NAME`,`VIEW_DEFINITION`,`CHECK_OPTION`,`IS_UPDATABLE`,`DEFINER`,`SECURITY_TYPE`,`CHARACTER_SET_CLIENT`,`COLLATION_CONNECTION` + +```sql ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +| TABLE_CATALOG | TABLE_SCHEMA | TABLE_NAME | VIEW_DEFINITION | CHECK_OPTION | IS_UPDATABLE | DEFINER | SECURITY_TYPE | CHARACTER_SET_CLIENT | COLLATION_CONNECTION | ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +| def | test | v | SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | CASCADED | NO | root@127.0.0.1 | DEFINER | utf8 | utf8_general_ci | ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +1 row in set (0.00 sec) +``` + +### use the HTTP API + +example: + +```sql +curl http://127.0.0.1:10080/schema/test/v +``` + +By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the meta-information for the view. + +```shell +{ + "id": 122, + "name": { + "O": "v", + "L": "v" + }, + "charset": "utf8", + "collate": "utf8_general_ci", + "cols": [ + { + "id": 1, + "name": { + "O": "a", + "L": "a" + }, + "offset": 0, + "origin_default": null, + "default": null, + "default_bit": null, + "default_is_expr": false, + "generated_expr_string": "", + "generated_stored": false, + "dependences": null, + "type": { + "Tp": 0, + "Flag": 0, + "Flen": 0, + "Decimal": 0, + "Charset": "", + "Collate": "", + "Elems": null + }, + "state": 5, + "comment": "", + "hidden": false, + "version": 0 + } + ], + "index_info": null, + "fk_info": null, + "state": 5, + "pk_is_handle": false, + "is_common_handle": false, + "comment": "", + "auto_inc_id": 0, + "auto_id_cache": 0, + "auto_rand_id": 0, + "max_col_id": 1, + "max_idx_id": 0, + "update_timestamp": 416801600091455490, + "ShardRowIDBits": 0, + "max_shard_row_id_bits": 0, + "auto_random_bits": 0, + "pre_split_regions": 0, + "partition": null, + "compression": "", + "view": { + "view_algorithm": 0, + "view_definer": { + "Username": "root", + "Hostname": "127.0.0.1", + "CurrentUser": false, + "AuthUsername": "root", + "AuthHostname": "%" + }, + "view_security": 0, + "view_select": "SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a`", + "view_checkoption": 1, + "view_cols": null + }, + "sequence": null, + "Lock": null, + "version": 3, + "tiflash_replica": null +} +``` + +## Example + +The following example will create a view, query the view, and finally delete the view. + +```sql +create table t(a int, b int); +Query OK, 0 rows affected (0.01 sec) +``` + +```sql +insert into t values(1, 1),(2,2),(3,3); +Query OK, 3 rows affected (0.00 sec) +Records: 3 Duplicates: 0 Warnings: 0 +``` + +```sql +create table s(a int); +Query OK, 0 rows affected (0.01 sec) +``` + +```sql +insert into s values(2),(3); +Query OK, 2 rows affected (0.01 sec) +Records: 2 Duplicates: 0 Warnings: 0 +``` + +```sql +create view v as select s.a from t left join s on t.a = s.a; +Query OK, 0 rows affected (0.01 sec) +``` + +```sql +select * from v; ++------+ +| a | ++------+ +| NULL | +| 2 | +| 3 | ++------+ +3 rows in set (0.00 sec) +``` + +```sql +drop view v; +Query OK, 0 rows affected (0.02 sec) +``` + +## View limitations + + Now views in TiDB are subject to the following limitations: + +* Materialized views are not supported yet. +* Views in TiDB are read-only, does not support write operations such as `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE` +* For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]` From 8574ad1e9f1aab07995fe7f51bd850e126cf0d18 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:44:05 +0800 Subject: [PATCH 07/38] Update view From 11caa5065c2cc160c4da361353a32684d7db2894 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:49:18 +0800 Subject: [PATCH 08/38] Create Constraint --- Constraint | 198 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 198 insertions(+) create mode 100644 Constraint diff --git a/Constraint b/Constraint new file mode 100644 index 0000000000000..45934118b20ec --- /dev/null +++ b/Constraint @@ -0,0 +1,198 @@ +# Constraint + +TiDB supports the same constraint as MySQL. + +## NOT NULL + +NOT NULL constraints supported by TiDB are the same as those supported by MySQL + +For Example: + +```sql +CREATE TABLE users ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + age INT NOT NULL, + last_login TIMESTAMP +); +``` + +```sql +INSERT INTO users (id,age,last_login) VALUES (NULL,123,NOW()); +Query OK, 1 row affected (0.02 sec) +``` + +```sql +INSERT INTO users (id,age,last_login) VALUES (NULL,NULL,NOW()); +ERROR 1048 (23000): Column 'age' cannot be null +``` + +```sql +INSERT INTO users (id,age,last_login) VALUES (NULL,123,NULL); +Query OK, 1 row affected (0.03 sec) +``` + +* The first `INSERT` statement succeeded. Because it is possible to assign `NULL` to the `AUTO_INCREMENT` column. TiDB will generate sequence numbers automatically. +* The second `INSERT` statement failed. Because column `age` is defined as `NOT NULL`. +* The third `INSERT` statement succeed. Because column `last_login` is not explicitly defined as `NOT NULL`. NULL values ​​are allowed by default. + +## UNIQUE KEY + +In TiDB's optimistic transcation mode, TiDB will do lazy check for unique constraints by default. By performing batch checks when transactions are committed, TiDB can reduce network overhead and improve performance. + +For Example: + +```sql +DROP TABLE IF EXISTS users; +CREATE TABLE users ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + username VARCHAR(60) NOT NULL, + UNIQUE KEY (username) +); +INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); +``` + +```sql +START TRANSACTION; +Query OK, 0 rows affected (0.00 sec) +``` + +```sql +INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); +Query OK, 3 rows affected (0.00 sec) +Records: 3 Duplicates: 0 Warnings: 0 +``` + +```sql +INSERT INTO users (username) VALUES ('steve'),('elizabeth'); +Query OK, 2 rows affected (0.00 sec) +Records: 2 Duplicates: 0 Warnings: 0 +``` + +```sql +COMMIT; +ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' +``` + +The first `INSERT` statement will not cause duplicate key errors, which is consistent with MySQL's rules. This check will be delayed until the transaction is committed. +You can disable this behavior by setting `tidb_constraint_check_in_place` to `1` (this variable setting has no effect on pessimistic transaction mode, pessimistic transaction mode always check constraints when the statement is executed). If this behavior is disabled, the unique constraint will be checked when the statement is executed. + +For Example + +```sql +DROP TABLE IF EXISTS users; +CREATE TABLE users ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + username VARCHAR(60) NOT NULL, + UNIQUE KEY (username) +); +INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); +``` + +```sql +SET tidb_constraint_check_in_place = 1; +Query OK, 0 rows affected (0.00 sec) +``` + +```sql +START TRANSACTION; +Query OK, 0 rows affected (0.00 sec) +``` + +```sql +INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); +ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' +.. +``` + +The first `INSERT` statement caused a duplicate key error. This causes additional network communication overhead and may reduce the throughput of insert operations. + +## PRIMARY KEY + +Like MySQL, primary key constraints contain unique constraint, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraint of TiDB are also similar to MySQL. + +For Example + +```sql +CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY); +Query OK, 0 rows affected (0.12 sec) +``` + +```sql +CREATE TABLE t2 (a INT NULL PRIMARY KEY); +ERROR 1171 (42000): All parts of a PRIMARY KEY must be NOT NULL; if you need NULL in a key, use UNIQUE instead +``` + +```sql +CREATE TABLE t3 (a INT NOT NULL PRIMARY KEY, b INT NOT NULL PRIMARY KEY); +ERROR 1068 (42000): Multiple primary key defined +``` + +```sql +CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); +Query OK, 0 rows affected (0.10 sec) +``` + +* table `t2` failed to create, Because column `a` is defined as the primary key and cannot allow NULL values. +* table `t3` failed to create, Because a table can only have one primary key. +* table t4 was created successfully, Although there can be only one primary key, TiDB supports the definition of a multi-column combination as a composite primary key. + +In addition to the above rules, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. + +When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, for an integer type primary key table created when the feature is not enabled, even if the add/delete primary key feature is enabled, the primary key cannot be deleted. + +## FOREIGN KEY + +>note: + +TiDB has limited support for foreign key constraint. + +TiDB supports creating foreign key constraint. + +For Example + +```plain +CREATE TABLE users ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + doc JSON +); +CREATE TABLE orders ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + user_id INT NOT NULL, + doc JSON, + FOREIGN KEY fk_user_id (user_id) REFERENCES users(id) +); +``` + +```sql +SELECT table_name, column_name, constraint_name, referenced_table_name, referenced_column_name +FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders'); ++------------+-------------+-----------------+-----------------------+------------------------+ +| table_name | column_name | constraint_name | referenced_table_name | referenced_column_name | ++------------+-------------+-----------------+-----------------------+------------------------+ +| users | id | PRIMARY | NULL | NULL | +| orders | id | PRIMARY | NULL | NULL | +| orders | user_id | fk_user_id | users | id | ++------------+-------------+-----------------+-----------------------+------------------------+ +3 rows in set (0.00 sec) +``` + +TiDB also supports using ALTER TABLE command to delete foreign keys (DROP FOREIGN KEY) or add foreign keys (ADD FOREIGN KEY) + +```sql +ALTER TABLE orders DROP FOREIGN KEY fk_user_id; +ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); +``` + +### Note + +TiDB supports foreign keys in order to avoid errors due to this syntax when migrating other databases to TiDB. + +However, TiDB does not perform constraint checking on foreign keys in DML statements. For example, even if there is no record with id=123 in the users table, the following transactions can be submitted successfully. + +```sql +START TRANSACTION; +INSERT INTO orders (user_id, doc) VALUES (123, NULL); +COMMIT; +``` + +* TiDB does not display foreign key information in the result of executing the `SHOW CREATE TABLE` statement. From 5d9253e5decfc842d4069b8c7bd2a34b54169472 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:50:39 +0800 Subject: [PATCH 09/38] Rename Constraint to constraint.md --- Constraint => constraint.md | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename Constraint => constraint.md (100%) diff --git a/Constraint b/constraint.md similarity index 100% rename from Constraint rename to constraint.md From 02a2e1e548bb66d533772af82fb3f34acbc8cade Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:51:43 +0800 Subject: [PATCH 10/38] Delete View.md --- View.md | 193 -------------------------------------------------------- 1 file changed, 193 deletions(-) delete mode 100644 View.md diff --git a/View.md b/View.md deleted file mode 100644 index 1d41d7f5d0a52..0000000000000 --- a/View.md +++ /dev/null @@ -1,193 +0,0 @@ -# view - -TiDB supports views, A view acts as a virtual table, It can be created from SELECT statements. On the one hand, Using the view can only expose safe columns and data to the user, to ensure the security of sensitive columns and data in the underlying table. On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. - -## query views - -You can query a view in a similar way as you query an actual table. When the query is going to be actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. - -## view metadata - -To obtain metadata about views: - -### use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement - -example: - -```sql -show create view v; -``` - -This statement shows the `CREATE VIEW` statement that created the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. - -```sql -+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ -| View | Create View | character_set_client | collation_connection | -+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ -| v | CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`127.0.0.1` SQL SECURITY DEFINER VIEW `v` (`a`) AS SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | utf8 | utf8_general_ci | -+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ -1 row in set (0.00 sec) -``` - -### query the `INFORMATION_SCHEMA.VIEWS` table - -example: - -```sql -select * from information_schema.views; -``` - -You can view the relevant meta information of the view by querying the table, Including `TABLE_CATALOG`, `TABLE_SCHEMA`, `TABLE_NAME`, `VIEW_DEFINITION`, `CHECK_OPTION`, `IS_UPDATABLE`, `DEFINER`, `SECURITY_TYPE`, `CHARACTER_SET_CLIENT`, `COLLATION_CONNECTION` - -```sql -+---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ -| TABLE_CATALOG | TABLE_SCHEMA | TABLE_NAME | VIEW_DEFINITION | CHECK_OPTION | IS_UPDATABLE | DEFINER | SECURITY_TYPE | CHARACTER_SET_CLIENT | COLLATION_CONNECTION | -+---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ -| def | test | v | SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | CASCADED | NO | root@127.0.0.1 | DEFINER | utf8 | utf8_general_ci | -+---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ -1 row in set (0.00 sec) -``` - -### use the HTTP API - -example: - -```shell -curl http://127.0.0.1:10080/schema/test/v -``` - -By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the meta-information for the view. - -```shell -{ - "id": 122, - "name": { - "O": "v", - "L": "v" - }, - "charset": "utf8", - "collate": "utf8_general_ci", - "cols": [ - { - "id": 1, - "name": { - "O": "a", - "L": "a" - }, - "offset": 0, - "origin_default": null, - "default": null, - "default_bit": null, - "default_is_expr": false, - "generated_expr_string": "", - "generated_stored": false, - "dependences": null, - "type": { - "Tp": 0, - "Flag": 0, - "Flen": 0, - "Decimal": 0, - "Charset": "", - "Collate": "", - "Elems": null - }, - "state": 5, - "comment": "", - "hidden": false, - "version": 0 - } - ], - "index_info": null, - "fk_info": null, - "state": 5, - "pk_is_handle": false, - "is_common_handle": false, - "comment": "", - "auto_inc_id": 0, - "auto_id_cache": 0, - "auto_rand_id": 0, - "max_col_id": 1, - "max_idx_id": 0, - "update_timestamp": 416801600091455490, - "ShardRowIDBits": 0, - "max_shard_row_id_bits": 0, - "auto_random_bits": 0, - "pre_split_regions": 0, - "partition": null, - "compression": "", - "view": { - "view_algorithm": 0, - "view_definer": { - "Username": "root", - "Hostname": "127.0.0.1", - "CurrentUser": false, - "AuthUsername": "root", - "AuthHostname": "%" - }, - "view_security": 0, - "view_select": "SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a`", - "view_checkoption": 1, - "view_cols": null - }, - "sequence": null, - "Lock": null, - "version": 3, - "tiflash_replica": null -} -``` - -## Example - -The following example will create a view, query the view, and finally delete the view. - -```sql -create table t(a int, b int); -Query OK, 0 rows affected (0.01 sec) -``` - -```sql -insert into t values(1, 1),(2,2),(3,3); -Query OK, 3 rows affected (0.00 sec) -Records: 3 Duplicates: 0 Warnings: 0 -``` - -```sql -create table s(a int); -Query OK, 0 rows affected (0.01 sec) -``` - -```sql -insert into s values(2),(3); -Query OK, 2 rows affected (0.01 sec) -Records: 2 Duplicates: 0 Warnings: 0 -``` - -```sql -create view v as select s.a from t left join s on t.a = s.a; -Query OK, 0 rows affected (0.01 sec) -``` - -```sql -select * from v; -+------+ -| a | -+------+ -| NULL | -| 2 | -| 3 | -+------+ -3 rows in set (0.00 sec) -``` - -```sql -drop view v; -Query OK, 0 rows affected (0.02 sec) -``` - -## View limitations - - Now views in TiDB are subject to the following limitations: - -* Materialized views are not supported yet. -* Views in TiDB are read-only, does not support write DML such as `UPDATE`, `INSERT`, `DELETE`, `TRUNCATE`. -* For created views, the only supported DDL is `DROP`, i.e., `DROP [VIEW | TABLE]`. From a4117d731a670bfc8740d22ceb2d8f1f192b0929 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:53:47 +0800 Subject: [PATCH 11/38] Rename view to view.md --- view => view.md | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename view => view.md (100%) diff --git a/view b/view.md similarity index 100% rename from view rename to view.md From 33c62a5996ef331e5061fb337c5229b016ead919 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 09:57:53 +0800 Subject: [PATCH 12/38] Update view.md --- view.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/view.md b/view.md index 8e1da9b1639d7..81c36ab804e80 100644 --- a/view.md +++ b/view.md @@ -1,6 +1,6 @@ # view -TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to the user, to ensure the security of sensitive columns and data in the underlying table. +TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to users, to ensure the security of sensitive columns and data in the underlying table. On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. @@ -186,10 +186,10 @@ drop view v; Query OK, 0 rows affected (0.02 sec) ``` -## View limitations +## Limitations  Now views in TiDB are subject to the following limitations: * Materialized views are not supported yet. -* Views in TiDB are read-only, does not support write operations such as `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE` +* Views in TiDB are read-only and do not support write operations like `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE` and so on. * For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]` From 7352458cb59662cc4d1df188498988e3dfcf1a1c Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 10:01:11 +0800 Subject: [PATCH 13/38] Update views.md --- views.md | 189 ++++++++++++++++++++++++++++++++++++++++++++++--------- 1 file changed, 159 insertions(+), 30 deletions(-) diff --git a/views.md b/views.md index c3e881b07f4f8..81c36ab804e80 100644 --- a/views.md +++ b/views.md @@ -1,44 +1,176 @@ ---- -title: Views -summary: Learn how to use views in TiDB. -category: reference -aliases: ['/docs/dev/reference/sql/views/'] ---- +# view -# Views +TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to users, to ensure the security of sensitive columns and data in the underlying table. -TiDB supports views. A view acts as a virtual table and its table schema is defined by the `SELECT` statement when you create the view. Using views has the following benefits: +On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. -- Exposing only safe fields and data to users to ensure security of sensitive fields and data stored in the underlying table -- Defining complex queries that frequently appear as views to make complex queries easier and more convenient +## query views -## Query views +You can query a view in a similar way as you query an actual table. When the query is actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. -Querying a view is similar to querying an ordinary table. However, when TiDB queries a view, it actually queries the `SELECT` statement associated with the view. +## metadata of view -## Examples +To obtain metadata about views: -The following example creates a view, queries this view, and delete this view: +### use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement + +example: + +```sql +show create view v; +``` + +This statement shows the `CREATE VIEW` statement that created the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. + +```sql ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +| View | Create View | character_set_client | collation_connection | ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +| v | CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`127.0.0.1` SQL SECURITY DEFINER VIEW `v` (`a`) AS SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | utf8 | utf8_general_ci | ++------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ +1 row in set (0.00 sec) +``` + +### query the `INFORMATION_SCHEMA.VIEWS` table + +example: + +```sql +select * from information_schema.views; +``` + +You can view the relevant meta information of the view by querying the table, i.e., `TABLE_CATALOG`,`TABLE_SCHEMA`,`TABLE_NAME`,`VIEW_DEFINITION`,`CHECK_OPTION`,`IS_UPDATABLE`,`DEFINER`,`SECURITY_TYPE`,`CHARACTER_SET_CLIENT`,`COLLATION_CONNECTION` + +```sql ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +| TABLE_CATALOG | TABLE_SCHEMA | TABLE_NAME | VIEW_DEFINITION | CHECK_OPTION | IS_UPDATABLE | DEFINER | SECURITY_TYPE | CHARACTER_SET_CLIENT | COLLATION_CONNECTION | ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +| def | test | v | SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | CASCADED | NO | root@127.0.0.1 | DEFINER | utf8 | utf8_general_ci | ++---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ +1 row in set (0.00 sec) +``` + +### use the HTTP API + +example: + +```sql +curl http://127.0.0.1:10080/schema/test/v +``` + +By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the meta-information for the view. + +```shell +{ + "id": 122, + "name": { + "O": "v", + "L": "v" + }, + "charset": "utf8", + "collate": "utf8_general_ci", + "cols": [ + { + "id": 1, + "name": { + "O": "a", + "L": "a" + }, + "offset": 0, + "origin_default": null, + "default": null, + "default_bit": null, + "default_is_expr": false, + "generated_expr_string": "", + "generated_stored": false, + "dependences": null, + "type": { + "Tp": 0, + "Flag": 0, + "Flen": 0, + "Decimal": 0, + "Charset": "", + "Collate": "", + "Elems": null + }, + "state": 5, + "comment": "", + "hidden": false, + "version": 0 + } + ], + "index_info": null, + "fk_info": null, + "state": 5, + "pk_is_handle": false, + "is_common_handle": false, + "comment": "", + "auto_inc_id": 0, + "auto_id_cache": 0, + "auto_rand_id": 0, + "max_col_id": 1, + "max_idx_id": 0, + "update_timestamp": 416801600091455490, + "ShardRowIDBits": 0, + "max_shard_row_id_bits": 0, + "auto_random_bits": 0, + "pre_split_regions": 0, + "partition": null, + "compression": "", + "view": { + "view_algorithm": 0, + "view_definer": { + "Username": "root", + "Hostname": "127.0.0.1", + "CurrentUser": false, + "AuthUsername": "root", + "AuthHostname": "%" + }, + "view_security": 0, + "view_select": "SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a`", + "view_checkoption": 1, + "view_cols": null + }, + "sequence": null, + "Lock": null, + "version": 3, + "tiflash_replica": null +} +``` + +## Example + +The following example will create a view, query the view, and finally delete the view. ```sql -tidb> create table t(a int, b int); +create table t(a int, b int); Query OK, 0 rows affected (0.01 sec) +``` -tidb> insert into t values(1, 1),(2,2),(3,3); +```sql +insert into t values(1, 1),(2,2),(3,3); Query OK, 3 rows affected (0.00 sec) Records: 3 Duplicates: 0 Warnings: 0 +``` -tidb> create table s(a int); +```sql +create table s(a int); Query OK, 0 rows affected (0.01 sec) +``` -tidb> insert into s values(2),(3); +```sql +insert into s values(2),(3); Query OK, 2 rows affected (0.01 sec) Records: 2 Duplicates: 0 Warnings: 0 +``` -tidb> create view v as select s.a from t left join s on t.a = s.a; +```sql +create view v as select s.a from t left join s on t.a = s.a; Query OK, 0 rows affected (0.01 sec) +``` -tidb> select * from v; +```sql +select * from v; +------+ | a | +------+ @@ -47,20 +179,17 @@ tidb> select * from v; | 3 | +------+ 3 rows in set (0.00 sec) +``` -tidb> drop view v; +```sql +drop view v; Query OK, 0 rows affected (0.02 sec) ``` ## Limitations -Currently, the TiDB view has the following limitations: - -- TiDB does not support materialized views. -- TiDB views are read-only and do not support write operations like `UPDATE`, `INSERT`, `DELETE` and so on. -- For created views, TiDB only support the `DROP [VIEW | TABLE]` DDL operation. - -## See also + Now views in TiDB are subject to the following limitations: -- [CREATE VIEW](/sql-statements/sql-statement-create-view.md) -- [DROP VIEW](/sql-statements/sql-statement-drop-view.md) +* Materialized views are not supported yet. +* Views in TiDB are read-only and do not support write operations like `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE` and so on. +* For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]` From 2ccd09406c5a03d14174f7ce383ced67f79f4235 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 10:01:31 +0800 Subject: [PATCH 14/38] Update views.md --- views.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/views.md b/views.md index 81c36ab804e80..02f16f4f9452c 100644 --- a/views.md +++ b/views.md @@ -1,4 +1,4 @@ -# view +# views TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to users, to ensure the security of sensitive columns and data in the underlying table. From 853b80aca795160a5b4791ddca040394fe57fe1f Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 10:20:02 +0800 Subject: [PATCH 15/38] Update constraint.md --- constraint.md | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/constraint.md b/constraint.md index 45934118b20ec..eb451c5817c58 100644 --- a/constraint.md +++ b/constraint.md @@ -37,7 +37,7 @@ Query OK, 1 row affected (0.03 sec) ## UNIQUE KEY -In TiDB's optimistic transcation mode, TiDB will do lazy check for unique constraints by default. By performing batch checks when transactions are committed, TiDB can reduce network overhead and improve performance. +In TiDB's optimistic transcation mode, UNIQUE constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB can reduce network overhead and improve performance. For Example: @@ -108,7 +108,7 @@ The first `INSERT` statement caused a duplicate key error. This causes addition ## PRIMARY KEY -Like MySQL, primary key constraints contain unique constraint, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraint of TiDB are also similar to MySQL. +Like MySQL, primary key constraints contain unique constraints, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraint of TiDB are also similar to MySQL. For Example @@ -132,9 +132,9 @@ CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); Query OK, 0 rows affected (0.10 sec) ``` -* table `t2` failed to create, Because column `a` is defined as the primary key and cannot allow NULL values. -* table `t3` failed to create, Because a table can only have one primary key. -* table t4 was created successfully, Although there can be only one primary key, TiDB supports the definition of a multi-column combination as a composite primary key. +* table `t2` failed to be created, Because column `a` is defined as the primary key and permitted NULL values. +* table `t3` failed to be created, Because a table can only have one primary key. +* table t4 was created successfully, Because even though there can be only one primary key, it may be defined as a composite of multiple columns. In addition to the above rules, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. @@ -144,9 +144,9 @@ When the add/delete primary key feature is enabled, TiDB allows adding/deleting >note: -TiDB has limited support for foreign key constraint. +TiDB has limited support for foreign key constraints. -TiDB supports creating foreign key constraint. +TiDB supports creating `FOREIGN KEY` creation in DDL commands. For Example @@ -176,14 +176,14 @@ FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders') 3 rows in set (0.00 sec) ``` -TiDB also supports using ALTER TABLE command to delete foreign keys (DROP FOREIGN KEY) or add foreign keys (ADD FOREIGN KEY) +TiDB also supports the syntax to `DROP FOREIGN KEY` and `ADD FOREIGN KEY` via the `ALTER TABLE` command. ```sql ALTER TABLE orders DROP FOREIGN KEY fk_user_id; ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); ``` -### Note +### Notes TiDB supports foreign keys in order to avoid errors due to this syntax when migrating other databases to TiDB. From 44c61f16967375e01f8c0ba189175b95bd65b033 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 10:22:34 +0800 Subject: [PATCH 16/38] Update constraints.md --- constraints.md | 250 +++++++++++++++++++++++++------------------------ 1 file changed, 128 insertions(+), 122 deletions(-) diff --git a/constraints.md b/constraints.md index 4694481973747..eb451c5817c58 100644 --- a/constraints.md +++ b/constraints.md @@ -1,192 +1,198 @@ ---- -title: Constraints -summary: Learn how SQL Constraints apply to TiDB. -category: reference -aliases: ['/docs/dev/reference/sql/constraints/'] ---- +# Constraint -# Constraints +TiDB supports the same constraint as MySQL. -## Overview +## NOT NULL -TiDB supports the same basic constraints supported in MySQL with the following exceptions: +NOT NULL constraints supported by TiDB are the same as those supported by MySQL -- `PRIMARY KEY` and `UNIQUE` constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB is able to reduce network communication. This behavior can be changed by setting `tidb_constraint_check_in_place` to `TRUE`. - -- `FOREIGN KEY` constraints are not currently enforced by DML. - -## Foreign Key - -TiDB currently only supports `FOREIGN KEY` creation in DDL commands. For example: +For Example: ```sql CREATE TABLE users ( id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - doc JSON -); - -CREATE TABLE orders ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - user_id INT NOT NULL, - doc JSON, - FOREIGN KEY fk_user_id (user_id) REFERENCES users(id) + age INT NOT NULL, + last_login TIMESTAMP ); - -mysql> SELECT table_name, column_name, constraint_name, referenced_table_name, referenced_column_name -FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders'); -+------------+-------------+-----------------+-----------------------+------------------------+ -| table_name | column_name | constraint_name | referenced_table_name | referenced_column_name | -+------------+-------------+-----------------+-----------------------+------------------------+ -| users | id | PRIMARY | NULL | NULL | -| orders | id | PRIMARY | NULL | NULL | -| orders | user_id | fk_user_id | users | id | -+------------+-------------+-----------------+-----------------------+------------------------+ -3 rows in set (0.00 sec) ``` -TiDB also supports the syntax to `DROP FOREIGN KEY` and `ADD FOREIGN KEY` via the `ALTER TABLE` command: - ```sql -ALTER TABLE orders DROP FOREIGN KEY fk_user_id; -ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); +INSERT INTO users (id,age,last_login) VALUES (NULL,123,NOW()); +Query OK, 1 row affected (0.02 sec) ``` -### Notes +```sql +INSERT INTO users (id,age,last_login) VALUES (NULL,NULL,NOW()); +ERROR 1048 (23000): Column 'age' cannot be null +``` -* TiDB supports foreign keys so that no errors are reported for this syntax when migrating data from other databases. Currently, foreign keys are not enforced as part of DML operations. For example, even though there is no such record as `id=123` in the `users` table, the following transaction commits successfully in TiDB: +```sql +INSERT INTO users (id,age,last_login) VALUES (NULL,123,NULL); +Query OK, 1 row affected (0.03 sec) +``` - ``` - START TRANSACTION; - INSERT INTO orders (user_id, doc) VALUES (123, NULL); - COMMIT; - ``` +* The first `INSERT` statement succeeded. Because it is possible to assign `NULL` to the `AUTO_INCREMENT` column. TiDB will generate sequence numbers automatically. +* The second `INSERT` statement failed. Because column `age` is defined as `NOT NULL`. +* The third `INSERT` statement succeed. Because column `last_login` is not explicitly defined as `NOT NULL`. NULL values ​​are allowed by default. -* In TiDB, the foreign key information is not displayed in the execution result of the `SHOW CREATE TABLE` statement. +## UNIQUE KEY -## Not Null +In TiDB's optimistic transcation mode, UNIQUE constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB can reduce network overhead and improve performance. -TiDB supports the `NOT NULL` constraint with identical semantics to MySQL. For example: +For Example: ```sql +DROP TABLE IF EXISTS users; CREATE TABLE users ( id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - age INT NOT NULL, - last_login TIMESTAMP + username VARCHAR(60) NOT NULL, + UNIQUE KEY (username) ); +INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); +``` -mysql> INSERT INTO users (id,age,last_login) VALUES (NULL,123,NOW()); -Query OK, 1 row affected (0.02 sec) - -mysql> INSERT INTO users (id,age,last_login) VALUES (NULL,NULL,NOW()); -ERROR 1048 (23000): Column 'age' cannot be null - -mysql> INSERT INTO users (id,age,last_login) VALUES (NULL,123,NULL); -Query OK, 1 row affected (0.03 sec) +```sql +START TRANSACTION; +Query OK, 0 rows affected (0.00 sec) ``` -* The first `INSERT` statement succeeded because `NULL` is permitted as a special value for columns defined as `AUTO_INCREMENT`. This results in the next auto-value being allocated. +```sql +INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); +Query OK, 3 rows affected (0.00 sec) +Records: 3 Duplicates: 0 Warnings: 0 +``` -* The second `INSERT` statement fails because the `age` column was defined as `NOT NULL`. +```sql +INSERT INTO users (username) VALUES ('steve'),('elizabeth'); +Query OK, 2 rows affected (0.00 sec) +Records: 2 Duplicates: 0 Warnings: 0 +``` -* The third `INSERT` statement succeeds because `last_login` did not explicitly specify the column as `NOT NULL`. The default behavior is to permit `NULL` values. +```sql +COMMIT; +ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' +``` -## Primary Key +The first `INSERT` statement will not cause duplicate key errors, which is consistent with MySQL's rules. This check will be delayed until the transaction is committed. +You can disable this behavior by setting `tidb_constraint_check_in_place` to `1` (this variable setting has no effect on pessimistic transaction mode, pessimistic transaction mode always check constraints when the statement is executed). If this behavior is disabled, the unique constraint will be checked when the statement is executed. -In TiDB, `PRIMARY KEY` constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB is able to reduce network communication. For example: +For Example ```sql -mysql> CREATE TABLE t1 (id INT NOT NULL PRIMARY KEY); -Query OK, 0 rows affected (0.01 sec) +DROP TABLE IF EXISTS users; +CREATE TABLE users ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + username VARCHAR(60) NOT NULL, + UNIQUE KEY (username) +); +INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); +``` -mysql> INSERT INTO t1 VALUES (1); -Query OK, 1 row affected (0.00 sec) +```sql +SET tidb_constraint_check_in_place = 1; +Query OK, 0 rows affected (0.00 sec) +``` -mysql> START TRANSACTION; +```sql +START TRANSACTION; Query OK, 0 rows affected (0.00 sec) +``` -mysql> INSERT INTO t1 VALUES (1); -- does not error -Query OK, 1 row affected (0.00 sec) +```sql +INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); +ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' +.. +``` -mysql> INSERT INTO t1 VALUES (2); -Query OK, 1 row affected (0.00 sec) +The first `INSERT` statement caused a duplicate key error. This causes additional network communication overhead and may reduce the throughput of insert operations. -mysql> COMMIT; -- triggers an error -ERROR 1062 (23000): Duplicate entry '1' for key 'PRIMARY' -``` +## PRIMARY KEY -`PRIMARY KEY` constraints otherwise have similar behavior and restrictions to MySQL: +Like MySQL, primary key constraints contain unique constraints, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraint of TiDB are also similar to MySQL. + +For Example ```sql -mysql> CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY); +CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY); Query OK, 0 rows affected (0.12 sec) +``` -mysql> CREATE TABLE t2 (a INT NULL PRIMARY KEY); +```sql +CREATE TABLE t2 (a INT NULL PRIMARY KEY); ERROR 1171 (42000): All parts of a PRIMARY KEY must be NOT NULL; if you need NULL in a key, use UNIQUE instead +``` -mysql> CREATE TABLE t3 (a INT NOT NULL PRIMARY KEY, b INT NOT NULL PRIMARY KEY); +```sql +CREATE TABLE t3 (a INT NOT NULL PRIMARY KEY, b INT NOT NULL PRIMARY KEY); ERROR 1068 (42000): Multiple primary key defined +``` -mysql> CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); +```sql +CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); Query OK, 0 rows affected (0.10 sec) ``` -* Table `t2` failed to be created because the column `a` permitted `NULL` values. -* Table `t3` failed because there can only be one `PRIMARY KEY` on a table. -* Table `t4` was successful, because even though there can only be one primary key, it may be defined as a composite of multiple columns. +* table `t2` failed to be created, Because column `a` is defined as the primary key and permitted NULL values. +* table `t3` failed to be created, Because a table can only have one primary key. +* table t4 was created successfully, Because even though there can be only one primary key, it may be defined as a composite of multiple columns. -In addition to these semantics, TiDB also imposes the restriction that once a table is created, the `PRIMARY KEY` can not be changed. +In addition to the above rules, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. -## Unique +When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, for an integer type primary key table created when the feature is not enabled, even if the add/delete primary key feature is enabled, the primary key cannot be deleted. -In TiDB, `UNIQUE` constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB is able to reduce network communication. For example: +## FOREIGN KEY -```sql -DROP TABLE IF EXISTS users; -CREATE TABLE users ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - username VARCHAR(60) NOT NULL, - UNIQUE KEY (username) -); -INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); +>note: -mysql> START TRANSACTION; -Query OK, 0 rows affected (0.00 sec) +TiDB has limited support for foreign key constraints. -mysql> INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); -Query OK, 3 rows affected (0.00 sec) -Records: 3 Duplicates: 0 Warnings: 0 +TiDB supports creating `FOREIGN KEY` creation in DDL commands. -mysql> INSERT INTO users (username) VALUES ('steve'),('elizabeth'); -Query OK, 2 rows affected (0.00 sec) -Records: 2 Duplicates: 0 Warnings: 0 +For Example -mysql> COMMIT; -ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' +```plain +CREATE TABLE users ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + doc JSON +); +CREATE TABLE orders ( + id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, + user_id INT NOT NULL, + doc JSON, + FOREIGN KEY fk_user_id (user_id) REFERENCES users(id) +); ``` -* The first `INSERT` statement does not cause a duplicate key error, as it would in MySQL. This check is deferred until the `COMMIT` statement is executed. +```sql +SELECT table_name, column_name, constraint_name, referenced_table_name, referenced_column_name +FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders'); ++------------+-------------+-----------------+-----------------------+------------------------+ +| table_name | column_name | constraint_name | referenced_table_name | referenced_column_name | ++------------+-------------+-----------------+-----------------------+------------------------+ +| users | id | PRIMARY | NULL | NULL | +| orders | id | PRIMARY | NULL | NULL | +| orders | user_id | fk_user_id | users | id | ++------------+-------------+-----------------+-----------------------+------------------------+ +3 rows in set (0.00 sec) +``` -By changing `tidb_constraint_check_in_place` to `TRUE`, `UNIQUE` constraints will be checked as statements are executed. For example: +TiDB also supports the syntax to `DROP FOREIGN KEY` and `ADD FOREIGN KEY` via the `ALTER TABLE` command. ```sql -DROP TABLE IF EXISTS users; -CREATE TABLE users ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - username VARCHAR(60) NOT NULL, - UNIQUE KEY (username) -); -INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); +ALTER TABLE orders DROP FOREIGN KEY fk_user_id; +ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); +``` -mysql> SET tidb_constraint_check_in_place = TRUE; -Query OK, 0 rows affected (0.00 sec) +### Notes -mysql> START TRANSACTION; -Query OK, 0 rows affected (0.00 sec) +TiDB supports foreign keys in order to avoid errors due to this syntax when migrating other databases to TiDB. -mysql> INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); -ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' +However, TiDB does not perform constraint checking on foreign keys in DML statements. For example, even if there is no record with id=123 in the users table, the following transactions can be submitted successfully. -.. +```sql +START TRANSACTION; +INSERT INTO orders (user_id, doc) VALUES (123, NULL); +COMMIT; ``` -* The first `INSERT` statement causes a duplicate key error. This results in additional network communication, and will likely decrease insert throughput. +* TiDB does not display foreign key information in the result of executing the `SHOW CREATE TABLE` statement. From 6d9fe48345ec077f27a3a39ee4a631f7cc476d0d Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 10:22:57 +0800 Subject: [PATCH 17/38] Delete constraint.md --- constraint.md | 198 -------------------------------------------------- 1 file changed, 198 deletions(-) delete mode 100644 constraint.md diff --git a/constraint.md b/constraint.md deleted file mode 100644 index eb451c5817c58..0000000000000 --- a/constraint.md +++ /dev/null @@ -1,198 +0,0 @@ -# Constraint - -TiDB supports the same constraint as MySQL. - -## NOT NULL - -NOT NULL constraints supported by TiDB are the same as those supported by MySQL - -For Example: - -```sql -CREATE TABLE users ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - age INT NOT NULL, - last_login TIMESTAMP -); -``` - -```sql -INSERT INTO users (id,age,last_login) VALUES (NULL,123,NOW()); -Query OK, 1 row affected (0.02 sec) -``` - -```sql -INSERT INTO users (id,age,last_login) VALUES (NULL,NULL,NOW()); -ERROR 1048 (23000): Column 'age' cannot be null -``` - -```sql -INSERT INTO users (id,age,last_login) VALUES (NULL,123,NULL); -Query OK, 1 row affected (0.03 sec) -``` - -* The first `INSERT` statement succeeded. Because it is possible to assign `NULL` to the `AUTO_INCREMENT` column. TiDB will generate sequence numbers automatically. -* The second `INSERT` statement failed. Because column `age` is defined as `NOT NULL`. -* The third `INSERT` statement succeed. Because column `last_login` is not explicitly defined as `NOT NULL`. NULL values ​​are allowed by default. - -## UNIQUE KEY - -In TiDB's optimistic transcation mode, UNIQUE constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB can reduce network overhead and improve performance. - -For Example: - -```sql -DROP TABLE IF EXISTS users; -CREATE TABLE users ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - username VARCHAR(60) NOT NULL, - UNIQUE KEY (username) -); -INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); -``` - -```sql -START TRANSACTION; -Query OK, 0 rows affected (0.00 sec) -``` - -```sql -INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); -Query OK, 3 rows affected (0.00 sec) -Records: 3 Duplicates: 0 Warnings: 0 -``` - -```sql -INSERT INTO users (username) VALUES ('steve'),('elizabeth'); -Query OK, 2 rows affected (0.00 sec) -Records: 2 Duplicates: 0 Warnings: 0 -``` - -```sql -COMMIT; -ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' -``` - -The first `INSERT` statement will not cause duplicate key errors, which is consistent with MySQL's rules. This check will be delayed until the transaction is committed. -You can disable this behavior by setting `tidb_constraint_check_in_place` to `1` (this variable setting has no effect on pessimistic transaction mode, pessimistic transaction mode always check constraints when the statement is executed). If this behavior is disabled, the unique constraint will be checked when the statement is executed. - -For Example - -```sql -DROP TABLE IF EXISTS users; -CREATE TABLE users ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - username VARCHAR(60) NOT NULL, - UNIQUE KEY (username) -); -INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); -``` - -```sql -SET tidb_constraint_check_in_place = 1; -Query OK, 0 rows affected (0.00 sec) -``` - -```sql -START TRANSACTION; -Query OK, 0 rows affected (0.00 sec) -``` - -```sql -INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); -ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' -.. -``` - -The first `INSERT` statement caused a duplicate key error. This causes additional network communication overhead and may reduce the throughput of insert operations. - -## PRIMARY KEY - -Like MySQL, primary key constraints contain unique constraints, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraint of TiDB are also similar to MySQL. - -For Example - -```sql -CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY); -Query OK, 0 rows affected (0.12 sec) -``` - -```sql -CREATE TABLE t2 (a INT NULL PRIMARY KEY); -ERROR 1171 (42000): All parts of a PRIMARY KEY must be NOT NULL; if you need NULL in a key, use UNIQUE instead -``` - -```sql -CREATE TABLE t3 (a INT NOT NULL PRIMARY KEY, b INT NOT NULL PRIMARY KEY); -ERROR 1068 (42000): Multiple primary key defined -``` - -```sql -CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); -Query OK, 0 rows affected (0.10 sec) -``` - -* table `t2` failed to be created, Because column `a` is defined as the primary key and permitted NULL values. -* table `t3` failed to be created, Because a table can only have one primary key. -* table t4 was created successfully, Because even though there can be only one primary key, it may be defined as a composite of multiple columns. - -In addition to the above rules, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. - -When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, for an integer type primary key table created when the feature is not enabled, even if the add/delete primary key feature is enabled, the primary key cannot be deleted. - -## FOREIGN KEY - ->note: - -TiDB has limited support for foreign key constraints. - -TiDB supports creating `FOREIGN KEY` creation in DDL commands. - -For Example - -```plain -CREATE TABLE users ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - doc JSON -); -CREATE TABLE orders ( - id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, - user_id INT NOT NULL, - doc JSON, - FOREIGN KEY fk_user_id (user_id) REFERENCES users(id) -); -``` - -```sql -SELECT table_name, column_name, constraint_name, referenced_table_name, referenced_column_name -FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders'); -+------------+-------------+-----------------+-----------------------+------------------------+ -| table_name | column_name | constraint_name | referenced_table_name | referenced_column_name | -+------------+-------------+-----------------+-----------------------+------------------------+ -| users | id | PRIMARY | NULL | NULL | -| orders | id | PRIMARY | NULL | NULL | -| orders | user_id | fk_user_id | users | id | -+------------+-------------+-----------------+-----------------------+------------------------+ -3 rows in set (0.00 sec) -``` - -TiDB also supports the syntax to `DROP FOREIGN KEY` and `ADD FOREIGN KEY` via the `ALTER TABLE` command. - -```sql -ALTER TABLE orders DROP FOREIGN KEY fk_user_id; -ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); -``` - -### Notes - -TiDB supports foreign keys in order to avoid errors due to this syntax when migrating other databases to TiDB. - -However, TiDB does not perform constraint checking on foreign keys in DML statements. For example, even if there is no record with id=123 in the users table, the following transactions can be submitted successfully. - -```sql -START TRANSACTION; -INSERT INTO orders (user_id, doc) VALUES (123, NULL); -COMMIT; -``` - -* TiDB does not display foreign key information in the result of executing the `SHOW CREATE TABLE` statement. From 014fd2112715080fb5996df077768eecd49fd419 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:50:37 +0800 Subject: [PATCH 18/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index a61981ab046fd..e6760242d74fa 100644 --- a/constraints.md +++ b/constraints.md @@ -11,7 +11,7 @@ TiDB supports the same constraint as MySQL. ## NOT NULL -NOT NULL constraints supported by TiDB are the same as those supported by MySQL +NOT NULL constraints supported by TiDB are the same as those supported by MySQL. For Example: From d6988a84efe3574e3cfddcda436d2bde61c2434a Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:50:50 +0800 Subject: [PATCH 19/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index e6760242d74fa..0bebc1eaeaaa7 100644 --- a/constraints.md +++ b/constraints.md @@ -13,7 +13,7 @@ TiDB supports the same constraint as MySQL. NOT NULL constraints supported by TiDB are the same as those supported by MySQL. -For Example: +For example: ```sql CREATE TABLE users ( From 5e455a0b6dc311de314b2b0f7798b36c1f35acb4 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:52:05 +0800 Subject: [PATCH 20/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/constraints.md b/constraints.md index 0bebc1eaeaaa7..f18781e7cfe42 100644 --- a/constraints.md +++ b/constraints.md @@ -38,9 +38,9 @@ INSERT INTO users (id,age,last_login) VALUES (NULL,123,NULL); Query OK, 1 row affected (0.03 sec) ``` -* The first `INSERT` statement succeeded. Because it is possible to assign `NULL` to the `AUTO_INCREMENT` column. TiDB will generate sequence numbers automatically. -* The second `INSERT` statement failed. Because column `age` is defined as `NOT NULL`. -* The third `INSERT` statement succeed. Because column `last_login` is not explicitly defined as `NOT NULL`. NULL values ​​are allowed by default. +* The first `INSERT` statement succeeds because it is possible to assign `NULL` to the `AUTO_INCREMENT` column. TiDB generates sequence numbers automatically. +* The second `INSERT` statement fails because the `age` column is defined as `NOT NULL`. +* The third `INSERT` statement succeeds because the `last_login` column is not explicitly defined as `NOT NULL`. NULL values ​​are allowed by default. ## UNIQUE KEY From ebe95f71529162a4f96aa1165b84ea77a2f2dcb9 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:52:44 +0800 Subject: [PATCH 21/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index f18781e7cfe42..d23a0d3298e1a 100644 --- a/constraints.md +++ b/constraints.md @@ -81,7 +81,7 @@ ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' ``` The first `INSERT` statement will not cause duplicate key errors, which is consistent with MySQL's rules. This check will be delayed until the transaction is committed. -You can disable this behavior by setting `tidb_constraint_check_in_place` to `1` (this variable setting has no effect on pessimistic transaction mode, pessimistic transaction mode always check constraints when the statement is executed). If this behavior is disabled, the unique constraint will be checked when the statement is executed. +You can disable this behavior by setting `tidb_constraint_check_in_place` to `1`. This variable setting does not take effect on pessimistic transactions, because in the pessimistic transaction mode the constraints are always checked when the statement is executed. If this behavior is disabled, the unique constraint is checked when the statement is executed. For Example From 14570b5269eb3a55d9fae27857a4ba9fd1654a5c Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:52:56 +0800 Subject: [PATCH 22/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index d23a0d3298e1a..829e714514403 100644 --- a/constraints.md +++ b/constraints.md @@ -44,7 +44,7 @@ Query OK, 1 row affected (0.03 sec) ## UNIQUE KEY -In TiDB's optimistic transcation mode, UNIQUE constraints are checked lazily by default. By batching checks until when the transaction commits, TiDB can reduce network overhead and improve performance. +In TiDB's optimistic transcation mode, UNIQUE constraints are [checked lazily](/transaction-overview.md#lazy-check-of-constraints) by default. By batching checks when the transaction is committed, TiDB can reduce network overhead and improve performance. For Example: From 5615c20b9c04cdd3ce00e22341ee5d6bba5930b2 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:53:06 +0800 Subject: [PATCH 23/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index 829e714514403..963646816286c 100644 --- a/constraints.md +++ b/constraints.md @@ -46,7 +46,7 @@ Query OK, 1 row affected (0.03 sec) In TiDB's optimistic transcation mode, UNIQUE constraints are [checked lazily](/transaction-overview.md#lazy-check-of-constraints) by default. By batching checks when the transaction is committed, TiDB can reduce network overhead and improve performance. -For Example: +For example: ```sql DROP TABLE IF EXISTS users; From dad8547fc8dda380b1d3d47864378fed41e2f5ad Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:53:18 +0800 Subject: [PATCH 24/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index 963646816286c..e1684cb39ff65 100644 --- a/constraints.md +++ b/constraints.md @@ -83,7 +83,7 @@ ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' The first `INSERT` statement will not cause duplicate key errors, which is consistent with MySQL's rules. This check will be delayed until the transaction is committed. You can disable this behavior by setting `tidb_constraint_check_in_place` to `1`. This variable setting does not take effect on pessimistic transactions, because in the pessimistic transaction mode the constraints are always checked when the statement is executed. If this behavior is disabled, the unique constraint is checked when the statement is executed. -For Example +For example: ```sql DROP TABLE IF EXISTS users; From 30cd301922d618cb2aa4b38b5adf0ef295506622 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:53:36 +0800 Subject: [PATCH 25/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index e1684cb39ff65..15ddb1530f4d8 100644 --- a/constraints.md +++ b/constraints.md @@ -115,7 +115,7 @@ The first `INSERT` statement caused a duplicate key error. This causes addition ## PRIMARY KEY -Like MySQL, primary key constraints contain unique constraints, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraint of TiDB are also similar to MySQL. +Like MySQL, primary key constraints contain unique constraints, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraints of TiDB are also similar to those of MySQL. For Example From e48a54e6de9465f356d60f608857ea5bf5b03f83 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:54:09 +0800 Subject: [PATCH 26/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/constraints.md b/constraints.md index 15ddb1530f4d8..d20a02aa78d3a 100644 --- a/constraints.md +++ b/constraints.md @@ -139,9 +139,9 @@ CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); Query OK, 0 rows affected (0.10 sec) ``` -* table `t2` failed to be created, Because column `a` is defined as the primary key and permitted NULL values. -* table `t3` failed to be created, Because a table can only have one primary key. -* table t4 was created successfully, Because even though there can be only one primary key, it may be defined as a composite of multiple columns. +* Table `t2` failed to be created, because column `a` is defined as the primary key and does not allow NULL values. +* Table `t3` failed to be created, because a table can only have one primary key. +* Table `t4` was created successfully, because even though there can be only one primary key, TiDB supports defining multiple columns as the composite primary key. In addition to the above rules, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. From d4d76d9dae3b11d9cea8f8a7b6f06feff8c03ff0 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:54:28 +0800 Subject: [PATCH 27/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index d20a02aa78d3a..a40e83feeb51b 100644 --- a/constraints.md +++ b/constraints.md @@ -143,7 +143,7 @@ Query OK, 0 rows affected (0.10 sec) * Table `t3` failed to be created, because a table can only have one primary key. * Table `t4` was created successfully, because even though there can be only one primary key, TiDB supports defining multiple columns as the composite primary key. -In addition to the above rules, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. +In addition to the rules above, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, for an integer type primary key table created when the feature is not enabled, even if the add/delete primary key feature is enabled, the primary key cannot be deleted. From 2443e1e478d3bae8e313f77f10f33af863864698 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:54:56 +0800 Subject: [PATCH 28/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index a40e83feeb51b..7fdae260cac11 100644 --- a/constraints.md +++ b/constraints.md @@ -145,7 +145,7 @@ Query OK, 0 rows affected (0.10 sec) In addition to the rules above, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. -When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, for an integer type primary key table created when the feature is not enabled, even if the add/delete primary key feature is enabled, the primary key cannot be deleted. +When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, if a table with an integer type primary key has been created before the feature is enabled, you cannot delete its primary key constraint even when you enabled the add/delete primary key feature. ## FOREIGN KEY From a21a6e2db8c187d3560c512cd1fa1ce154aed511 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:55:37 +0800 Subject: [PATCH 29/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index 7fdae260cac11..7c3ae2a12ce4c 100644 --- a/constraints.md +++ b/constraints.md @@ -192,7 +192,7 @@ ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); ### Notes -TiDB supports foreign keys in order to avoid errors due to this syntax when migrating other databases to TiDB. +TiDB supports foreign keys to avoid errors caused by this syntax when you migrate data from other databases to TiDB. However, TiDB does not perform constraint checking on foreign keys in DML statements. For example, even if there is no record with id=123 in the users table, the following transactions can be submitted successfully. From 5a3259837faefa2c02f7f02932760d12d114ba55 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:55:55 +0800 Subject: [PATCH 30/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/constraints.md b/constraints.md index 7c3ae2a12ce4c..c55187e18e2ad 100644 --- a/constraints.md +++ b/constraints.md @@ -151,7 +151,7 @@ When the add/delete primary key feature is enabled, TiDB allows adding/deleting >note: -TiDB has limited support for foreign key constraints. +> TiDB has limited support for foreign key constraints. TiDB supports creating `FOREIGN KEY` creation in DDL commands. From 5da6b65827893614c5a179f68fc2b2fb3130e2b8 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 20:58:25 +0800 Subject: [PATCH 31/38] Update constraints.md --- constraints.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/constraints.md b/constraints.md index c55187e18e2ad..3d88fd2fefd8f 100644 --- a/constraints.md +++ b/constraints.md @@ -173,6 +173,9 @@ CREATE TABLE orders ( ```sql SELECT table_name, column_name, constraint_name, referenced_table_name, referenced_column_name FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders'); +``` + +```sql +------------+-------------+-----------------+-----------------------+------------------------+ | table_name | column_name | constraint_name | referenced_table_name | referenced_column_name | +------------+-------------+-----------------+-----------------------+------------------------+ From 1ae15c37b9c77e8f7ed15dc9d31c5389533fa4e7 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 21:00:19 +0800 Subject: [PATCH 32/38] Update constraints.md Co-authored-by: Ran --- constraints.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/constraints.md b/constraints.md index 3d88fd2fefd8f..c7b4ce089d78b 100644 --- a/constraints.md +++ b/constraints.md @@ -149,8 +149,8 @@ When the add/delete primary key feature is enabled, TiDB allows adding/deleting ## FOREIGN KEY ->note: - +> **Note:** +> > TiDB has limited support for foreign key constraints. TiDB supports creating `FOREIGN KEY` creation in DDL commands. From 823db872e3e291ecfa15294dd5612d17d05f30e9 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 21:00:56 +0800 Subject: [PATCH 33/38] Delete view.md --- view.md | 195 -------------------------------------------------------- 1 file changed, 195 deletions(-) delete mode 100644 view.md diff --git a/view.md b/view.md deleted file mode 100644 index 81c36ab804e80..0000000000000 --- a/view.md +++ /dev/null @@ -1,195 +0,0 @@ -# view - -TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to users, to ensure the security of sensitive columns and data in the underlying table. - -On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. - -## query views - -You can query a view in a similar way as you query an actual table. When the query is actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. - -## metadata of view - -To obtain metadata about views: - -### use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement - -example: - -```sql -show create view v; -``` - -This statement shows the `CREATE VIEW` statement that created the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. - -```sql -+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ -| View | Create View | character_set_client | collation_connection | -+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ -| v | CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`127.0.0.1` SQL SECURITY DEFINER VIEW `v` (`a`) AS SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | utf8 | utf8_general_ci | -+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ -1 row in set (0.00 sec) -``` - -### query the `INFORMATION_SCHEMA.VIEWS` table - -example: - -```sql -select * from information_schema.views; -``` - -You can view the relevant meta information of the view by querying the table, i.e., `TABLE_CATALOG`,`TABLE_SCHEMA`,`TABLE_NAME`,`VIEW_DEFINITION`,`CHECK_OPTION`,`IS_UPDATABLE`,`DEFINER`,`SECURITY_TYPE`,`CHARACTER_SET_CLIENT`,`COLLATION_CONNECTION` - -```sql -+---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ -| TABLE_CATALOG | TABLE_SCHEMA | TABLE_NAME | VIEW_DEFINITION | CHECK_OPTION | IS_UPDATABLE | DEFINER | SECURITY_TYPE | CHARACTER_SET_CLIENT | COLLATION_CONNECTION | -+---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ -| def | test | v | SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a` | CASCADED | NO | root@127.0.0.1 | DEFINER | utf8 | utf8_general_ci | -+---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ -1 row in set (0.00 sec) -``` - -### use the HTTP API - -example: - -```sql -curl http://127.0.0.1:10080/schema/test/v -``` - -By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the meta-information for the view. - -```shell -{ - "id": 122, - "name": { - "O": "v", - "L": "v" - }, - "charset": "utf8", - "collate": "utf8_general_ci", - "cols": [ - { - "id": 1, - "name": { - "O": "a", - "L": "a" - }, - "offset": 0, - "origin_default": null, - "default": null, - "default_bit": null, - "default_is_expr": false, - "generated_expr_string": "", - "generated_stored": false, - "dependences": null, - "type": { - "Tp": 0, - "Flag": 0, - "Flen": 0, - "Decimal": 0, - "Charset": "", - "Collate": "", - "Elems": null - }, - "state": 5, - "comment": "", - "hidden": false, - "version": 0 - } - ], - "index_info": null, - "fk_info": null, - "state": 5, - "pk_is_handle": false, - "is_common_handle": false, - "comment": "", - "auto_inc_id": 0, - "auto_id_cache": 0, - "auto_rand_id": 0, - "max_col_id": 1, - "max_idx_id": 0, - "update_timestamp": 416801600091455490, - "ShardRowIDBits": 0, - "max_shard_row_id_bits": 0, - "auto_random_bits": 0, - "pre_split_regions": 0, - "partition": null, - "compression": "", - "view": { - "view_algorithm": 0, - "view_definer": { - "Username": "root", - "Hostname": "127.0.0.1", - "CurrentUser": false, - "AuthUsername": "root", - "AuthHostname": "%" - }, - "view_security": 0, - "view_select": "SELECT `s`.`a` FROM `test`.`t` LEFT JOIN `test`.`s` ON `t`.`a`=`s`.`a`", - "view_checkoption": 1, - "view_cols": null - }, - "sequence": null, - "Lock": null, - "version": 3, - "tiflash_replica": null -} -``` - -## Example - -The following example will create a view, query the view, and finally delete the view. - -```sql -create table t(a int, b int); -Query OK, 0 rows affected (0.01 sec) -``` - -```sql -insert into t values(1, 1),(2,2),(3,3); -Query OK, 3 rows affected (0.00 sec) -Records: 3 Duplicates: 0 Warnings: 0 -``` - -```sql -create table s(a int); -Query OK, 0 rows affected (0.01 sec) -``` - -```sql -insert into s values(2),(3); -Query OK, 2 rows affected (0.01 sec) -Records: 2 Duplicates: 0 Warnings: 0 -``` - -```sql -create view v as select s.a from t left join s on t.a = s.a; -Query OK, 0 rows affected (0.01 sec) -``` - -```sql -select * from v; -+------+ -| a | -+------+ -| NULL | -| 2 | -| 3 | -+------+ -3 rows in set (0.00 sec) -``` - -```sql -drop view v; -Query OK, 0 rows affected (0.02 sec) -``` - -## Limitations - - Now views in TiDB are subject to the following limitations: - -* Materialized views are not supported yet. -* Views in TiDB are read-only and do not support write operations like `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE` and so on. -* For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]` From 9ca6ff281c91a25c32b479a73e53d47f2291ce01 Mon Sep 17 00:00:00 2001 From: KASSADAR Date: Wed, 8 Jul 2020 21:06:43 +0800 Subject: [PATCH 34/38] Update views.md --- views.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/views.md b/views.md index e85931d176d14..c486e3e37461a 100644 --- a/views.md +++ b/views.md @@ -178,6 +178,9 @@ Query OK, 0 rows affected (0.01 sec) ```sql select * from v; +``` + +```sql +------+ | a | +------+ From 456ee193bce3f2080bfa751aa0befcc3a1ecf5aa Mon Sep 17 00:00:00 2001 From: Ran Date: Thu, 9 Jul 2020 12:20:51 +0800 Subject: [PATCH 35/38] update format and wording --- constraints.md | 103 +++++++++++++++++++++++++++++++++++++++++++------ views.md | 88 +++++++++++++++++++++++++++++++----------- 2 files changed, 157 insertions(+), 34 deletions(-) diff --git a/constraints.md b/constraints.md index c7b4ce089d78b..96db5763fbdd1 100644 --- a/constraints.md +++ b/constraints.md @@ -15,6 +15,8 @@ NOT NULL constraints supported by TiDB are the same as those supported by MySQL. For example: +{{< copyable "sql" >}} + ```sql CREATE TABLE users ( id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, @@ -23,18 +25,33 @@ CREATE TABLE users ( ); ``` +{{< copyable "sql" >}} + ```sql INSERT INTO users (id,age,last_login) VALUES (NULL,123,NOW()); +``` + +``` Query OK, 1 row affected (0.02 sec) ``` +{{< copyable "sql" >}} + ```sql INSERT INTO users (id,age,last_login) VALUES (NULL,NULL,NOW()); +``` + +``` ERROR 1048 (23000): Column 'age' cannot be null ``` +{{< copyable "sql" >}} + ```sql INSERT INTO users (id,age,last_login) VALUES (NULL,123,NULL); +``` + +``` Query OK, 1 row affected (0.03 sec) ``` @@ -44,10 +61,12 @@ Query OK, 1 row affected (0.03 sec) ## UNIQUE KEY -In TiDB's optimistic transcation mode, UNIQUE constraints are [checked lazily](/transaction-overview.md#lazy-check-of-constraints) by default. By batching checks when the transaction is committed, TiDB can reduce network overhead and improve performance. +In TiDB's optimistic transaction mode, UNIQUE constraints are [checked lazily](/transaction-overview.md#lazy-check-of-constraints) by default. By batching checks when the transaction is committed, TiDB can reduce network overhead and improve performance. For example: +{{< copyable "sql" >}} + ```sql DROP TABLE IF EXISTS users; CREATE TABLE users ( @@ -58,29 +77,50 @@ CREATE TABLE users ( INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); ``` +{{< copyable "sql" >}} + ```sql START TRANSACTION; +``` + +``` Query OK, 0 rows affected (0.00 sec) ``` +{{< copyable "sql" >}} + ```sql INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); +``` + +``` Query OK, 3 rows affected (0.00 sec) Records: 3 Duplicates: 0 Warnings: 0 ``` +{{< copyable "sql" >}} + ```sql INSERT INTO users (username) VALUES ('steve'),('elizabeth'); +``` + +``` Query OK, 2 rows affected (0.00 sec) Records: 2 Duplicates: 0 Warnings: 0 ``` +{{< copyable "sql" >}} + ```sql COMMIT; +``` + +``` ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' ``` The first `INSERT` statement will not cause duplicate key errors, which is consistent with MySQL's rules. This check will be delayed until the transaction is committed. + You can disable this behavior by setting `tidb_constraint_check_in_place` to `1`. This variable setting does not take effect on pessimistic transactions, because in the pessimistic transaction mode the constraints are always checked when the statement is executed. If this behavior is disabled, the unique constraint is checked when the statement is executed. For example: @@ -95,18 +135,33 @@ CREATE TABLE users ( INSERT INTO users (username) VALUES ('dave'), ('sarah'), ('bill'); ``` +{{< copyable "sql" >}} + ```sql SET tidb_constraint_check_in_place = 1; +``` + +``` Query OK, 0 rows affected (0.00 sec) ``` +{{< copyable "sql" >}} + ```sql START TRANSACTION; +``` + +``` Query OK, 0 rows affected (0.00 sec) ``` +{{< copyable "sql" >}} + ```sql INSERT INTO users (username) VALUES ('jane'), ('chris'), ('bill'); +``` + +``` ERROR 1062 (23000): Duplicate entry 'bill' for key 'username' .. ``` @@ -117,25 +172,45 @@ The first `INSERT` statement caused a duplicate key error. This causes addition Like MySQL, primary key constraints contain unique constraints, that is, creating a primary key constraint is equivalent to having a unique constraint. In addition, other primary key constraints of TiDB are also similar to those of MySQL. -For Example +For example: + +{{< copyable "sql" >}} ```sql CREATE TABLE t1 (a INT NOT NULL PRIMARY KEY); +``` + +``` Query OK, 0 rows affected (0.12 sec) ``` +{{< copyable "sql" >}} + ```sql CREATE TABLE t2 (a INT NULL PRIMARY KEY); +``` + +``` ERROR 1171 (42000): All parts of a PRIMARY KEY must be NOT NULL; if you need NULL in a key, use UNIQUE instead ``` +{{< copyable "sql" >}} + ```sql CREATE TABLE t3 (a INT NOT NULL PRIMARY KEY, b INT NOT NULL PRIMARY KEY); +``` + +``` ERROR 1068 (42000): Multiple primary key defined ``` +{{< copyable "sql" >}} + ```sql CREATE TABLE t4 (a INT NOT NULL, b INT NOT NULL, PRIMARY KEY (a,b)); +``` + +``` Query OK, 0 rows affected (0.10 sec) ``` @@ -155,9 +230,9 @@ When the add/delete primary key feature is enabled, TiDB allows adding/deleting TiDB supports creating `FOREIGN KEY` creation in DDL commands. -For Example +For example: -```plain +```sql CREATE TABLE users ( id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, doc JSON @@ -170,12 +245,14 @@ CREATE TABLE orders ( ); ``` +{{< copyable "sql" >}} + ```sql SELECT table_name, column_name, constraint_name, referenced_table_name, referenced_column_name FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders'); ``` -```sql +``` +------------+-------------+-----------------+-----------------------+------------------------+ | table_name | column_name | constraint_name | referenced_table_name | referenced_column_name | +------------+-------------+-----------------+-----------------------+------------------------+ @@ -188,6 +265,8 @@ FROM information_schema.key_column_usage WHERE table_name IN ('users', 'orders') TiDB also supports the syntax to `DROP FOREIGN KEY` and `ADD FOREIGN KEY` via the `ALTER TABLE` command. +{{< copyable "sql" >}} + ```sql ALTER TABLE orders DROP FOREIGN KEY fk_user_id; ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); @@ -195,14 +274,14 @@ ALTER TABLE orders ADD FOREIGN KEY fk_user_id (user_id) REFERENCES users(id); ### Notes -TiDB supports foreign keys to avoid errors caused by this syntax when you migrate data from other databases to TiDB. +* TiDB supports foreign keys to avoid errors caused by this syntax when you migrate data from other databases to TiDB. -However, TiDB does not perform constraint checking on foreign keys in DML statements. For example, even if there is no record with id=123 in the users table, the following transactions can be submitted successfully. + However, TiDB does not perform constraint checking on foreign keys in DML statements. For example, even if there is no record with id=123 in the users table, the following transactions can be submitted successfully. -```sql -START TRANSACTION; -INSERT INTO orders (user_id, doc) VALUES (123, NULL); -COMMIT; -``` + ```sql + START TRANSACTION; + INSERT INTO orders (user_id, doc) VALUES (123, NULL); + COMMIT; + ``` * TiDB does not display foreign key information in the result of executing the `SHOW CREATE TABLE` statement. diff --git a/views.md b/views.md index c486e3e37461a..2e96da55503ee 100644 --- a/views.md +++ b/views.md @@ -5,29 +5,32 @@ category: reference aliases: ['/docs/dev/views/','/docs/dev/reference/sql/views/'] --- -# views +# Views -TiDB supports views, A view acts as a virtual table, It can be created from `SELECT` statements. On the one hand, Using the view can only expose safe columns and data to users, to ensure the security of sensitive columns and data in the underlying table. +TiDB supports views. A view acts as a virtual table, whose schema is defined by the `SELECT` statement that creates the view. Using views has the following benefits: -On the other hand, defining complex queries that frequently appear as views can make complex queries simpler and more convenient. +- Exposing only safe fields and data to users to ensure security of sensitive fields and data stored in the underlying table. +- Defining complex queries that frequently appear as views to make complex queries easier and more convenient. -## query views +## Query views -You can query a view in a similar way as you query an actual table. When the query is actually executed, the view is expanded into the SELECT statement defined when the view was created, and then the expanded query statment is executed. +Querying a view is similar to querying an ordinary table. However, when TiDB queries a view, it actually queries the `SELECT` statement associated with the view. -## metadata of view +## Show metadata -To obtain metadata about views: +To obtain the metadata of views, choose any of the following methods. -### use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement +### Use the `SHOW CREATE TABLE view_name` or `SHOW CREATE VIEW view_name` statement -example: +Usage example: + +{{< copyable "sql" >}} ```sql show create view v; ``` -This statement shows the `CREATE VIEW` statement that created the named view. And show the value of the `character_set_client` and `collation_connection` system variable when the view was created. +This statement shows the `CREATE VIEW` statement corresponding to this view and the value of the `character_set_client` and `collation_connection` system variables when the view was created. ```sql +------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------+----------------------+----------------------+ @@ -38,15 +41,17 @@ This statement shows the `CREATE VIEW` statement that created the named view. 1 row in set (0.00 sec) ``` -### query the `INFORMATION_SCHEMA.VIEWS` table +### Query the `INFORMATION_SCHEMA.VIEWS` table + +Usage example: -example: +{{< copyable "sql" >}} ```sql select * from information_schema.views; ``` -You can view the relevant meta information of the view by querying the table, i.e., `TABLE_CATALOG`,`TABLE_SCHEMA`,`TABLE_NAME`,`VIEW_DEFINITION`,`CHECK_OPTION`,`IS_UPDATABLE`,`DEFINER`,`SECURITY_TYPE`,`CHARACTER_SET_CLIENT`,`COLLATION_CONNECTION` +You can view the relevant meta information of the view by querying this table, such as `TABLE_CATALOG`, `TABLE_SCHEMA`, `TABLE_NAME`, `VIEW_DEFINITION`, `CHECK_OPTION`, `IS_UPDATABLE`, `DEFINER`, `SECURITY_TYPE`, `CHARACTER_SET_CLIENT`, and `COLLATION_CONNECTION`. ```sql +---------------+--------------+------------+------------------------------------------------------------------------+--------------+--------------+----------------+---------------+----------------------+----------------------+ @@ -57,17 +62,19 @@ You can view the relevant meta information of the view by querying the table, i 1 row in set (0.00 sec) ``` -### use the HTTP API +### Use the HTTP APIs + +Usage example: -example: +{{< copyable "" >}} ```sql curl http://127.0.0.1:10080/schema/test/v ``` -By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the meta-information for the view. +By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the metadata for the view. -```shell +``` { "id": 122, "name": { @@ -147,40 +154,67 @@ By visiting `http://{TiDBIP}:10080/schema/{db}/{view}`, you can get all the met ## Example -The following example will create a view, query the view, and finally delete the view. +The following example creates a view, queries this view, and delete this view: + +{{< copyable "sql" >}} ```sql create table t(a int, b int); +``` + +``` Query OK, 0 rows affected (0.01 sec) ``` +{{< copyable "sql" >}} + ```sql insert into t values(1, 1),(2,2),(3,3); +``` + +``` Query OK, 3 rows affected (0.00 sec) Records: 3 Duplicates: 0 Warnings: 0 ``` +{{< copyable "sql" >}} + ```sql create table s(a int); +``` + +``` Query OK, 0 rows affected (0.01 sec) ``` +{{< copyable "sql" >}} + ```sql insert into s values(2),(3); +``` + +``` Query OK, 2 rows affected (0.01 sec) Records: 2 Duplicates: 0 Warnings: 0 ``` +{{< copyable "sql" >}} + ```sql create view v as select s.a from t left join s on t.a = s.a; +``` + +``` Query OK, 0 rows affected (0.01 sec) ``` +{{< copyable "sql" >}} + ```sql select * from v; ``` -```sql +``` +------+ | a | +------+ @@ -191,15 +225,25 @@ select * from v; 3 rows in set (0.00 sec) ``` +{{< copyable "sql" >}} + ```sql drop view v; +``` + +``` Query OK, 0 rows affected (0.02 sec) ``` ## Limitations - Now views in TiDB are subject to the following limitations: +Currently, views in TiDB are subject to the following limitations: * Materialized views are not supported yet. -* Views in TiDB are read-only and do not support write operations like `UPDATE`,`INSERT`,`DELETE`,`TRUNCATE` and so on. -* For created views, the only supported DDL opertion is `DROP`, i.e., `DROP [VIEW | TABLE]` +* Views in TiDB are read-only and do not support write operations such as `UPDATE`, `INSERT`, `DELETE`, and `TRUNCATE`. +* For created views, the only supported DDL operation is `DROP [VIEW | TABLE]` + +## See also + +- [CREATE VIEW](/sql-statements/sql-statement-create-view.md) +- [DROP VIEW](/sql-statements/sql-statement-drop-view.md) From f7fdabd4cd22bd029ef9a2065cfcbbb520aad18c Mon Sep 17 00:00:00 2001 From: Ran Date: Thu, 9 Jul 2020 12:31:30 +0800 Subject: [PATCH 36/38] fix a dead anchor --- transaction-overview.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/transaction-overview.md b/transaction-overview.md index ae043d5f911a6..7579f87b57c39 100644 --- a/transaction-overview.md +++ b/transaction-overview.md @@ -107,7 +107,7 @@ For DDL statements, the transaction is committed automatically and does not supp ## Lazy check of constraints -**Lazy check** means that by default TiDB will not check [primary key](/constraints.md#primary-key) or [unique constraints](/constraints.md#unique) when an `INSERT` statement is executed, but instead checks when the transaction is committed. In TiDB, the lazy check is performed for values written by ordinary `INSERT` statements. +**Lazy check** means that by default TiDB will not check [primary key](/constraints.md#primary-key) or [unique constraints](/constraints.md#unique-key) when an `INSERT` statement is executed, but instead checks when the transaction is committed. In TiDB, the lazy check is performed for values written by ordinary `INSERT` statements. For example: From 4eca55a0b5b796cb067d6914fc950e9e4b574ed1 Mon Sep 17 00:00:00 2001 From: Ran Date: Thu, 9 Jul 2020 12:33:23 +0800 Subject: [PATCH 37/38] Apply suggestions from code review --- constraints.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/constraints.md b/constraints.md index 96db5763fbdd1..dff03cb76a778 100644 --- a/constraints.md +++ b/constraints.md @@ -220,7 +220,7 @@ Query OK, 0 rows affected (0.10 sec) In addition to the rules above, by default, TiDB has an additional restriction that once a table is successfully created, its primary key cannot be changed. If you need to add/remove the primary key, you need to set `alter-primary-key` to `true` in the TiDB configuration file, and restart the TiDB instance to make it effective. -When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, if a table with an integer type primary key has been created before the feature is enabled, you cannot delete its primary key constraint even when you enabled the add/delete primary key feature. +When the add/delete primary key feature is enabled, TiDB allows adding/deleting primary key to the table. However, it should be noted that, if a table with an integer type primary key has been created before the feature is enabled, you cannot delete its primary key constraint even when you enable the add/delete primary key feature. ## FOREIGN KEY @@ -228,7 +228,7 @@ When the add/delete primary key feature is enabled, TiDB allows adding/deleting > > TiDB has limited support for foreign key constraints. -TiDB supports creating `FOREIGN KEY` creation in DDL commands. +TiDB supports creating `FOREIGN KEY` constraints in DDL commands. For example: From 1c2fbe70a5b0895908fedce7fd2803a2be86e560 Mon Sep 17 00:00:00 2001 From: Ran Date: Thu, 16 Jul 2020 15:53:52 +0800 Subject: [PATCH 38/38] Apply suggestions from code review --- constraints.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/constraints.md b/constraints.md index 172d37fd0d929..bb32e5a9b69a1 100644 --- a/constraints.md +++ b/constraints.md @@ -4,9 +4,9 @@ summary: Learn how SQL Constraints apply to TiDB. aliases: ['/docs/dev/constraints/','/docs/dev/reference/sql/constraints/'] --- -# Constraint +# Constraints -TiDB supports the same constraint as MySQL. +TiDB supports almost the same constraint as MySQL. ## NOT NULL