この記事について
| 環境 | mysqlのバージョンアップを伴うサーバー移行 |
|---|---|
| 目的 | 移行後に出るようになった mysqli_sql_exception を解消する |
| 結果 | sql_mode を NO_ENGINE_SUBSTITUTION にして STRICT_TRANS_TABLES を外して解決 |
つまずきポイント要約
- STRICT_TRANS_TABLES が有効だと、デフォルト値のないNOT NULLカラムへの空挿入がエラーになる
- sql_mode に明示的に STRICT_TRANS_TABLES を含めないことで無効化できる
- 設定は my.cnf の [mysqld] セクション。変更後は mysqld を再起動
事象
webサイトを新サーバーに移行してmysqlもバージョンアップしたがエラーが出るようになった
Fatal error: Uncaught mysqli_sql_exception: Field 'chk1_20170804' doesn't have a default value in /var/www/html/hyogen/input/check.php:207 Stack trace: #0 /var/www/html/hyogen/input/check.php(207): mysqli->query() #1 {main} thrown in /var/www/html/hyogen/input/check.php on line 207
原因
これはデータを更新するときにフィールドにデフォルト値が設定されていないときに発生する
MySQLのバージョンや設定によっては、STRICT_TRANS_TABLES モードが有効になっていると、デフォルト値が指定されていない NOT NULL カラムに対して空の値を挿入できず、エラーになる
対処
my.cnfおよびmy.cnf.d以下のファイル内の[mysqld]セクションを以下のように変更。[mysqld]セクション自体が見つからない場合は、my.cnfに追加
[mysqld]
sql_mode="NO_ENGINE_SUBSTITUTION"
[mysqld]は、MySQLサーバーに関する設定であることを意味する
再起動で設定を反映
sudo systemctl restart mysqld
どうしてこの設定で STRICT_TRANS_TABLES が無効になるのか?
sql_mode は、MySQLで使用されるSQLの動作モードを指定するもの。
STRICT_TRANS_TABLES がデフォルトで有効な場合、sql_mode に明示的に STRICT_TRANS_TABLES を含めないことで、その動作を無効化できる。
NO_ENGINE_SUBSTITUTION は、エンジンが指定されたときに存在しない場合、エラーを発生させる設定
補足
本来はカラムにデフォルト値を設定するか、INSERT時に全カラムを指定するのが筋。旧サーバーの挙動に合わせて一括で直すなら sql_mode 変更が手っ取り早い。
