序文
ブログ投稿(トランザクションと分離-概念)では、著者はMySQLのトランザクションの基本概念について説明しています。この記事では、トランザクション制御の関連するSQLコマンドに焦点を当て、関連する例をシミュレートします。
トランザクション制御言語
MySQL関連のトランザクション制御SQLステートメント(キーワード)は次のとおりです。
SET AUTOCOMMIT:自动提交;
START TRANSACTION (or BEGIN):显示的开始一个新的事物;
SAVEPOINT:设置一个保存点,用于后续(回滚)引用;
COMMIT:提交,永久保存事务修改;
ROLLBACK:取消当前事务的所有修改(回滚);
ROLLBACK TO SAVEPOINT:回滚到savepoint;
RELEASE SAVEPOINT: 删除所有保存点;
上記のSQLステートメントのうち、システム構成に属するSET AUTOCOMMITを除いて、その他はすべてトランザクション内の論理制御ステートメントです。包括的なトランザクション制御のサンプル図は次のとおりです。
AUTOCOMMIT自動送信
MySQL AUTOCOMMITモードはデフォルトで有効になっています。つまり、各SQLステートメントはトランザクションとして扱われ、ユーザーはBEGINまたはSTART TRANSACTIONを使用してこの自動送信をオーバーライドし、新しい1つのトランザクションを開くことができます。
コマンド
- AUTOCOMMITモードを表示する
mysql> show variables like '%autocommit%';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| autocommit | ON |
+---------------+-------+
1 row in set (0.33 sec)
- AUTOCOMMITモード(セッションレベル、グローバルレベル)を設定します
mysql> set autocommit=0;
Query OK, 0 rows affected (0.00 sec)
mysql> show variables like '%autocommit%';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| autocommit | OFF |
+---------------+-------+
1 row in set (0.01 sec)
テスト
まず、セッションの自動コミットをOFF / 0に設定し、送信されていない2行のデータ(test_1、test_2)を挿入しますが、選択は表示できます。その後、上記の変更がロールバックによってロールバックされ、前の挿入ステートメントが存在しないことが判明しました。これは、ファントム読み取りが発生したことを意味しますか??
mysql> select @@autocommit;
+--------------+
| @@autocommit |
+--------------+
| 0 |
+--------------+
1 row in set (0.00 sec)
mysql> insert into zavier.char_test (char_col) values ('test_2');
Query OK, 1 row affected (0.00 sec)
mysql> select * from zavier.char_test;
+----------+
| char_col |
+----------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
| test_1 |
| test_2 |
+----------+
7 rows in set (0.00 sec)
mysql> rollback;
Query OK, 0 rows affected (0.04 sec)
mysql> select * from zavier.char_test;
+----------+
| char_col |
+----------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
+----------+
5 rows in set (0.00 sec)
mysql> select @@transaction_isolation;
+-------------------------+
| @@transaction_isolation |
+-------------------------+
| REPEATABLE-READ |
+-------------------------+
1 row in set (0.00 sec)
暗黙のコミット
暗黙的なコミットとは、明示的なコミットステートメントがなく、データベースへの変更がコミットされたままであり、ロールバックできないことを意味します。MySQLの一般的な非トランザクションステートメントは、次のような暗黙のコミットを引き起こします。
- DFL:変更、作成、ドロップ等;
- 行政声明:付与、取り消し、パスワードの設定等;
一般に、DML以外のすべてを暗黙的なコミットの原因として扱うことをお勧めします。
SAVEPOINTセーブポイント
SAVEPOINTステートメントは、名前付きトランザクションのセーブポイントを識別子の名前で設定します。現在のトランザクションに同じ名前のセーブポイントがある場合、古いセーブポイントが削除され、新しいセーブポイントが設定されます。
SAVEPOINTステートメントは、トランザクションの名前付きセーブポイントを設定するために使用され、後続のROLLBACK TOSAVEPOINTステートメントがこのセーブポイントにロールバックするために使用されます。
COMMITを実行すると、現在のトランザクションのすべてのセーブポイントが削除されます。
セーブポイントに名前を付けないでください。
注:セーブポイントはトランザクションレイヤーの概念です。トランザクションが発生すると、すべてのセーブポイントが削除されます。
完全なトランザクションの例
mysql> begin;
Query OK, 0 rows affected (0.00 sec)
mysql> select * from zavier.char_test;
+----------+
| char_col |
+----------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
+----------+
5 rows in set (0.00 sec)
mysql> insert into zavier.char_test (char_col) values ('before_save');
Query OK, 1 row affected (0.00 sec)
mysql> select * from zavier.char_test;
+-------------+
| char_col |
+-------------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
| before_save |
+-------------+
6 rows in set (0.00 sec)
mysql> savepoint sp1;
Query OK, 0 rows affected (0.00 sec)
mysql> insert into zavier.char_test (char_col) values ('after_save');
Query OK, 1 row affected (0.00 sec)
mysql> select * from zavier.char_test;
+-------------+
| char_col |
+-------------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
| before_save |
| after_save |
+-------------+
7 rows in set (0.00 sec)
mysql> rollback to savepoint sp1;
Query OK, 0 rows affected (0.00 sec)
mysql> select * from zavier.char_test;
+-------------+
| char_col |
+-------------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
| before_save |
+-------------+
6 rows in set (0.00 sec)
mysql> commit;
Query OK, 0 rows affected (0.24 sec)
mysql> select * from zavier.char_test;
+-------------+
| char_col |
+-------------+
| string1 |
| string2 |
| string3 |
| string4 |
| string4 |
| before_save |
+-------------+
6 rows in set (0.00 sec)
説明:
- まず、トランザクションは、beginステートメントを介して明示的に開かれます(自動送信をオフにするため)。
- テーブルの内容を初めて表示する場合に選択します。
- 最初の挿入では、「before_save」のコンテンツが挿入されます。
- 選択してテーブルの内容を2回目に表示すると、「before_save」-----ファントムの読み取り値が表示されます。
- セーブポイントセットセーブポイント;
- 2番目の挿入は、「after_save」のコンテンツを挿入します。
- テーブルの内容を3回目に表示する場合に選択すると、「before_save」、「after_save」-----ファントムの読み取り値が表示されます。
- セーブポイントsp1へのロールバック;セーブポイントsp1へのロールバック;
- 4番目の選択ビュー「after_save」がロールバックされました。
- commit;トランザクションをコミットします
- 5回目に選択したとき、「after_save」コンテンツは実際にはありません。
総括する
この記事では、AUTOCOMMIT、セーブポイント、ロールバック(セーブポイントXXへのロールバック)、begin、commitなど、MySQLでサポートされているトランザクション制御ステートメントについて説明します。これらのステートメントを深く理解することで、読者は後続の実際の作業で複雑なトランザクション制御に直面できます。よく考えられており、簡単に実行できます。