2

We're getting started with running Liquibase migrations on Grails server startup. We'd like to use dbCreate='validate' on the dataSource, to ensure that the database and object model stay in sync. Our datasource config currently looks like this:

development {
    dataSource_dbm {
        dbCreate = ''
        url = "jdbc:h2:mem:devDb;MVCC=TRUE;LOCK_TIMEOUT=10000;MODE=Oracle"
        username = 'sa'
        password = ''
    }
    dataSource {
        dbCreate = 'validate'
        url = "jdbc:h2:mem:devDb;MVCC=TRUE;LOCK_TIMEOUT=10000;MODE=Oracle"
        username = 'sa'
        password = ''
    }
}

with

grails.plugin.databasemigration.dbm.updateOnStart = true
grails.plugin.databasemigration.dbm.updateOnStartFileNames = ['changelog.groovy']

in our Config.groovy. This results in some errors on startup:

Initialization of bean failed; nested exception is org.springframework.beans.factory.BeanCreationException: 
Error creating bean with name 'transactionManager': 
Cannot resolve reference to bean 'sessionFactory' while setting bean property 'sessionFactory';
nested exception is org.springframework.beans.factory.BeanCreationException:
Error creating bean with name 'sessionFactory': 
Invocation of init method failed; 
nested exception is org.hibernate.HibernateException: 
Missing table: ...

It looks as though the default dataSource is created and the dbCreate policy applied before the liquibase migrations are run.

If we comment out the second dataSource, we see that all of the migrations are indeed applied at startup.

Is there a way to configure our datasources or the databasemigration plugin such that the migrations are run before validation? Or do we have to give up on validation on server startup, and use a dataSource with dbCreate='', and depend on runtime errors to catch problems?

4

1 回答 1

1

您可以自己验证模式,就像schema-export脚本允许您捕获 Hibernate 运行的 SQL(如果您使用“create-drop”)一样。如果您可以访问 Spring ApplicationContext(这里我通过依赖注入grailsApplicationbean 来获得它),那么您可以在 BootStrap 中运行它:

import org.hibernate.tool.hbm2ddl.SchemaValidator

def grailsApplication

....

def ctx = grailsApplication.mainContext
def sessionFactoryFactory = ctx.getBean('&sessionFactory')
def sessionFactory = ctx.getBean('sessionFactory')
def configuration = sessionFactoryFactory.configuration
def settings = sessionFactory.settings

def validator = new SchemaValidator(configuration, settings)
validator.validate()

如果您在http://jira.grails.org/browse/GPDATABASEMIGRATION创建增强请求,这可能是对插件的一个很好的补充,我将考虑在即将发布的版本中添加它。

于 2013-04-30T21:20:16.503 回答