我有一个使用3.0.14的相对较新的Grails项目。我希望通过Database Migration plugin(2.0.0.RC4)集成liquibase进行数据库迁移。
到目前为止,我有一个足够大的域模型,我已经使用该插件来“播种”初始更改日志。这直接来自文档,并按预期工作:
grails dbm-generate-gorm-changelog changelog.groovy
我现在尝试测试/开始工作的是dbm-gorm-diff
命令,它将更改域模型并创建可应用的更改日志。这是我遇到问题的地方。
Grails documentation建议从数据源中删除dbCreate
块以确保Hibernate不进行更新,并且Liquibase可以接管。很棒,正是我想要的。
当我删除dbCreate
时,Grails / hibernate似乎仍然在数据库迁移插件有机会进行差异之前更新数据库。在执行diff时,看到更改已经太晚了,因此更改日志不包含正确的数据。
dataSource:
pooled: true
jmxExport: true
driverClassName: org.h2.Driver
username: sa
password:
environments:
development:
dataSource:
dbCreate: verify
driverClassName: org.postgresql.Driver
dialect: org.hibernate.dialect.PostgreSQLDialect
url: jdbc:postgresql://127.0.0.1:5432/liquibase_test
username: dbuser
password: dbuser
logSql: false
formatSql: true
(我知道dbCreate已设置为验证。稍后会详细介绍)
dbcreate -U dbuser liquibase_test
grails dbm-update
select * from databasechangelog
是否等于changelog.groovy
添加一个新的简单域类:
class TestDomain {
int testInt
}
运行插件以获取差异 - grails dbm-gorm-diff add-simple-domain.groovy
。该命令失败,但出现异常:
:DataModel:dbmGormDiff
Command execution error: liquibase.command.CommandExecutionException: java.lang.NullPointerException
DataModel:dbmGormDiff FAILED
现在,从上方删除配置dbCreate: verify
,然后重新运行
成功完成无一例外,但存在问题:
add-simple-domain.groovy
,但它没有提到我刚刚创建的新域类。 (它有索引/序列,但我认为这是known issue)databasechangelog
仍然具有原始行计数,即使在询问时也没有对新域类的引用所以,我无法解释发生了什么。我可以处理额外的创建/删除索引&序列,但我似乎无法让liquibase工作。任何人都可以为我阐明这一点吗?
我更多地挖掘了NullPointer,它似乎来自类liquibase/ext/hibernate/snapshot/ForeignKeySnapshotGenerator.java:45
,其中插件试图构造一个外键到继承的表id字段(使用tablePerHierarchy false
这个继承)。在一次不错的搜索后,我找不到任何与此错误相关的内容。
我在Github上发现了tablePerHierarchy
NPE的问题:https://github.com/grails-plugins/grails-database-migration/issues/68
答案 0 :(得分:0)
更新数据源的application.yml
(或application.groovy
)配置:
dataSource:
dbCreate: none
设置为"无"与完全删除dbCreate
不同 - 您需要明确设置它以覆盖其他地方设置的任何默认值。
答案 1 :(得分:0)
“none”在使用JNDI数据源时似乎对我不起作用,仍会导致ddl运行。我将其设置为“忽略”,以便能够在Grails 3.0.x中使用db-migrations和JNDI数据源
答案 2 :(得分:0)
我最终通过在hibernate.hbm2ddl.auto = 'none'
中设置application.groovy
来实现这一目标。有趣的是,当我尝试将相同的配置放在我的application.yml
中时,它没有任何效果。
我怀疑在这里可能还有其他的力量,因为我尝试在没有问题的情况下在新的Grails项目上复制行为。
目前我已经决定在groovy文件中使用hibernate属性了,尽管我仍然很好奇为什么我不能让配置像我的项目一样为我工作。