【Aurora MySQL 5.7 -> 8.0】アップグレードすると起動しない罠

# お前はこれまでEOLを通り越した回数を覚えているのか。
忘れた、笑。

オンプレでは Firewall の中で動作しているから問題なしって
一体どこの口から出た出まかせ（表現）。

本題；Amazon Aurora マイナーバージョン
https://docs.aws.amazon.com/ja_jp/AmazonRDS/latest/AuroraUserGuide/Aurora.VersionPolicy.html#Aurora.VersionPolicy.MinorVersions

| Aurora MySQL ver. | Release | EOL |
|:-:|:-:|:-:|
3.05（MySQL8.0.32） | 2023年10月 | 2025年1月　
3.04（MySQL8.0.28）| 2023年7月 | 2026年10月　
3.02（MySQL8.0.26） | 2023年3月 | 2024年5月 
3.01（MySQL8.0.23） | 2022年4月 | 2024年1月 
2.12（MySQL5.7.40） | 2023年7月 | 2024年10月 
2.11（MySQL5.7.12） | 2022年10月 | 2024年10月 
2.07（MySQL5.7.12） | 2019年11月 | 2024年4月 

みなさん、お手持ちのバージョンはどこに該当しているか分かりますかしら。
もちろん私は 2.07 ・・・。ていうか早速切れてるし。誰だ！

嫌なことは忘れるようにしていたものの、クラウドで運用しているからには
EOLになる前にバージョンアップが必要です。

みんなでのっかっていきましょう。


## Aurora MySQL 5.7 のお尻を叩くと失敗。

メジャーバージョンアップをする場合には互換具合が気になりますよね
ひとまず延命措置で 2.11.x に変更してから
メジャーバージョンアップを試みる人がいるかもしれません。わたしも。

Aurora 2.x の長期サポートバージョンである 2.11.4 にひとまずあげたら
お尻が今年の 10月まで伸びました！（注；先延ばし。）

それだけでも短期間だったので結構、大変でしたが。
ひとまず乗り越えた直後、体温が高いうちに
開発環境のDBをメジャーバージョンアップすることに。

```python
May 25, 2024, 16:41 (UTC+09:00)	DB cluster created
May 25, 2024, 17:00 (UTC+09:00)	Database cluster engine version upgrade started.
May 25, 2024, 17:01 (UTC+09:00)	Upgrade preparation in progress: Starting online upgrade prechecks.
May 25, 2024, 17:01 (UTC+09:00)	Upgrade preparation in progress: Completed online upgrade prechecks.
May 25, 2024, 17:02 (UTC+09:00)	Upgrade preparation in progress: Starting offline upgrade prechecks.
May 25, 2024, 17:02 (UTC+09:00)	Upgrade preparation in progress: Completed offline upgrade prechecks.
May 25, 2024, 17:03 (UTC+09:00)	Upgrade in progress: Creating pre-upgrade snapshot [preupgrade-new-dev-yamada-cls-80-cluster-5-7-mysql-aurora-2-11-4-to-8-0-mysql-aurora-3-04-2-2024-05-24-10-00].
May 25, 2024, 17:05 (UTC+09:00)	Upgrade in progress: Cloning volume.
May 25, 2024, 17:07 (UTC+09:00)	Upgrade in progress: Purging undo records for old row versions. Records remaining: 2335
May 25, 2024, 17:09 (UTC+09:00)	Upgrade in progress: Purging undo records for old row versions. Records remaining: 2335
May 25, 2024, 17:10 (UTC+09:00)	Database cluster is in a state that cannot be upgraded: Engine bootstrap failed with no mysqld process running...
```

ていうか <b>失敗</b> 。

なんだこのメッセージ。mysqld が起動していないですって。
同件を探すとメモリが少ないとか言われている事例があるみたいですが
db.r5.large
一応最小構成です。

パラメタグループ一応変更前に設定していたものは全部引き継ぐように
ちくちく設定したのに。何故。

ひとまずぐぐると。

https://repost.aws/ja/questions/QUcB03dIuKROaLbNZdVulDnQ/aurora-mysql-database-cluster-is-in-a-state-that-cannot-be-upgraded-engine-bootstrap-failed-with-no-mysqld-process-running

:::note
承認された回答
I have created a technical case for AWS Support to investigate the issue. It was due to table schema comments that contain invalid UTF-8 characters. After I remove the comment then Aurora can do the upgrade smoothly.
:::

スキーマコメントに UTF-8 で無効な文字があるからですって。
なんだそれ。どうやって調べたのかしら。

ひとまず AWS サポートに聞けばいいのか。先が長そうなので黙祷。

MySQL 8 で予約語になった単語がテーブル名とか項目名にあると
そのままでは動かないって聞いたので早くやってみたいのに
DBすら起動ができないのは日頃の行いかしら。

対策方法が明確になったら追記すること（明日の自分に・・・・。

## 予約語

ちまたでは RANK という単語が MySQL 8 で予約語になったので
要修正（エスケープ）が必要って話題があふれています。

https://dev.mysql.com/doc/refman/8.0/en/keywords.html

手元のテーブル名、項目名と上記ページの一覧を突合したら大惨事。
テーブル名の users とか項目名の status とか衝突しまくり。
まじか。
こんな状態でアップデートなどできるわけがない。

https://dev.mysql.com/doc/refman/5.7/en/keywords.html

ていうかよくみたら 5.7 でも status は予約語・・・。
あれ。動いていますけど？

https://dev.mysql.com/doc/refman/8.0/en/information-schema-keywords-table.html

:::note
影響する対象は以下の単語のみ
SELECT WORD FROM INFORMATION_SCHEMA.KEYWORDS WHERE RESERVED = 1;

These queries lists all keywords, all reserved keywords, and all nonreserved keywords, respectively:
:::

ていうか影響ない単語なんて一覧に書かないでください罠

## バージョンアップに失敗した原因

サポート先生に問合せをしてから５日目。問題は解決しました。

ていうか。当日エラーメッセージでぐぐった無効な文字と同件 orz
まじか orz

具体的にはTABLE COMMENT もしくは TABLE COLUMN COOMMENT に
UTF-8 以外の文字コード（Shift JIS）で設定していたことが原因。

決して不適切な文字ではないです。
欧州のGDPRや公安の何かに検知されてNGとなったわけではないです
かつての作業ミス。

とはいえテーブル数が 1,000個以上とか古い時代から運用していると
誰がコメント設定したのか分からない人とかいると思いますので
当該事象をトラブルシュートの方法を記載しておきます。

### トラブルシューティング方法

Aurora メジャーバージョンアップしたとき
upgrade-prechecks には成功したけど何故か失敗したとき

Engine bootstrap failed with no mysqld process running...

イベントログに上記のメッセージが出た場合にはラッキーです。

その場合はあわてず騒がず mysql-error-running.log を開く。
このファイル、正直者にはエラーが見つけにくくなっています（嘘

```python
先頭

2024-05-24T17:02:03.374009Z 0 [Note] #
2024-05-24T17:02:03.374050Z 0 [Note] #
2024-05-24T17:02:03.374052Z 0 [Note] #
2024-05-24T17:02:03.374053Z 0 [Note] #
2024-05-24T17:02:03.374054Z 0 [Note] #
2024-05-24T17:02:03.374055Z 0 [Note] #
2024-05-24T17:02:03.374056Z 0 [Note] #
2024-05-24T17:02:03.374057Z 0 [Note] #
2024-05-24T17:02:03.374058Z 0 [Note] #
2024-05-24T17:02:03.374059Z 0 [Note] #
2024-05-24T17:02:03.374060Z 0 [Note] MYSQL57 STARTING UP...
2024-05-24T17:07:02.932925Z 0 [Note] #
2024-05-24T17:07:03.067692Z 0 [Warning] 'NO_AUTO_CREATE_USER' sql mode was not set.
2024-05-24T17:07:03.067902Z 0 [Note] /rdsdbbin/oscar/bin/mysqld (mysqld 5.7.12) starting as process 306 ...
2024-05-24T17:07:03.083393Z 0 [Warning] InnoDB: Setting innodb_checksums to OFF is DEPRECATED. This option may be removed in future releases. You should set innodb_checksum_algorithm=NONE instead.
2024-05-24T17:07:03.083474Z 0 [Note] InnoDB: PUNCH HOLE support available
2024-05-24T17:07:03.083488Z 0 [Note] InnoDB: Mutexes and rw_locks use GCC atomic builtins
2024-05-24T17:07:03.083493Z 0 [Note] InnoDB: Uses event mutexes
2024-05-24T17:07:03.083498Z 0 [Note] InnoDB: GCC builtin __atomic_thread_fence() is used for memory barrier
2024-05-24T17:07:03.083502Z 0 [Note] InnoDB: Compressed tables use zlib 1.2.13
2024-05-24 17:07:03 0x15266d50f940[IB_LOG_LEVEL_INFO]:Initializing buffer pool, size = 7.7G (srv0start.cc:4341)
```

```python
最後

2024-05-24T17:12:30.827254Z 0 [Note] Recovering after a crash using /rdsdbdata/log/binlog/mysql-bin-changelog
2024-05-24T17:12:30.827274Z 0 [Note] Starting crash recovery...
2024-05-24T17:12:30.827301Z 0 [Note] Crash recovery finished.
2024-05-24T17:12:30.870138Z 0 [Note] InnoDB: Last MySQL binlog file position 0 150, file name mysql-bin-changelog.002735
2024-05-24T17:12:30.877560Z 0 [Note] Skipping generation of SSL certificates as options related to SSL are specified.
2024-05-24T17:12:30.878186Z 0 [Note] Skipping generation of RSA key pair as key files are present in data directory.
2024-05-24T17:12:30.878506Z 0 [Note] Server hostname (bind-address): '*'; port: 3306
2024-05-24T17:12:30.878537Z 0 [Note] IPv6 is available.
2024-05-24T17:12:30.878562Z 0 [Note]   - '::' resolves to '::';
2024-05-24T17:12:30.878756Z 0 [Note] Server socket created on IP: '::'.
2024-05-24T17:12:31.165888Z 0 [Note] Event Scheduler: Loaded 0 events
2024-05-24T17:12:31.729031Z 0 [Note] /rdsdbbin/oscar/bin/mysqld: ready for connections.
Version: '5.7.12-log'  socket: '/tmp/mysql.sock'  port: 3306  MySQL Community Server (GPL)

```

<b>まんなかをみよ</b>、笑。

ていうか目が節穴。
テキストファイルなんだから ERROR で grep しましょう。

```python
ファイルの真ん中；犯人部分

2024-05-24T17:09:36.181819Z 1 [Warning] [MY-010995] [Server] Error in renaming mysql_index_stats.ibd. (upgrade.cc:193)
2024-05-24T17:09:36.181831Z 1 [Warning] [MY-010995] [Server] Error in renaming mysql_index_stats.ibd. (upgrade.cc:204)
2024-05-24T17:09:36.255951Z 0 [Note] [MY-010990] [Server] Resource group feature shall not be available. Incompatible thread handling option. (resource_group_mgr.h:132)
2024-05-24T17:09:40.218288Z 2 [ERROR] [MY-013140] [Server] Comment for table 'yamadb.order' contains an invalid utf8mb3 character string: '\x97\x8e\x82\xc6\x82\xb5\x8c\x8a'.
2024-05-24T17:09:47.523644Z 2 [Warning] [MY-010778] [Server] Parsing 'mysql.rds_collect_global_status_history' routine body failed. Creating routine without parsing routine body (routine.cc:440)
2024-05-24T17:09:47.533558Z 2 [Warning] [MY-010778] [Server] Parsing 'mysql.rds_set_gsh_collector' routine body failed. Creating routine without parsing routine body (routine.cc:440)
2024-05-24T17:09:47.533860Z 2 [Warning] [MY-010778] [Server] Parsing 'mysql.rds_set_gsh_rotation' routine body failed. Creating routine without parsing routine body (routine.cc:440)
2024-05-24T17:09:48.040187Z 0 [ERROR] [MY-010022] [Server] Failed to Populate DD tables. (mysqld.cc:7776)
2024-05-24T17:09:48.040357Z 0 [ERROR] [MY-010119] [Server] Aborting (mysqld.cc:3316)
2024-05-24T17:09:48.040407Z 0 [Note] [MY-012330] [InnoDB] FTS optimize thread exiting. (fts0opt.cc:2925)
10:09:48 UTC - mysqld got signal 11 ;
Most likely, you have hit a bug, but this error can also be caused by malfunctioning hardware.
Thread pointer: 0x0

```

ていうか Aborting しているし笑

yamadb.order のコメントに無効な utf8mb3 文字列が含まれています
なんだそれ。
むしろ予約語をテーブル名に使うな（そこ

なにが設定されているのかと確認をするのは少し難易度高いです

show コマンドでは何も出てきません。

```sql
> show table status like 'order';

+-------+--------+---------+------------+-------+----------------+-------------+-----------------+--------------+-----------+----------------+-------------+---------------------+------------+-----------------+----------+----------------+---------+
| Name  | Engine | Version | Row_format | Rows  | Avg_row_length | Data_length | Max_data_length | Index_length | Data_free | Auto_increment | Create_time | Update_time         | Check_time | Collation       | Checksum | Create_options | Comment |
+-------+--------+---------+------------+-------+----------------+-------------+-----------------+--------------+-----------+----------------+-------------+---------------------+------------+-----------------+----------+----------------+---------+
| order | InnoDB |      10 | Dynamic    | 53464 |           1811 |    96862208 |               0 |     34226176 |  33554432 |       80008745 | NULL        | 2024-05-31 17:05:08 | NULL       | utf8_general_ci |     NULL | partitioned    |         |
+-------+--------+---------+------------+-------+----------------+-------------+-----------------+--------------+-----------+----------------+-------------+---------------------+------------+-----------------+----------+----------------+---------+

> show full columns from `order`;

+------------+------------------+-----------------+------+-----+---------+----------------+---------------------------------+---------+
| Field      | Type             | Collation       | Null | Key | Default | Extra          | Privileges                      | Comment |
+------------+------------------+-----------------+------+-----+---------+----------------+---------------------------------+---------+
| id         | int(10) unsigned | NULL            | NO   | PRI | NULL    | auto_increment | select,insert,update,references |         |
| voucher_no | varchar(20)      | utf8_general_ci | YES  |     | NULL    |                | select,insert,update,references |         |
+------------+------------------+-----------------+------+-----+---------+----------------+---------------------------------+---------+
```

information_schema でも見えない

```python
select table_name, table_comment
from information_schema.tables
where table_name = 'order'

+------------+---------------+
| TABLE_NAME | TABLE_COMMENT |
+------------+---------------+
| order     |               |
+------------+---------------+

select table_name, column_name, column_type, is_nullable, column_key, column_default, extra, column_comment
from information_schema.columns
where table_name = 'order'

+------------+-------------+------------------+-------------+------------+----------------+----------------+----------------+
| TABLE_NAME | COLUMN_NAME | COLUMN_TYPE      | IS_NULLABLE | COLUMN_KEY | COLUMN_DEFAULT | EXTRA          | COLUMN_COMMENT |
+------------+-------------+------------------+-------------+------------+----------------+----------------+----------------+
| order      | id          | int(10) unsigned | NO          | PRI        | NULL           | auto_increment |                |
| order      | voucher_no  | varchar(20)      | YES         |            | NULL           |                |                |
+------------+-------------+------------------+-------------+------------+----------------+----------------+----------------
```

むむむ。

```python
> show create table `order`;

+--------+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Table  | Create Table                                                                                                                                                                                                      |
+--------+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| order | CREATE TABLE `order` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `voucher_no` varchar(20) DEFAULT NULL COMMENT '�`�[�ԍ�',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='���Ƃ���'             |
+--------+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
```

ｷﾞｬｰ

show create table を利用したときだけ目視で分かる罠
まじか。

1000個以上のテーブルに show create table とか入力したとて
目視するのは嫌。

小人さんにやってもらうしかない（注；新人に丸投げではない

### 大人の解決方法

・show create table を大量生産するスクリプトを作成

```sql
show.sql

SELECT
 CONCAT('SHOW CREATE TABLE `', table_name, '`;') AS show_create_table_query
FROM information_schema.tables
where table_schema = 'yamadb';
```

・スクリプトを実行

```sql
# create table を作成する
mysql -u ${USER_NAME} -p -h ${DATABASE} yamadb -N < show.sql > create_table.sql

# create table を出力する
mysql -u ${USER_NAME} -p -h ${DATABASE} yamadb -N < create_table.sql > create_table.txt

```

・出力された中身を確認

```python
% cat create_table.txt
Table   Create Table
order  CREATE TABLE `order` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `voucher_no` varchar(20) DEFAULT NULL COMMENT '�`�[�ԍ�',\n  PRIMARY KEY (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='���Ƃ���'
Table	Create Table
store	CREATE TABLE `store` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `store_name` varchar(255) DEFAULT NULL) ENGINE=InnoDB AUTO_INCREMENT=119429 DEFAULT CHARSET=utf8
　；

鬼沢山
```

こんな感じ.テーブルの件数が少ない場合はこれでほぼ解決。
あとはなんかいやなデータを探して ALTER TABLE しまくってください。

・駄目なデータを探す

目視をしたくない（できない場合はこんな感じで

```python
> python detect_encoding.py create_table.txt | grep -v UTF-8
b"order\tCREATE TABLE `order` (\\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\\n  `voucher_no` varchar(20) DEFAULT NULL COMMENT '\x93`\x95[\x94\xd4\x8d\x86',\\n  PRIMARY KEY (`id`)\\n) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='\x97\x8e\x82\xc6\x82\xb5\x8c\x8a'\n"
```

ここに出てきたのは全部要対処。もし数億レコードのテーブルが出たら
即座に ALTER TABLE の日程調整開始。

<details><summary>某スクリプトｗ</summary>

```python
import sys
import codecs

def detect_encoding(file_path):
    with open(file_path, 'rb') as file:
        for line in file:
            try:
                line.decode('utf-8')
                print("UTF-8")
            except UnicodeDecodeError:
                try:
                    line.decode('shift_jis')
                    print("ShiftJIS")
                    print(line)
                except UnicodeDecodeError:
                    print("Unknown")
                    print(line)

if __name__ == "__main__":
    if len(sys.argv) != 2:
        print("Usage: python detect_encoding.py <file_path>")
        sys.exit(1)

    file_path = sys.argv[1]
    detect_encoding(file_path)
```
</details>


これで過去の遺跡も含まれる環境だって笑顔で立ち向かえます。

いつも心に太陽を。
これでアップグレードなんて怖くない（結論、嬉しくはない orz