KimuraTweetこんにちは。リスペクトの木村です。雪もすっかり解け、いよいよ春が待ち遠しい季節となりましたがいかがお過ごしでしょうか。暖かくなると共にそろそろ花粉も飛び始めますので、長年花粉症を患っている身としては少し憂鬱になってきました・・・。そんな今回は、VagrantのProvision機能を利用して、仮想環境内のDBにマイグレーションを行ってみた、という話題をお送りします。想定している読者Vagrantでの開発に慣れている※Vagrantって何?という人は、以下のサイトがわかりやすく説明してますのでご一読ください。http://weblabo.oscasierra.net/vagrant/SQLについての知識が多少あるマイグレーションは少し面倒だと思っているけど、そろそろ本腰入れてやらないと・・・とも思っているという方です。(要は自分です・・・。弊社は最近までレガシーな環境(バージョン管理を使用していなかったり、テスト環境を複数人で共有していたり・・・)だったのですが、少しずつGitやVagrantといった開発環境を利用しつつあります。DBもそろそろ構成管理をしなければと思っていたのですが、これも以下のような理由でなかなか進みませんでした。スクラッチで開発したアプリケーションの場合は、マイグレーションが標準で備わっていないため、一から準備する必要があるフレームワークを利用している場合は、マイグレーション機能が備わってたりプラグインで実現できる場合が殆どですが、フレームワーク毎に学習コストがかかってしまう。up時に実行できるスタンドアロンで動作するマイグレーションツールと組み合わせれば、言語やフレームワークに依存せず使えるという所に目を付け、今回はVagrantに「Flyway」を組み合わせて、実装を行ってみました。APIやMaven、ANTからだけではなくコマンドラインからでも実行できるため、Java以外でも利用できます。その為、Javaが利用できる環境であれば言語やフレームワークに依存せずにマイグレーション作業を行えます。マイグレーション時に使うファイルの中身はSQLクエリをそのまま書けば良いため、新たに構文を覚える必要があまり無いのも嬉しい所です。難点として、生のSQLを使っているせいかマイグレーションのロールバックができませんので、そこは割り切って使う必要があります。)」というのもあります。(こちらもJava製)簡単に比較してみるとこんな感じです。参考にどうぞ)比較したのを見てみると、対象となるシステムや環境がそこそこ違っているように見えます。Flywayは小~中規模のシステム向きでシンプルに扱え、Liquibaseは大規模なシステム向きで高度なマイグレーションを行えるが若干じゃじゃ馬、といった所でしょうか。今回はLiquibaseまでの機能を求めていないなかったり覚える事も多いため、とっかかりやすそうなFlywayを採用しています。今回は次のような環境で構築しています。3.1今回はMySQLを使用します。他のRDBMSの場合は、別途JDBCのドライバが必要だったり、DBへ接続する時の構文が少し異なります。LAMP環境が構築済みのBoxを使っているので、他のBoxを使う場合は必要に応じて導入して下さい。手順では、実際に導入〜実行までやってみます。適当なDBを作成しておいて下さい。今回は「test_migration」というテーブルを作成しましたので、これを利用します。Flywayの導入Flywayを利用するため、次のものを導入します。入っていない場合は導入する必要があります。Toolを使用します。FlywayからMySQLを制御するために導入します。JavaとFlywayを導入します。flyway-3.1/flywayと入力してFlywayを実行して、コマンド一覧が出てくるか確認します。command(以下略)出てくるのを確認したら、次はJDBCドライバを導入します。flyway-3.1/drivers/これで導入完了です。続いて、マイグレーションファイル(クエリ)を作成します。デフォルトの命名規則は「V(バージョンナンバー)__(概要).sql」なので、「V1__add_testtable.sql」というファイル名で作成し、flyway-3.1内にある「sql」ディレクトリに置いておきます。)sqlディレクトリにあるマイグレーションファイルが、バージョンに沿って順次実行されます。TABLE文を書きます。試せる環境は整いましたので、Flyway単独でマイグレーションを実行してみます。今回は検証なのでパスを通さずに実行していますが、今後常用するようであれば別途パスを通しておくと良いかもしれません。-password=hogehoge今回指定したオプションはこんな中身です。詳細な出力を表示するデバッグモードです。JDBCの接続文字列です。いう書き方で記述します。接続に使用するユーザーです。ユーザーに紐付くパスワードです。実行してみるとズラズラと長ーく出力されますが、-Xでデバッグモードが有効なためです。(付いてない場合は、「DEBUG:」から始まっていない行のみが出力されるので、短くなります。schema」と表示されれば成功です。tablesすると、V1__add_test_table.sqlでcreateした「testtable」と、マイグレーション管理テーブルである「schema_version」が作成されています。sec)ここまでで、一通りの動作確認ができました。test_migrationテーブルにあるtesttableとschema_versionはdropして、最初の状態に戻しておきます。続けて、Vagrantと連動するのに必要なシェルスクリプトを作成します。今回はVagrantで立ち上げた仮想環境内に作成せず、ローカル環境のVagrantfileがあるディレクトリ下に色々作成するようにします。Vagrantfileがある所は/vagrant/としてデフォルトでマウントされ、ローカル環境とのやりとりがしやすいためです。構成図にするとこんな感じです。...ただ、実運用では別の場所にGitリポジトリがありそこにsynced_folderでマウントしているという場合も多いと思います。その場合は、上記のroot_folderをマウント先にしたり、スクリプトは上の構成に沿って作成して、マイグレーション用SQLだけsynced_folderでマウントした先を参照するようにする事も可能です。run.shの中身はFlywayを実行するだけですので、こんな感じです。先ほど実行したスクリプトと若干オプションが変化しています。-locations=filesystem:/vagrant/migrate/sql/違いは、-Xオプションを使用していない所と、1つオプションが増えている所です。マイグレーションファイルがある場所を指定します。今回はゲスト側から見た場合の/vagrant/migrate/sql/に作成したので、「/vagrant/migrate/sql」を指定しています。SQLディレクトリを別にマウントした場合は、引数の「filesystem:」以降のパスをsynced_folderでマウントした先にある管理ディレクトリのパスに置き換えて下さい。Vagrantfileへの設定provisionでコマンドを実行させるにはVagrantfileにスクリプトのパスを指定する必要があるので、指定します。1行追加するだけですので、一番下の「end」の手前の行に記述しておきます。"./migrate/script/run.sh"Vagrantfileのあるディレクトリ下に置いて無い場合は、パスをスクリプトがある先に書き換えると、同じように動作します。provisionで実行してみます。schema」と表示され、テーブルが2つ作成されていれば成功です。まとめという訳で、Vagrant環境上のDBマイグレーションがお手軽に行えました。provisionを実行するだけでマイグレーションされるようになりますし、destroyしてupした場合はprovisionが自動で実行されるため、自動で最新の状態になってくれます。そのため、複数人で作業する時は、ある程度同じようなDB環境で作業できるのではないかと思います。tableしか使っていませんが、もちろんinsertやupdate/deleteも使えますので、テストデータの追加や擬似的なロールバック的な事も行えます。簡易的でもいいからマイグレーションに手を出してみたいという方や、複数人の環境でDBの状況を保ちたいなと考えている方は是非お試し下さい。navigationFuelPHPのOrmとキャッシュについてのTips【導入決定!】PHP7で実装されるスカラー型宣言とは?株式会社リスペクトという、仙台・東京に拠点を持つ会社のシステム部門のブログです。プログラミングやシステム運用のノウハウなどを公開していきます。