遗留应用的 Flyway 部分迁移
Flyway partial migration of legacy application
在我们想要用 Flyway 替换的自定义数据库迁移器的应用程序中。
这些迁移分为一些类别,例如用于用户管理的 "account" 和用于产品目录的 "catalog"。
文件名为 $category.migration.$version.sql
。这里,$category
是上述类别之一,$version
是从0开始的整数版本。
例如account.migration.23.sql
虽然有人可能会争辩说每个类别都应该是一个单独的数据库,但实际上并非如此,需要进行重大重构才能改变这一点。
我也可以为每个类别使用一个模式,但这同样需要重写所有 SQL 查询。
所以我做了以下事情:
- 将
$category.migration.$version.sql
移动到 /sql/$category/V$version__$category.sql
(例如 account.migration.1.sql
变为 /sql/account/V1_account.sql
)
- 每个类别使用元数据table
- 将基准版本设置为零
在代码中
String[] _categories = new String[] { "catalog", "account" };
for (String _category : _categories) {
Flyway _flyway = new Flyway();
_flyway.setDataSource(databaseUrl.getUrl(), databaseUrl.getUser(), databaseUrl.getPassword());
_flyway.setBaselineVersion(MigrationVersion.fromVersion("0"));
_flyway.setLocations("classpath:/sql/" + applicationName);
_flyway.setTarget(MigrationVersion.fromVersion(_version + ""));
_flyway.setTable(category + "_schema_version");
_flyway.setBaselineOnMigrate(true); // (1)
_flyway.migrate();
}
所以会有元数据 tables catalog_schema_version
和 account_schema_version
.
现问题如下:
从一个空数据库开始,我想按类别应用所有预先存在的迁移,如上所述。
如果我删除 _flyway.setBaselineOnMigrate(true);
(1),那么 catalog
迁移(第一个)会成功,但它会抱怨 account
模式 public
不为空。
同样设置 _flyway.setBaselineOnMigrate(true);
会导致以下行为:
"catalog" 的迁移成功但 V0_account.sql
被忽略并且 Flyway 以 V1_account.sql
开头,可能是因为它仍然以某种方式认为数据库已经基线化?
有没有人有解决问题的建议?
最简单的解决方案是将 schema_version
表分别保存在另一个架构中。我已经回答了 .
根据您对 baseline
的观察,这些是预期的特征。 account
的迁移从 v1
开始,因为结合了 baseline=0
、baselineOnMigrate=true
和非空目标模式(因为 catalog
已经填充了它)Flyway 有确定这是一个等于基线的预先存在的数据库 - 因此从 v1
.
开始
在我们想要用 Flyway 替换的自定义数据库迁移器的应用程序中。
这些迁移分为一些类别,例如用于用户管理的 "account" 和用于产品目录的 "catalog"。
文件名为 $category.migration.$version.sql
。这里,$category
是上述类别之一,$version
是从0开始的整数版本。
例如account.migration.23.sql
虽然有人可能会争辩说每个类别都应该是一个单独的数据库,但实际上并非如此,需要进行重大重构才能改变这一点。
我也可以为每个类别使用一个模式,但这同样需要重写所有 SQL 查询。
所以我做了以下事情:
- 将
$category.migration.$version.sql
移动到/sql/$category/V$version__$category.sql
(例如account.migration.1.sql
变为/sql/account/V1_account.sql
) - 每个类别使用元数据table
- 将基准版本设置为零
在代码中
String[] _categories = new String[] { "catalog", "account" };
for (String _category : _categories) {
Flyway _flyway = new Flyway();
_flyway.setDataSource(databaseUrl.getUrl(), databaseUrl.getUser(), databaseUrl.getPassword());
_flyway.setBaselineVersion(MigrationVersion.fromVersion("0"));
_flyway.setLocations("classpath:/sql/" + applicationName);
_flyway.setTarget(MigrationVersion.fromVersion(_version + ""));
_flyway.setTable(category + "_schema_version");
_flyway.setBaselineOnMigrate(true); // (1)
_flyway.migrate();
}
所以会有元数据 tables catalog_schema_version
和 account_schema_version
.
现问题如下:
从一个空数据库开始,我想按类别应用所有预先存在的迁移,如上所述。
如果我删除 _flyway.setBaselineOnMigrate(true);
(1),那么 catalog
迁移(第一个)会成功,但它会抱怨 account
模式 public
不为空。
同样设置 _flyway.setBaselineOnMigrate(true);
会导致以下行为:
"catalog" 的迁移成功但 V0_account.sql
被忽略并且 Flyway 以 V1_account.sql
开头,可能是因为它仍然以某种方式认为数据库已经基线化?
有没有人有解决问题的建议?
最简单的解决方案是将 schema_version
表分别保存在另一个架构中。我已经回答了
根据您对 baseline
的观察,这些是预期的特征。 account
的迁移从 v1
开始,因为结合了 baseline=0
、baselineOnMigrate=true
和非空目标模式(因为 catalog
已经填充了它)Flyway 有确定这是一个等于基线的预先存在的数据库 - 因此从 v1
.