PHPマイグレーションについて

採用はこちら

PHPにおけるマイグレーションとは、データベースの構造変更をコードで管理する仕組みのことです。

ここでいう構造変更とは、テーブルの作成、カラムの追加や削除、インデックスの設定、外部キーの追加などを指します。

Laravelでは、こうした変更を migration class として定義し、コマンドで適用・ロールバックできます。

Doctrine Migrations でも同様に、データベース変更を履歴として管理する考え方が採用されています。

目次

なぜマイグレーションが必要なのか

データベースの変更は、手作業でSQLを実行して進めることもできます。

ただし、そのやり方だけに頼ると、どの環境に何を反映したのか分かりにくくなり、開発メンバーごとにデータベース構造がズレる原因になります。

マイグレーションを使えば、変更内容をコードとして保存し、Gitなどで履歴を管理しながら、同じ変更を複数の環境に再現しやすくなります。

Doctrine Migrations でも、手動SQLではなく、安全にスキーマ変更を展開する方法として migrations が位置付けられています。

基本的な考え方

マイグレーションでは、通常は1つのファイルに1つの変更目的を持たせます。

たとえば、

  • usersテーブルを作成する
  • usersテーブルにphoneカラムを追加する
  • postsテーブルにindexを追加する

といった単位で分けて管理します。

Laravelでは migration class の中に up()down() を定義します。

up() は変更を適用する処理、down() はその変更を元に戻す処理です。

Doctrine Migrations でも、基本的には up / down を通じて変更と巻き戻しを扱います。

Laravelでのマイグレーション

Laravelでは、マイグレーションを使ってテーブル作成やカラム追加を行います。

マイグレーションは php artisan migrate で実行され、未適用のものだけが順番に反映されます。

また、Laravelは実行済みの migration をデータベース上で管理しており、どこまで適用済みかを追跡できる仕組みを持っています。

代表的なコマンドは次の通りです。

php artisan migrate
php artisan migrate:rollback
php artisan migrate:reset
php artisan migrate:refresh
php artisan migrate:fresh

それぞれの役割は概ね次のように理解できます。

  • migrate
    未適用の migration を実行する
  • migrate:rollback
    直近の batch をロールバックする
  • migrate:reset
    すべての migration をロールバックする
  • migrate:refresh
    一度すべて戻してから再度 migrate する
  • migrate:fresh
    テーブルを削除してから migrate を実行する

特に注意したいのは、migrate:rollback は「必ず1ファイルだけ戻す」わけではないという点です。

Laravel公式では、これは最後に実行した batch をロールバックするコマンドとして説明されています。

最後の batch に複数の migration が含まれていれば、それらがまとめて戻ることがあります。

Seederとの違い

マイグレーションと混同されやすいのが Seeder です。

この2つは役割が異なります。

  • Migration
    テーブルやカラム、インデックスなど、データベースの構造を変更する
  • Seeder
    初期データやテストデータ、マスタデータを投入する

つまり、マイグレーションは器を作るもので、Seederは中身を入れるものと考えると分かりやすいです。

LaravelでもSeederは別の仕組みとして用意されています。

生SQLを使うことはあるのか

あります。

Laravelには migration のための便利なAPIがありますが、すべての変更を抽象化だけで表現できるとは限りません。

そのため、実務では必要に応じて raw SQL を使うことがあります。

Doctrine Migrations でもSQLを直接扱う考え方が用意されています。

ただし、生SQLを使う場合は注意が必要です。

たとえば、MySQLでは動くSQLがPostgreSQLではそのまま使えないことがあります。

データベース製品をまたぐ可能性があるなら、できるだけ標準の migration API を使ったほうが安全です。

ロールバックは万能ではない

ここは実務でとても重要な点です。

down() が用意されているからといって、すべての変更が安全に元通りになるとは限りません。

たとえば、カラム削除やデータ変換を含む変更では、構造だけを戻せても、失われたデータそのものまでは復元できないことがあります。

さらに、DDLの扱いはデータベース製品によって異なり、トランザクションの安全性も一律ではありません。

Doctrine Migrations でも、変更内容やDBの種類によって扱いが変わることが示されています。

そのため、本番環境では

  • 事前バックアップを取る
  • nullableで追加してから段階的に必須化する
  • 旧仕様と新仕様を一時的に共存させる
  • データ移行を構造変更と分けて進める

といった慎重な進め方が重要になります。

これは公式コマンドを覚えること以上に、実務では大切な考え方です。

CakePHPとDoctrine系の位置づけ

PHPのマイグレーションはLaravelだけのものではありません。

Symfony系では Doctrine Migrations が広く使われており、データベース変更を履歴として管理するという思想は共通しています。

CakePHPでもマイグレーションは利用できますが、ここは少し注意が必要です。

古い文脈では Phinx ベースとして説明されることがありますが、CakePHP Migrations 5.x では Phinx 依存は外れており、builtin backend のみがサポートされています。

そのため、現在の説明としては「CakePHPでもマイグレーションは使えるが、現行では builtin backend を前提に考える」としておくのがより正確です。

初学者向けにわかりやすく言うと

マイグレーションとは、「データベース設計の変更履歴を、その場の手作業ではなく、再現可能なコードとして残す仕組み」です。

Web制作の感覚に近い言い方をすると、

  • HTMLやCSSの変更をファイルで管理する
  • WordPressテーマの修正履歴をGitで管理する

のと同じように、

  • データベース構造の変更もコードファイルとして管理する

というイメージです。

まとめ

PHPマイグレーションとは、データベースのスキーマ変更をコードとして管理する仕組みです。

Laravelでは up()down() を持つ migration class を使い、migraterollback などのコマンドで適用・巻き戻しを行います。

Doctrine系でも同じように、データベース変更を履歴として管理する考え方が採用されています。

ただし、運用上は注意も必要です。

rollback は単純に「1つ前のファイルを戻す」という意味ではなく、Laravelでは最後の batch を戻すのが正確です。

また、down() があるからといって、削除済みデータまで完全に元に戻せるとは限りません。

本番環境では、段階移行やバックアップを前提に、慎重に設計することが重要です。

以上、PHPマイグレーションについてでした。

最後までお読みいただき、ありがとうございました。

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!
目次