Spring 启动应用程序不是 运行 启动时的 Flyway 迁移
Spring Boot Application is not running Flyway migrations on startup
我有一个 Spring 启动应用程序和一对实体 类,我正在尝试使用 flyway 实现数据库迁移。 似乎在启动时,Spring 引导根本不是 运行ning flyway。
这是我的application.properties
spring.datasource.url= jdbc:postgresql://localhost:5555/mfidb
spring.datasource.username=postgres
spring.datasource.password=postgres
spring.jpa.hibernate.ddl-auto=validate
spring.flyway.enabled=true
这是我的 build.gradle 中与飞行路线有关的几行
plugins {
id 'org.springframework.boot' version '2.2.6.RELEASE'
id 'io.spring.dependency-management' version '1.0.9.RELEASE'
id 'java'
id "org.flywaydb.flyway" version "6.4.1"
}
dependencies {
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
implementation 'org.springframework.boot:spring-boot-starter-web'
implementation 'org.flywaydb:flyway-core'
runtime('org.postgresql:postgresql:42.2.12')
}
flyway {
url = 'jdbc:postgresql://localhost:5555/mfidb'
user = 'postgres'
password = 'postgres'
}
我可以通过在终端中输入 gradle flywayMigrate -i
来 运行 我的迁移。
但我希望在启动时迁移到 运行。
任何帮助将不胜感激,在此先感谢。
编辑:
这是 运行 应用程序
时的控制台输出
2020-05-05 11:55:59.022 INFO 50754 --- [ main] com.ubm.mfi.MfiApplication : Starting MfiApplication on MacBook-Pro.local with PID 50754 (~/Downloads/mfi 5/build/classes/java/main started by will in ~/Downloads/mfi 5)
2020-05-05 11:55:59.024 INFO 50754 --- [ main] com.ubm.mfi.MfiApplication : No active profile set, falling back to default profiles: default
2020-05-05 11:55:59.457 INFO 50754 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data JPA repositories in DEFAULT mode.
2020-05-05 11:55:59.495 INFO 50754 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 33ms. Found 2 JPA repository interfaces.
2020-05-05 11:55:59.778 INFO 50754 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat initialized with port(s): 8080 (http)
2020-05-05 11:55:59.783 INFO 50754 --- [ main] o.apache.catalina.core.StandardService : Starting service [Tomcat]
2020-05-05 11:55:59.784 INFO 50754 --- [ main] org.apache.catalina.core.StandardEngine : Starting Servlet engine: [Apache Tomcat/9.0.33]
2020-05-05 11:55:59.838 INFO 50754 --- [ main] o.a.c.c.C.[Tomcat].[localhost].[/] : Initializing Spring embedded WebApplicationContext
2020-05-05 11:55:59.838 INFO 50754 --- [ main] o.s.web.context.ContextLoader : Root WebApplicationContext: initialization completed in 768 ms
2020-05-05 11:55:59.917 INFO 50754 --- [ main] o.hibernate.jpa.internal.util.LogHelper : HHH000204: Processing PersistenceUnitInfo [name: default]
2020-05-05 11:55:59.944 INFO 50754 --- [ main] org.hibernate.Version : HHH000412: Hibernate ORM core version 5.4.12.Final
2020-05-05 11:55:59.991 INFO 50754 --- [ main] o.hibernate.annotations.common.Version : HCANN000001: Hibernate Commons Annotations {5.1.0.Final}
2020-05-05 11:56:00.051 INFO 50754 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting...
2020-05-05 11:56:00.114 INFO 50754 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed.
2020-05-05 11:56:00.124 INFO 50754 --- [ main] org.hibernate.dialect.Dialect : HHH000400: Using dialect: org.hibernate.dialect.PostgreSQL10Dialect
2020-05-05 11:56:00.545 INFO 50754 --- [ main] o.h.e.t.j.p.i.JtaPlatformInitiator : HHH000490: Using JtaPlatform implementation: [org.hibernate.engine.transaction.jta.platform.internal.NoJtaPlatform]
2020-05-05 11:56:00.548 INFO 50754 --- [ main] j.LocalContainerEntityManagerFactoryBean : Initialized JPA EntityManagerFactory for persistence unit 'default'
2020-05-05 11:56:00.818 WARN 50754 --- [ main] JpaBaseConfiguration$JpaWebConfiguration : spring.jpa.open-in-view is enabled by default. Therefore, database queries may be performed during view rendering. Explicitly configure spring.jpa.open-in-view to disable this warning
2020-05-05 11:56:00.891 INFO 50754 --- [ main] o.s.s.concurrent.ThreadPoolTaskExecutor : Initializing ExecutorService 'applicationTaskExecutor'
2020-05-05 11:56:01.005 INFO 50754 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat started on port(s): 8080 (http) with context path ''
2020-05-05 11:56:01.007 INFO 50754 --- [ main] com.ubm.mfi.MfiApplication : Started MfiApplication in 2.255 seconds (JVM running for 2.983)
这是数据迁移的路径
添加 logging.level.root=debug
您的 application.properties
文件以在启动应用程序期间查看详细信息。
也只需将 flyway 用户和密码添加到 application.properties
。
spring.flyway.url = 'jdbc:postgresql://localhost:5555/mfidb'
spring.flyway.password=postgres
spring.flyway.user=postgres
如果您不需要 运行 来自 gradle 的飞行路线,您可以从 build.gradle
中删除飞行路线配置
我觉得你的 application.properties 很完美。
我也在使用 Flyway,它就像一个魅力,在我的应用程序启动时执行迁移。我的 build.gradle
中唯一与 flyway 相关的条目是 dependency
runtime("org.flywaydb:flyway-core")
我认为您应该从 build.gradle
.
中删除所有其他与飞路相关的条目
当我执行 gradle 干净构建时,我的依赖项没有得到刷新,因此 flyway 源永远不存在。我不得不在我的 IDE 中手动刷新我的依赖项,它开始工作了。当你花几个小时在如此简单的事情上时,你会很难过。 Giga 更改日志记录级别的评论帮助我找到了问题所在。谢谢
在我的例子中,情况是这样的:
我花了将近 4 个小时来解决这个问题,我的假设是 Spring JPA starter 带来了 flyway 核心依赖项。我没有明确添加 flyway-core 的依赖。所以如果我们不这样做 spring boot flyway auto configuration 不会给出任何错误,只是简单地忽略迁移设置。
通过跟踪自动配置我发现了这一点,如果没有手动添加依赖项,自动配置将忽略飞路设置,而不是像这样使用条件注释抛出异常 @ConditionalOnMissingBean({Flyway.class})
检查您的脚本是否已经 运行。
诀窍是,一旦 Flyway 成功 运行 更新脚本,它就创建了 table flyway_schema_history,即记录下我已经运行创建脚本成功一次
当我第二次尝试 运行 脚本时,该脚本被拒绝了,但由于最初创建的 table(在我的例子中称为 'bike')在应用程序关闭时被删除上次在 spring.jpa.hibernate.ddl-auto=create-drop 模式下 运行 时,我得到了
SchemaManagementException: Schema-validation: missing table [bike]
异常。
删除 flyway_schema_history table 或删除与前一个脚本对应的记录 运行 并再次滚动!
手动检查 SQL 后,这对我有用(使用 Spring Boot + Cloud):
我的重要部分 build.gradle:
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
implementation 'org.flywaydb:flyway-core'
implementation 'org.hibernate:hibernate-core'
implementation 'org.hibernate.validator:hibernate-validator:7.0.1.Final'
没有 gradle 插件。在 application.yml/application-local.yml:
spring:
flyway:
baseline-on-migrate: true
jpa:
database: POSTGRESQL
show-sql: true
hibernate:
ddl-auto: validate
open-in-view: true
datasource:
platform: postgres
url: jdbc:postgresql://localhost:5432/your_db
username: your_db_user
password: your_db_passwd
driverClassName: org.postgresql.Driver
请注意,您不需要针对 DB user/url 的 flyway 特定配置。 Spring Boot 在类路径上检测到 Flyway(或者 Liquibase,如果你正在使用它...)。 然后它 使用主数据源。 参见:https://docs.spring.io/spring-boot/docs/2.5.6/reference/html/howto.html#howto.data-initialization。然后最后一个技巧是制作你的第一个脚本 V2__init.sql 。这一点很关键,因为 baseline-on-migrate: true 位会创建 flyway_schema_history table 并且它的作用是第一件事,所以版本 1,或 V1_ 即第一行......所以如果它是 V1__init.sql 或其他什么,你的脚本将不会运行。它会认为它已经运行。它必须是下一个,V2__init.sql 或其他。
我正在使用 maven,并通过 运行 mvn clean install
解决了这个问题
spring-boot-starter-data-jpa
和 mysql-connector-java
依赖项是通往 运行 的飞路所必需的。您可以通过在应用程序属性中启用 logging.level.root=DEBUG
来检查调试输出。
只需添加以下依赖项即可解决问题:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.28</version>
</dependency>
在我的例子中,db/migration
拼写错误:)
在我的例子中,飞路初始化脚本的文件名中缺少一个字符。
- Bad-Filename: V1_init.sql
- Good-Filename:V1__init.sql(双'_')
我在文件名中缺少下划线,它需要 2 个而不是 1 个。
使用 spring-boot 2.6.7,我的 application.properties
spring.datasource.url=jdbc:h2:mem:db;DB_CLOSE_DELAY=-1
spring.datasource.username=sa
spring.datasource.password=
spring.jpa.hibernate.ddl-auto=validate # or 'none'
Resource-Folder
src/main/resources
- db/migration
- V1__init.sql
V1__init.sql
的例子
create sequence hibernate_sequence start with 1 increment by 1;
CREATE TABLE person
(
id INT NOT NULL,
name VARCHAR(255),
age INT,
CONSTRAINT pk_person PRIMARY KEY (id)
);
在spring docs中描述正确,但我认识得太晚了
经过几天尝试不同的配置排列后,我找到了自己的出路。对于我来说,当我尝试从 6.2.1
一路升级到 8.5.11
时,我只需要在我的集成测试中的每个之前添加 flyway.migrate()
。
我有一个 Spring 启动应用程序和一对实体 类,我正在尝试使用 flyway 实现数据库迁移。 似乎在启动时,Spring 引导根本不是 运行ning flyway。
这是我的application.properties
spring.datasource.url= jdbc:postgresql://localhost:5555/mfidb
spring.datasource.username=postgres
spring.datasource.password=postgres
spring.jpa.hibernate.ddl-auto=validate
spring.flyway.enabled=true
这是我的 build.gradle 中与飞行路线有关的几行
plugins {
id 'org.springframework.boot' version '2.2.6.RELEASE'
id 'io.spring.dependency-management' version '1.0.9.RELEASE'
id 'java'
id "org.flywaydb.flyway" version "6.4.1"
}
dependencies {
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
implementation 'org.springframework.boot:spring-boot-starter-web'
implementation 'org.flywaydb:flyway-core'
runtime('org.postgresql:postgresql:42.2.12')
}
flyway {
url = 'jdbc:postgresql://localhost:5555/mfidb'
user = 'postgres'
password = 'postgres'
}
我可以通过在终端中输入 gradle flywayMigrate -i
来 运行 我的迁移。
但我希望在启动时迁移到 运行。
任何帮助将不胜感激,在此先感谢。
编辑:
这是 运行 应用程序
时的控制台输出2020-05-05 11:55:59.022 INFO 50754 --- [ main] com.ubm.mfi.MfiApplication : Starting MfiApplication on MacBook-Pro.local with PID 50754 (~/Downloads/mfi 5/build/classes/java/main started by will in ~/Downloads/mfi 5)
2020-05-05 11:55:59.024 INFO 50754 --- [ main] com.ubm.mfi.MfiApplication : No active profile set, falling back to default profiles: default
2020-05-05 11:55:59.457 INFO 50754 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data JPA repositories in DEFAULT mode.
2020-05-05 11:55:59.495 INFO 50754 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 33ms. Found 2 JPA repository interfaces.
2020-05-05 11:55:59.778 INFO 50754 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat initialized with port(s): 8080 (http)
2020-05-05 11:55:59.783 INFO 50754 --- [ main] o.apache.catalina.core.StandardService : Starting service [Tomcat]
2020-05-05 11:55:59.784 INFO 50754 --- [ main] org.apache.catalina.core.StandardEngine : Starting Servlet engine: [Apache Tomcat/9.0.33]
2020-05-05 11:55:59.838 INFO 50754 --- [ main] o.a.c.c.C.[Tomcat].[localhost].[/] : Initializing Spring embedded WebApplicationContext
2020-05-05 11:55:59.838 INFO 50754 --- [ main] o.s.web.context.ContextLoader : Root WebApplicationContext: initialization completed in 768 ms
2020-05-05 11:55:59.917 INFO 50754 --- [ main] o.hibernate.jpa.internal.util.LogHelper : HHH000204: Processing PersistenceUnitInfo [name: default]
2020-05-05 11:55:59.944 INFO 50754 --- [ main] org.hibernate.Version : HHH000412: Hibernate ORM core version 5.4.12.Final
2020-05-05 11:55:59.991 INFO 50754 --- [ main] o.hibernate.annotations.common.Version : HCANN000001: Hibernate Commons Annotations {5.1.0.Final}
2020-05-05 11:56:00.051 INFO 50754 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting...
2020-05-05 11:56:00.114 INFO 50754 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed.
2020-05-05 11:56:00.124 INFO 50754 --- [ main] org.hibernate.dialect.Dialect : HHH000400: Using dialect: org.hibernate.dialect.PostgreSQL10Dialect
2020-05-05 11:56:00.545 INFO 50754 --- [ main] o.h.e.t.j.p.i.JtaPlatformInitiator : HHH000490: Using JtaPlatform implementation: [org.hibernate.engine.transaction.jta.platform.internal.NoJtaPlatform]
2020-05-05 11:56:00.548 INFO 50754 --- [ main] j.LocalContainerEntityManagerFactoryBean : Initialized JPA EntityManagerFactory for persistence unit 'default'
2020-05-05 11:56:00.818 WARN 50754 --- [ main] JpaBaseConfiguration$JpaWebConfiguration : spring.jpa.open-in-view is enabled by default. Therefore, database queries may be performed during view rendering. Explicitly configure spring.jpa.open-in-view to disable this warning
2020-05-05 11:56:00.891 INFO 50754 --- [ main] o.s.s.concurrent.ThreadPoolTaskExecutor : Initializing ExecutorService 'applicationTaskExecutor'
2020-05-05 11:56:01.005 INFO 50754 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat started on port(s): 8080 (http) with context path ''
2020-05-05 11:56:01.007 INFO 50754 --- [ main] com.ubm.mfi.MfiApplication : Started MfiApplication in 2.255 seconds (JVM running for 2.983)
这是数据迁移的路径
添加 logging.level.root=debug
您的 application.properties
文件以在启动应用程序期间查看详细信息。
也只需将 flyway 用户和密码添加到 application.properties
。
spring.flyway.url = 'jdbc:postgresql://localhost:5555/mfidb'
spring.flyway.password=postgres
spring.flyway.user=postgres
如果您不需要 运行 来自 gradle 的飞行路线,您可以从 build.gradle
我觉得你的 application.properties 很完美。
我也在使用 Flyway,它就像一个魅力,在我的应用程序启动时执行迁移。我的 build.gradle
中唯一与 flyway 相关的条目是 dependency
runtime("org.flywaydb:flyway-core")
我认为您应该从 build.gradle
.
当我执行 gradle 干净构建时,我的依赖项没有得到刷新,因此 flyway 源永远不存在。我不得不在我的 IDE 中手动刷新我的依赖项,它开始工作了。当你花几个小时在如此简单的事情上时,你会很难过。 Giga 更改日志记录级别的评论帮助我找到了问题所在。谢谢
在我的例子中,情况是这样的:
我花了将近 4 个小时来解决这个问题,我的假设是 Spring JPA starter 带来了 flyway 核心依赖项。我没有明确添加 flyway-core 的依赖。所以如果我们不这样做 spring boot flyway auto configuration 不会给出任何错误,只是简单地忽略迁移设置。
通过跟踪自动配置我发现了这一点,如果没有手动添加依赖项,自动配置将忽略飞路设置,而不是像这样使用条件注释抛出异常 @ConditionalOnMissingBean({Flyway.class})
检查您的脚本是否已经 运行。
诀窍是,一旦 Flyway 成功 运行 更新脚本,它就创建了 table flyway_schema_history,即记录下我已经运行创建脚本成功一次
当我第二次尝试 运行 脚本时,该脚本被拒绝了,但由于最初创建的 table(在我的例子中称为 'bike')在应用程序关闭时被删除上次在 spring.jpa.hibernate.ddl-auto=create-drop 模式下 运行 时,我得到了
SchemaManagementException: Schema-validation: missing table [bike]
异常。
删除 flyway_schema_history table 或删除与前一个脚本对应的记录 运行 并再次滚动!
手动检查 SQL 后,这对我有用(使用 Spring Boot + Cloud):
我的重要部分 build.gradle:
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
implementation 'org.flywaydb:flyway-core'
implementation 'org.hibernate:hibernate-core'
implementation 'org.hibernate.validator:hibernate-validator:7.0.1.Final'
没有 gradle 插件。在 application.yml/application-local.yml:
spring:
flyway:
baseline-on-migrate: true
jpa:
database: POSTGRESQL
show-sql: true
hibernate:
ddl-auto: validate
open-in-view: true
datasource:
platform: postgres
url: jdbc:postgresql://localhost:5432/your_db
username: your_db_user
password: your_db_passwd
driverClassName: org.postgresql.Driver
请注意,您不需要针对 DB user/url 的 flyway 特定配置。 Spring Boot 在类路径上检测到 Flyway(或者 Liquibase,如果你正在使用它...)。 然后它 使用主数据源。 参见:https://docs.spring.io/spring-boot/docs/2.5.6/reference/html/howto.html#howto.data-initialization。然后最后一个技巧是制作你的第一个脚本 V2__init.sql 。这一点很关键,因为 baseline-on-migrate: true 位会创建 flyway_schema_history table 并且它的作用是第一件事,所以版本 1,或 V1_ 即第一行......所以如果它是 V1__init.sql 或其他什么,你的脚本将不会运行。它会认为它已经运行。它必须是下一个,V2__init.sql 或其他。
我正在使用 maven,并通过 运行 mvn clean install
spring-boot-starter-data-jpa
和 mysql-connector-java
依赖项是通往 运行 的飞路所必需的。您可以通过在应用程序属性中启用 logging.level.root=DEBUG
来检查调试输出。
只需添加以下依赖项即可解决问题:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.28</version>
</dependency>
在我的例子中,db/migration
拼写错误:)
在我的例子中,飞路初始化脚本的文件名中缺少一个字符。
- Bad-Filename: V1_init.sql
- Good-Filename:V1__init.sql(双'_')
我在文件名中缺少下划线,它需要 2 个而不是 1 个。
使用 spring-boot 2.6.7,我的 application.properties
spring.datasource.url=jdbc:h2:mem:db;DB_CLOSE_DELAY=-1
spring.datasource.username=sa
spring.datasource.password=
spring.jpa.hibernate.ddl-auto=validate # or 'none'
Resource-Folder
src/main/resources
- db/migration
- V1__init.sql
V1__init.sql
的例子create sequence hibernate_sequence start with 1 increment by 1;
CREATE TABLE person
(
id INT NOT NULL,
name VARCHAR(255),
age INT,
CONSTRAINT pk_person PRIMARY KEY (id)
);
在spring docs中描述正确,但我认识得太晚了
经过几天尝试不同的配置排列后,我找到了自己的出路。对于我来说,当我尝试从 6.2.1
一路升级到 8.5.11
时,我只需要在我的集成测试中的每个之前添加 flyway.migrate()
。