在 Gradle Spring Boot Hibernate 项目中设置 LiquiBase
Posted
技术标签:
【中文标题】在 Gradle Spring Boot Hibernate 项目中设置 LiquiBase【英文标题】:Setup LiquiBase in a Gradle Spring Boot Hibernate project 【发布时间】:2019-03-02 04:50:04 【问题描述】:我很难在我的 Spring Boot 项目中设置 LiquiBase。我尝试浏览文档并找到一些指南 - 但它们似乎相互矛盾:(
我希望通过 Gradle 使用 LiquiBase,我希望它从 Hibernate 生成更改日志,并最终生成一个 SQL 脚本,我可以在服务器上运行以将架构更新到适当的版本。
为了让它通过 Gradle 运行,我使用了这个插件 https://github.com/liquibase/liquibase-gradle-plugin,使用了他们 README 中推荐的设置。
为了让 Hibernate diff 正常工作,我使用了 https://github.com/liquibase/liquibase-hibernate
这是我的 build.gradle 文件:
buildscript
ext
springBootVersion = '2.0.5.RELEASE'
repositories
mavenCentral()
dependencies
classpath("org.springframework.boot:spring-boot-gradle-plugin:$springBootVersion")
plugins
id 'java'
id 'net.ltgt.apt' version '0.10' // https://projectlombok.org/setup/gradle
id 'org.liquibase.gradle' version '2.0.1' // https://github.com/liquibase/liquibase-gradle-plugin
apply plugin: 'eclipse-wtp'
apply plugin: 'org.springframework.boot'
apply plugin: 'io.spring.dependency-management'
apply plugin: 'war'
group = 'com.example'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = 1.8
repositories
mavenCentral()
maven
credentials
username = oracleUser
password = oraclePass
url 'https://www.oracle.com/content/secure/maven/content'
liquibase
activities
main
changeLogFile 'main.groovy'
url 'jdbc:oracle:thin:@localhost:1521:XE'
referenceUrl 'hibernate:spring:com.example?dialect=org.hibernate.dialect.Oracle10gDialect'
username 'user'
password 'pass'
configurations
providedRuntime
dependencies
compile('org.springframework.boot:spring-boot-starter-data-jpa')
compile('org.springframework.boot:spring-boot-starter-data-rest')
compile('org.springframework.boot:spring-boot-starter-hateoas')
compile('org.springframework.boot:spring-boot-starter-jooq')
compile('org.springframework.boot:spring-boot-starter-web')
compile('org.springframework.boot:spring-boot-starter-mail')
compile('com.github.waffle:waffle-spring-boot-starter:1.9.0')
compile('com.oracle.jdbc:ojdbc8:12.2.0.1')
runtime('org.springframework.boot:spring-boot-devtools')
compileOnly('org.projectlombok:lombok')
apt('org.projectlombok:lombok:1.18.2')
liquibaseRuntime('org.liquibase:liquibase-core:3.6.2')
liquibaseRuntime('org.liquibase:liquibase-groovy-dsl:2.0.1')
liquibaseRuntime('org.liquibase.ext:liquibase-hibernate5:3.6')
liquibaseRuntime('com.oracle.jdbc:ojdbc8:12.2.0.1') // duplicate...
providedRuntime('org.springframework.boot:spring-boot-starter-tomcat')
testCompile('org.springframework.boot:spring-boot-starter-test')
testCompile('org.springframework.restdocs:spring-restdocs-mockmvc')
运行方式
> .\gradlew diffChangeLog -PrunList=main
但是失败了
Task :diffChangeLog liquibase-plugin: Running the 'main' activity... 在 2018 年 9 月 26 日星期三 13:36:24 CEST 开始 Liquibase(版本 3.6.2 建于 2018-07-03 11:28:09)线程“主”中的异常 java.lang.NoClassDefFoundError: org/springframework/core/io/ClassPathResource 在 liquibase.ext.hibernate.database.HibernateSpringPackageDatabase.isXmlFile(HibernateSpringPackageDatabase.java:54)
似乎找不到 Spring Boot。所以我然后尝试删除liquibaseRuntime
,但随后LiquiBase Gradle 插件抱怨liquibaseRuntime
丢失。
似乎我陷入了困境。什么是合理的设置方法?
我真的不想重复liquibaseRuntime
中的每个依赖项。文档也字面意思是:
dependencies // All of your normal project dependencies would be here in addition to... liquibaseRuntime 'org.liquibase:liquibase-core:3.6.1' liquibaseRuntime 'org.liquibase:liquibase-groovy-dsl:2.0.1' liquibaseRuntime 'mysql:mysql-connector-java:5.1.34'
注意
// 除了...
是的。为什么...
请帮忙!
另外...我注意到您必须编写两次数据库配置。为什么在 Spring Boot 配置中已经设置了它?
进展
所以把liquibaseRuntime
改成
liquibaseRuntime('org.liquibase:liquibase-core:3.6.2')
liquibaseRuntime('org.liquibase:liquibase-groovy-dsl:2.0.1')
liquibaseRuntime('org.liquibase.ext:liquibase-hibernate5:3.6')
liquibaseRuntime('com.oracle.jdbc:ojdbc8:12.2.0.1')
liquibaseRuntime('org.springframework.boot:spring-boot-starter-data-jpa')
liquibaseRuntime files('src/main')
使错误消失。但是还是不行。
运行这个命令
.\gradlew 差异
给我这个输出
> Task :diff liquibase-plugin: Running the 'main' activity... Starting Liquibase at Wed, 26 Sep 2018 16:47:19 CEST (version 3.6.2 built at 2018-07-03 11:28:09) Diff Results: Reference Database: null @ hibernate:spring:com.example.model?dialect=org.hibernate.dialect.Oracle10gDialect (Default Schema: HIBERNATE) Comparison Database: SYSTEM @ jdbc:oracle:thin:@localhost:1521:XE (Default Schema: SYSTEM) Compared Schemas: HIBERNATE -> SYSTEM Product Name: Reference: 'Hibernate' Target: 'Oracle' Product Version: Reference: '5.2.17.Final' Target: 'Oracle Database 11g Express Edition Release 11.2.0.2.0 - 64bit Production' Missing Catalog(s): HIBERNATE Unexpected Catalog(s): NONE Changed Catalog(s): NONE Missing Column(s): NONE Unexpected Column(s): NONE Changed Column(s): NONE Missing Foreign Key(s): NONE Unexpected Foreign Key(s): NONE Changed Foreign Key(s): NONE Missing Index(s): NONE Unexpected Index(s): NONE Changed Index(s): NONE Missing Primary Key(s): NONE Unexpected Primary Key(s): NONE Changed Primary Key(s): NONE Missing Sequence(s): NONE Unexpected Sequence(s): NONE Changed Sequence(s): NONE Missing Stored Procedure(s): NONE Unexpected Stored Procedure(s): NONE Changed Stored Procedure(s): NONE Missing Table(s): NONE Unexpected Table(s): NONE Changed Table(s): NONE Missing Unique Constraint(s): NONE Unexpected Unique Constraint(s): NONE Changed Unique Constraint(s): NONE Missing View(s): NONE Unexpected View(s): NONE Changed View(s): NONE Liquibase command 'diff' was executed successfully. BUILD SUCCESSFUL in 7s 1 actionable task: 1 executed
针对空数据库运行时。所以是的 - 它不起作用:(
【问题讨论】:
【参考方案1】:这就是我使用 Gradle 6.3.0 的方式:
configurations
liquibaseRuntime.extendsFrom runtimeClasspath
dependencies
liquibaseRuntime sourceSets.main.output
【讨论】:
【参考方案2】:我知道这是一个旧线程,但我想为以后找到此答案的人添加一些说明...
liquibaseRuntime
配置不继承自任何其他配置。这是因为在大多数情况下,Liquibase 只需要能够解析更改日志并连接到数据库即可。要使用 Hibernate 模块之类的东西,或者从代码中生成更改日志,您需要向 liquibaseRuntime 添加额外的东西,例如 Hibernate 或 Spring Data,并且您需要srcSets.main.output
才能找到您的项目文件自己。
说“除了...之外,您的所有正常项目依赖项都将在此处”的评论指的是您将在块中拥有一堆其他依赖项来构建和运行您的项目,而不是它们将是liquibaseRuntime
配置的一部分。如果您确实希望项目中的所有库也成为liquibaseRuntime
的一部分,您可以将configurations.liquibaseRuntime.extendsFrom configurations.runtime
添加到您的build.gradle,或者如果您已经有configurations
块,您可以添加liquibaseRuntime.extendsFrom runtime
到那个街区。这应该将所有项目依赖项和项目文件本身添加到您的 liquibaseRuntime。
我希望这会有所帮助。
【讨论】:
【参考方案3】:原来我需要添加一些无证的魔法酱。
diff.dependsOn compileJava
diffChangeLog.dependsOn compileJava
generateChangelog.dependsOn compileJava
dependencies
// as before
liquibaseRuntime sourceSets.main.output // replaces liquibaseRuntime files('src/main')
【讨论】:
以上是关于在 Gradle Spring Boot Hibernate 项目中设置 LiquiBase的主要内容,如果未能解决你的问题,请参考以下文章
多模块 Spring Boot 项目中的 Gradle 依赖插件