FuelPHPのMagic Migrationsがうまく動作しないことがあったので調査した
FuelPHPのMagic Migrationsがうまく動作しない現象に悩まされたので、どのような状況で発生するのか検証しました。まだソースコードを追えていないので、ひとまず検証結果をメモしておきます。
結論から言うと、table_prefixを指定した状態で、ドライバがPDOだった場合、テーブルの削除 oil generate migration drop_tablenameと、フィールド名の変更 oil generate migration rename_field_oldname_to_newname_in_tablenameが思うように機能しませんでした。
開発環境
環境は以下の通りで、各種ソフトウェアはインストール済みという前提で進めます。パスやバージョン等は、必要に応じて読み替えてください。
ソフトウェア | バージョン | 備考 |
---|---|---|
MAMP | 2.0.5 | – |
MySQL | 5.5.9 | MAMPのMySQLを使うものとする |
PHP | 5.3.6 | MAMPのPHPを使うものとする |
FuelPHP | 1.3 | /User/username/work/fuelphp に配置しているとする * |
* usernameには、Macのユーザ名が入ります。
Magic Migrations について
検証を行う前にマジックマイグレーションについて確認をします。
There are a number of “magic” migrations which automatically build you a migration based on a prefix to your migration name.
引用元:Magic Migrations : Generate – Oil Package – FuelPHP Documentation
上記にある通り、マジックマイグレーションとは、マイグレーション名のプレフィックスに基づいて、自動的にマイグレーションを構築するFuelPHPの機能のことです。例えば、以下のようなものです。赤い部分に基づいて自動的にマイグレーションを構築します。
# テーブルの作成
oil generate migration create_users name:text email:string[50] password:string[125] memo:text
# テーブル名の変更
oil generate migration rename_table_users_to_accounts
# フィールドの追加
oil generate migration add_bio_to_accounts bio:text
# フィールド名の変更
oil generate migration rename_field_name_to_username_in_accounts
# テーブルの削除
oil generate migration drop_accounts
検証
以下の4つのパターンを検証しました。
- table_prefix:なし / ドライバ:PDO
- table_prefix:なし / ドライバ:mysqli
- table_prefix:あり / ドライバ:PDO
- table_prefix:あり / ドライバ:mysqli
パターン1 – table_prefix:なし / ドライバ:PDO
こちらはFuelPHPの初期設定です。結果は以下の通りで、期待通りの動作となりました。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | # テーブルの作成 oil generate migration create_users name:text email:string[50] password:string[125] Creating migration: /Users/mawatari/work/fuelphp/fuel/app/migrations/001_create_users.php oil r migrate Performed migrations for app:default: 001_create_users # テーブル名の変更 oil generate migration rename_table_users_to_accounts Creating migration: /Users/mawatari/work/fuelphp/fuel/app/migrations/002_rename_table_users_to_accounts.php oil r migrate Performed migrations for app:default: 002_rename_table_users_to_accounts # フィールドの追加 oil generate migration add_bio_to_accounts bio:text Creating migration: /Users/mawatari/work/fuelphp/fuel/app/migrations/003_add_bio_to_accounts.php oil r migrate Performed migrations for app:default: 003_add_bio_to_accounts # フィールド名の変更 oil generate migration rename_field_name_to_username_in_accounts Creating migration: /Users/mawatari/work/fuelphp/fuel/app/migrations/004_rename_field_name_to_username_in_accounts.php oil r migrate Performed migrations for app:default: 004_rename_field_name_to_username_in_accounts # テーブルの削除 oil generate migration drop_accounts Creating migration: /Users/mawatari/work/fuelphp/fuel/app/migrations/005_drop_accounts.php oil r migrate Performed migrations for app:default: 005_drop_accounts |
パターン2 – table_prefix:なし / ドライバ:mysqli
ドライバをmysqliに変更して検証します。 db.phpを以下のように修正しました。結果はパターン1と全く同じでしたので割愛します。
参考リンク:Database Introduction – Class – FuelPHP Documentation
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | <?php /** * The development database settings. */ return array( 'default' => array( 'type' => 'mysqli', 'connection' => array( 'hostname' => 'localhost', 'port' => '3306', 'database' => 'fuel_db', 'username' => 'your_username', 'password' => 'y0uR_p@ssW0rd', 'persistent' => false, ), ), ); |
パターン3 – table_prefix:あり / ドライバ:PDO
ドライバをPDOに戻し、 'table_prefix' => 'pr_'を追記しました。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | <?php /** * The development database settings. */ return array( 'default' => array( 'connection' => array( 'dsn' => 'mysql:host=localhost;dbname=fuel_db;charset=utf8', 'username' => 'your_username', 'password' => 'y0uR_p@ssW0rd', ), ), ); |
18 19 20 21 22 | // 省略 'identifier' => '`', 'table_prefix' => 'pr_', 'charset' => 'utf8', // 省略 |
oilコマンドでマイグレーションの構築を行ったところ、フィールド名の変更とテーブルの削除でエラーが出てしまいました。エラーメッセージを見ると、プレフィックスがついていないため、テーブルを見つけることができていないようです。
1 2 3 4 5 6 7 8 9 | # create, rename_table, add は、パターン1と同様の結果を示すため省略 # フィールド名の変更 oil generate migration rename_field_name_to_username_in_accounts 42S02 - SQLSTATE[42S02]: Base table or view not found: 1146 Table 'fuel.accounts' doesn't exist in COREPATH/classes/database/pdo/connection.php on line 233 # テーブルの削除 oil generate migration drop_accounts 42S02 - SQLSTATE[42S02]: Base table or view not found: 1146 Table 'fuel.accounts' doesn't exist in COREPATH/classes/database/pdo/connection.php on line 233 |
パターン4 – table_prefix:あり / ドライバ:mysqli
ドライバをmysqliに変更して実行したところ、table_prefixを指定した状態でも正常に終了しました。結果はパターン1と全く同じでしたので割愛します。
検証結果
table_prefixを指定した状態で、ドライバがPDOだった場合、テーブルの削除と、フィールド名の変更が失敗することがわかりました。
ドライバ:PDO | ドライバ:mysqli | |
---|---|---|
table_prefix:なし | ○ | ○ |
table_prefix:あり | × | ○ |
MySQLのクエリログを見てみると、ドライバがPDOの時は、プレフィックスがつけられていないことが見て取れます。
参考リンク:MAMPでMySQLのクエリログを出力する
1 2 3 4 5 6 7 8 9 10 11 12 13 | -- パターン3のDrop Magic Migrationのログ Command Argument Connect root@localhost on fuel_db Query SET NAMES 'utf8' Query DESCRIBE accounts Quit -- パターン4のDrop Magic Migrationのログ Command Argument Connect root@localhost on fuel_db Query SET NAMES utf8 Query SHOW FULL COLUMNS FROM `pr_accounts` Quit |
とりあえず、ここまで。どうすればPDOでもMagic Migrationsを完全に利用できるようになるのかは、時間があるときにでも調査してみたいと思います。それまでは、table_prefixを指定した状態で、Magic Migrationsを使う場合は、ドライバをmysqliにすることで対応します。