## モジュール 5: オンラインDDLを使用してオンラインスキーマ変更を実行

+ このモジュールでは、進行中の**INSERTジョブ**が中断されることなく継続実行されることを保証しながら、**TiDB**で**オンラインスキーマ変更（DDL操作）**を実行する方法を示します。このプロセスの重要な課題は、スキーマ変更が一時的にトランザクションをブロックする際に発生する**エラーコード8028**を処理することです。このデモでは、スキーマ変更にもかかわらず**挿入ジョブ**が回復して継続できるようにする、このシナリオを管理する堅牢なアプローチを示します。

+ このモジュールは2つの主要な操作で構成されています：

1. **挿入ジョブ（`--insert`）**
   + 指定されたテーブルに新しいレコードを継続的に挿入します。
   + 同時DDL操作により発生する可能性のあるスキーマ変更例外（エラーコード**8028**）を処理します。
   + サービス可用性を維持するために、失敗した場合は挿入操作を再試行します。

2. **スキーマ変更（`--alter`）**
   + 挿入が進行中にテーブル構造を変更するために`ALTER TABLE`コマンドを実行します。
   + TiDBが**オンラインスキーマ変更**を許可することを示しますが、スキーマ変更によりトランザクションが一時的に失敗する可能性があります。
   + 進行中のトランザクションが適応する中で、新しいスキーマが正常に適用されることを保証します。

> [!TIP]
> **重要な実装詳細：**
>
> + **TiDBメタデータロックの処理**：スクリプトは**メタデータロックを無効化**（`SET GLOBAL tidb_enable_metadata_lock = OFF`）して、クエリをブロックせずにDDL変更を許可します。
> + **自動エラー処理**：挿入ジョブは**エラーコード8028を検出**し、クラッシュを防ぐために**失敗したトランザクションを再試行**します。
> + **同時実行**：スクリプトは**挿入ジョブ**と**スキーマ変更**を別々のターミナルで実行できるようにし、データベース更新が進行中のトランザクションと並行して発生する実際のシナリオをシミュレートします。

+ 最初に挿入ジョブを実行します。

  ```bash
  rm -f DemoJdbcOnlineDDL.class
  javac -cp mysql-connector-j-9.1.0.jar DemoJdbcOnlineDDL.java
  sleep 1
  java -cp :mysql-connector-j-9.1.0.jar DemoJdbcOnlineDDL --insert
  ```

  ```output
  ...
  Inserting record 0
  Inserting record 1
  Inserting record 2
  Inserting record 3
  Inserting record 4
  Inserting record 5
  ...
  ```

+ VS Codeで`+`ボタンをクリックして新しいターミナルを作成します。

  <![90%](https://lab-static.pingcap.com/images/2025/7/7/797b653f8fc9a08a362cf618d2fe7fb9ef960fad.jpeg)>

+ 新しいターミナルでスキーマ変更を実行します。

  ```bash
  source env.sh
  java -cp :mysql-connector-j-9.1.0.jar DemoJdbcOnlineDDL --alter
  ```

  ```output
  Executing ALTER TABLE on online_ddl_test
  Connected to TiDB: xxxxxx.xxxxxx@gateway01.us-west-2.prod.aws.tidbcloud.com:4000 using database test
  Table online_ddl_test exists, proceeding with ALTER TABLE
  Executing: ALTER TABLE online_ddl_test ADD COLUMN (ed VARCHAR(10) DEFAULT 'N/A')
  ALTER TABLE completed successfully in 0.39 seconds

  Updated table structure:
    id: int(11)
    k: int(11)
    c: char(120)
    pad: char(60)
    ed: varchar(10)
  ```

+ VS Codeで最初のターミナルに戻ると、挿入ジョブが再試行ログとともに継続していることがわかります。

  ```output
  ...
  Inserting record 105
  Inserting record 106
  Schema mutation encountered, retrying...
  Inserting record 107
  Inserting record 108
  ...
  ```

+ 挿入DMLもDDL操作もブロックされていません。

+ ターミナルで`CTRL + c`を使用して実行中の挿入プログラムを終了できます。
