【发布时间】:2014-08-24 17:57:53
【问题描述】:
在将 mysql-connector 替换为 MariaDB 期间,我遇到了 Liquibase 在我检查主键不存在的变更集上失败的情况:
<preConditions onFail="MARK_RAN">
<not>
<primaryKeyExists tableName="users"/>
</not>
</preConditions>
NullPointerException 失败
Error: null java.lang.NullPointerException at liquibase.snapshot.jvm.MySQLDatabaseSnapshotGenerator.convertPrimaryKeyName(MySQLDatabaseSnapshotGenerator.java:124)
at liquibase.snapshot.jvm.JdbcDatabaseSnapshotGenerator.readPrimaryKeys(JdbcDatabaseSnapshotGenerator.java:759)
at liquibase.snapshot.jvm.JdbcDatabaseSnapshotGenerator.createSnapshot(JdbcDatabaseSnapshotGenerator.java:243)
at liquibase.snapshot.DatabaseSnapshotGeneratorFactory.createSnapshot(DatabaseSnapshotGeneratorFactory.java:69)
at liquibase.precondition.core.PrimaryKeyExistsPrecondition.check(PrimaryKeyExistsPrecondition.java:52)
at liquibase.precondition.core.NotPrecondition.check(NotPrecondition.java:30)
at liquibase.precondition.core.AndPrecondition.check(AndPrecondition.java:34)
at liquibase.precondition.core.PreconditionContainer.check(PreconditionContainer.java:199)
at liquibase.changelog.ChangeSet.execute(ChangeSet.java:249)
如果我删除此子句,则 liquibase 可以正常工作。有趣的是,其他前置条件也可以正常工作,例如检查某些表是否存在。
在深入研究代码后,我发现问题出在 JdbcDatabaseSnapshotGenerator#readPrimaryKeys 中,我们尝试在其中获取主键。但是,当然,对于不同的数据库,有不同的实现,所以我使用 MariaDB 得到的 ResultSet(主键为空列)似乎有点不同,但是,有趣的是方法(在 MySQLDatabaseSnapshotGenerator 中)在哪里失败是这样的:
@Override
protected String convertPrimaryKeyName(String pkName) throws SQLException {
if (pkName.equals("PRIMARY")) {
return null;
} else {
return pkName;
}
}
所以,如果它是相反的方式,它对我有用:) 我的意思是这样的:
if ("PRIMARY".equals(pkName))
问题:是 liquibase 的错误还是我做错了什么?
【问题讨论】:
-
我讨厌 Java。
-
是的,这不是一件好事。
标签: java mysql mysql-connector liquibase mariadb