Flyway は DB マイグレーションを実現するためのツールです。主に Java を対象としています。Rails におけるマイグレーション機能のようなものです。基本的な使い方をまとめます。
公式ドキュメント
Flyway は後述の Spring Boot プラグインや Java API 等によってアプリケーションから利用することもできますが、ここではコマンドラインから単体で Flyway を利用する場合を考えます。コマンドラインから利用する方法は複数提供されていますが、特に以下の三つを対象とします。
こちらのページの Command-line Tool
からコマンドをダウンロードして解凍します。
wget https://repo1.maven.org/maven2/org/flywaydb/flyway-commandline/4.2.0/flyway-commandline-4.2.0-linux-x64.tar.gz
tar zxvf flyway-commandline-4.2.0-linux-x64.tar.gz
こちらのページを参考に mvn コマンドをインストールします。以下のコマンドを実行してプロジェクトの雛形を生成します。
mvn archetype:generate -B \
-DarchetypeGroupId=org.apache.maven.archetypes \
-DarchetypeArtifactId=maven-archetype-quickstart \
-DarchetypeVersion=1.1 \
-DgroupId=foo \
-DartifactId=bar \
-Dversion=1.0-SNAPSHOT \
-Dpackage=foobar
pom.xml
は以下のように設定します。
<project ...>
...
<build>
<plugins>
<plugin>
<groupId>org.flywaydb</groupId>
<artifactId>flyway-maven-plugin</artifactId>
<version>4.2.0</version>
<configuration>
<url>jdbc:mysql://localhost:3306/mydb</url>
<user>root</user>
<password></password>
</configuration>
<dependencies>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>6.0.6</version>
</dependency>
</dependencies>
</plugin>
</plugins>
</build>
</project>
こちらのページを参考に Gradle コマンドをインストールします。build.gradle
は以下のように記載します。
buildscript {
dependencies {
classpath 'mysql:mysql-connector-java:6.0.6' // http://search.maven.org/#artifactdetails|mysql|mysql-connector-java|6.0.6|jar
}
}
plugins {
id "org.flywaydb.flyway" version "4.2.0"
}
flyway {
url = 'jdbc:mysql://localhost:3306/mydb'
user = 'root'
password = ''
}
タスクが追加されたことを確認します。
$ ./gradlew tasks
...
Flyway tasks
------------
flywayBaseline - Baselines an existing database, excluding all migrations up to and including baselineVersion.
flywayClean - Drops all objects in the configured schemas.
flywayInfo - Prints the details and status information about all the migrations.
flywayMigrate - Migrates the schema to the latest version.
flywayRepair - Repairs the Flyway metadata table.
flywayValidate - Validate applied migrations against resolved ones (on the filesystem or classpath) to detect accidental changes that may prevent the schema(s) from being recreated exactly. Validation fails if differences in migration names, types or checksums are found, versions have been applied that aren"t resolved locally anymore or versions have been resolved that haven"t been applied yet
設定ファイルを編集します。
vi conf/flyway.conf
以下のようにログイン情報を設定します。ここでは MySQL への接続を考えます。
flyway.url=jdbc:mysql://localhost:3306/mydb
flyway.user=root
flyway.password=
こちらのページの情報をもとに、マイグレーション用の SQL を用意します。
touch sql/V1__Create_person_table.sql
vi sql/V1__Create_person_table.sql
V1__Create_person_table.sql
というファイル名における「1」がマイグレーションバージョンです。Create_person_table
がマイグレーションの説明です。
CREATE TABLE person (
id INT NOT NULL,
name VARCHAR(100) NOT NULL
);
事前に mydb
を作成しておきます。
mysql> CREATE DATABASE mydb;
以下のコマンドでマイグレーションを実行します。
./flyway migrate
続けて以下のファイルを作成します。
V2__Add_people.sql
INSERT INTO person (id, name) VALUES (1, 'Axel');
INSERT INTO person (id, name) VALUES (2, 'Mr. Foo');
INSERT INTO person (id, name) VALUES (3, 'Ms. Bar');
再度マイグレーションを実行します。
./flyway migrate
以下のような状態になります。
$ ./flyway info
Flyway 4.2.0 by Boxfuse
Database: jdbc:mysql://localhost:3306/mydb (MySQL 5.5)
+---------+---------------------+---------------------+---------+
| Version | Description | Installed on | State |
+---------+---------------------+---------------------+---------+
| 1 | Create person table | 2017-04-04 19:43:42 | Success |
| 2 | Add people | 2017-04-04 19:45:02 | Success |
+---------+---------------------+---------------------+---------+
$ mysql -uroot mydb -e 'SHOW TABLES';
+----------------+
| Tables_in_mydb |
+----------------+
| person |
| schema_version |
+----------------+
$ mysql -uroot mydb -e 'SELECT * FROM schema_version'
+----------------+---------+---------------------+------+-----------------------------+-------------+--------------+---------------------+----------------+---------+
| installed_rank | version | description | type | script | checksum | installed_by | installed_on | execution_time | success |
+----------------+---------+---------------------+------+-----------------------------+-------------+--------------+---------------------+----------------+---------+
| 1 | 1 | Create person table | SQL | V1__Create_person_table.sql | -1455529326 | root | 2017-04-04 19:43:42 | 2 | 1 |
| 2 | 2 | Add people | SQL | V2__Add_people.sql | -1280448963 | root | 2017-04-04 19:45:02 | 0 | 1 |
+----------------+---------+---------------------+------+-----------------------------+-------------+--------------+---------------------+----------------+---------+
その他のコマンドには以下のようなものがあります。
DB Drop を実行して初期化します。Production 環境では絶対に実行してはいけないコマンドです。
./flyway clean
マイグレーションファイルに記載された情報が、DB に適用した時点から現在までに何らかの原因で書き換えられてしまっていないかどうかを検証します。
./flyway validate
マイグレーションファイルは src/main/resources/db/migration/
内に設置します。
mvn flyway:migrate
mvn flyway:clean
mvn flyway:info
mvn flyway:validate
マイグレーションファイルは src/main/resources/db/migration/
内に設置します。
./gradlew flywayMigrate
./gradlew flywayClean
./gradlew flywayInfo
./gradlew flywayValidate
こちらのページで環境構築の方法をまとめた Spring Boot から Flyway を利用することができます。アプリケーション起動時に DB マイグレーションが自動で実行されるようになります。
build.gradle
Flyway 公式ドキュメントに記載されているとおり、build.gradle に設定を追記します。
compile('org.flywaydb:flyway-core:4.2.0')
更に今回は MySQL を DB として利用するため、追加で以下の設定を行います。ちなみに、『Spring Batch サンプルコード』では、org.springframework.boot:spring-boot-starter-batch
が org.springframework.boot:spring-boot-starter-jdbc
に依存するため、明示的に設定する必要はありませんでした。
compile('org.springframework.boot:spring-boot-starter-jdbc')
compile('mysql:mysql-connector-java:6.0.6')
src/main/resources/application.yml
spring:
datasource:
url: jdbc:mysql://localhost:3306/mydb
username: myuser
password: myuser
driver-class-name: com.mysql.jdbc.Driver
src/main/resources/db/migration/V1__Create_person_table.sql
SQL ファイルの場所を変更したい場合は flyway.locations
を設定します。以下は既定の場所です。
DROP TABLE IF EXISTS people;
CREATE TABLE people (
person_id BIGINT NOT NULL AUTO_INCREMENT,
first_name VARCHAR(20),
last_name VARCHAR(20),
PRIMARY KEY (person_id)
);