我们有几个数据模式,我们调查迁移到Liquibase。 (其中一个数据模式已经迁移到Liquibase)。
对我们来说,重要的问题是Liquibase是否支持干运行:
(类似于此SQL Server query dry run但与Liquibase相关的问题)
在答案后添加
我阅读了与updateSQL相关的文档,并没有回答“干运行”的要求。 它只是生成SQL(在命令行中,在Ant任务和Maven插件中)。 我会澄清我的问题:
Liquibase是否支持对交易的控制?
我想在执行Liquibase changelog之前打开事务,并在更改日志执行后回滚事务。 当然,我需要验证执行的结果。
有可能吗?
加
如果不对交易(或干运行)进行控制,我们就无法将所有模式迁移到Liquibase。
请帮忙。
答案 0 :(得分:7)
不幸的是,没有。
默认情况下,Liquibase提交执行变更集的所有语句的事务。我假设您考虑的迁移路径通常涉及多个变更集。
您可以修改交易行为的唯一方法是runInTransaction
代码的<changeset>
属性,为documented here。通过将其设置为false
,您可以有效地禁用事务管理,即它可以启用自动提交模式,如ChangeSet.java中所示。
我认为此功能可能是Liquibase的一个有价值的补充,所以我打开了一个功能请求:CORE-1790。
答案 1 :(得分:6)
您可以尝试“updateSQL”模式,它将连接db(检查您的访问权限),获取数据库锁定,生成/打印要应用的SQL语句(基于db状态和您当前的liquibase更改集)也会打印在当前的db状态和释放db锁中缺少chageset id。
答案 2 :(得分:2)
我认为你的答案是“它不支持干运行”,但问题主要在于数据库而不是liquibase。
Liquibase在事务中运行每个changeSet并在插入DATABASECHANGELOG表后提交它,所以理论上你可以覆盖liquibase逻辑来回滚该事务而不是提交它,但是你会遇到大多数SQL运行的问题liquibase是自动提交的。
例如,如果您的changeSet为:
<changeSet>
<createTable name="test">
...
</createTable>
</changeSet>
运行的是:
START TRANSACTION
CREATE TABLE NAME ...
INSERT INTO DATABASECHANGELOG...
COMMIT
但即使您将最后一个命令更改为ROLLBACK,create table调用也会在运行时自动提交,而实际回滚的唯一内容是INSERT。
注意:有些数据库会回滚DDL SQL,例如postgresql,但大多数数据库都没有。
INSERT / UPDATE命令将在事务中运行,并且可以在结尾处自动回滚,但是liquibase没有postCondition命令来执行对所需状态的事务内检查。这将是一个有用的功能(https://liquibase.jira.com/browse/CORE-1793),但即使它在变更集中有任何自动提交更改标记也不可用。如果您添加了一个后置条件以创建上面的表示例,则后置条件将失败并且更新将失败,但该表仍将存在。
答案 3 :(得分:0)
如果您的Liquibase迁移完全独立于数据库,则可以在内存中的H2数据库(或其他“丢弃数据库”)上运行它,只需使用几行代码即可轻松启动。
var info = new Properties();
info.put("user", "sa");
info.put("password", "");
try (var con = new org.h2.Driver().connect("jdbc:h2:mem:db", info)) {
var accessor = new FileSystemResourceAccessor();
var jdbc = new JdbcConnection(con);
var database = DatabaseFactory.getInstance().findCorrectDatabaseImplementation(jdbc);
Liquibase liquibase = new Liquibase("/path/to/liquibase.xml", accessor, database);
liquibase.update("");
}