返回 导航

SpringBoot / Cloud

hangge.com

SpringBoot - 整合Flyway实现数据库版本管理教程

作者:hangge | 2026-06-16 09:33
    在日常开发中,数据库表结构往往会随着业务不断变化:今天新增一个字段,明天改一下索引,后天又要补一张表。如果这些变更靠人工手动执行,不仅麻烦,还很容易出现“脚本执行顺序错乱”“线上线下结构不一致”等问题。
    Flyway 就是专门用来解决这类问题的数据库版本管理工具。它可以把数据库变更脚本像代码一样纳入项目管理,随着应用启动自动检查并执行未完成的数据库迁移脚本,让我们的数据库结构始终保持可追踪、可回放、可控。下面我将通过样例演示如何在 Spring Boot 项目中集成并使用 Flyway

一、基本介绍与安装配置

1,什么是 Flyway?

(1)Flyway 是一款开源的数据库版本迁移工具,支持 MySQLPostgreSQLOracle 等绝大多数主流数据库。它的核心思想是:所有数据库结构变更都以 SQL 脚本的形式存在,按版本号排序,自动执行并记录历史。
(2)Flyway 具有如下优势:
  • 版本控制:每次数据库变更都有明确的版本号,便于追溯和管理
  • 自动化执行:应用启动时自动执行未运行的迁移脚本
  • 环境一致性:确保所有环境使用相同的迁移脚本,保证一致性
  • 团队协作:迁移脚本作为代码的一部分,便于团队协作和代码审查
  • 回滚支持:虽然社区版不支持自动回滚,但可以通过新迁移实现回滚
  • 多种格式:支持 SQLJava 两种迁移脚本格式

2,核心工作原理

(1)Flyway 会在数据库中自动创建一张名为 flyway_schema_history 的元数据表,用于记录所有已经执行过的脚本版本、描述、校验值、执行时间等信息。
(2)应用启动时,Flyway 会执行以下流程:
  • 扫描指定目录下的所有 SQL 迁移脚本
  • 读取元数据表,对比哪些脚本已经执行、哪些是新增的
  • 按照版本号从小到大的顺序,依次执行未执行的脚本
  • 执行完成后,将脚本信息写入元数据表

3,常用脚本类型

Flyway 支持三种主要的脚本类型,通过文件名前缀区分:
  • V 开头(Versioned):版本化迁移脚本,每个版本只执行一次,版本号唯一
  • U 开头(Undo):撤销迁移脚本,用于回滚对应版本的变更(专业版功能)
  • R 开头(Repeatable):可重复执行脚本,当脚本内容校验和发生变化时重新执行,适合视图、存储过程、函数等

4,安装配置

(1)编辑项目的 pom.xml 文件,添加 Flyway 依赖。
<dependency>
	<groupId>org.flywaydb</groupId>
	<artifactId>flyway-core</artifactId>
</dependency>
<!-- MySQL 8.x 需要添加此依赖 -->
<dependency>
    <groupId>org.flywaydb</groupId>
    <artifactId>flyway-mysql</artifactId>
</dependency>

(2)在 application.yml 中添加 Flyway 基础配置:
spring:
  application:
    name: demo
  datasource:
    url: jdbc:mysql://192.168.121.128:3306/jeecg-boot?characterEncoding=UTF-8........
    username: root
    password: Hangge_123
    driver-class-name: com.mysql.cj.jdbc.Driver
  # Flyway 配置
  flyway:
    # 是否启用Flyway,默认true
    enabled: true
    # SQL脚本存放路径,默认classpath:db/migration
    locations: classpath:db/migration
    # 迁移脚本编码
    encoding: UTF-8
    # 元数据表名称,默认flyway_schema_history
    table: flyway_schema_history
    # 当数据库非空且没有元数据表时,是否自动创建基线
    baseline-on-migrate: true
    # 基线版本号,默认1
    baseline-version: 1

(3)在 resources 目录下创建 db/migration 文件夹,后续 SQL 脚本将会存放在该目录下。

二、使用样例

1,版本化迁移脚本(只执行一次)

(1)首先我们在 src/main/resources/db/migration 目录下创建第一个初始化脚本 V1__init_user_table.sql,内容如下:
命名规范: 前缀 + 版本号 + __ + 描述.sql
  • 前缀V 表示版本化脚本
  • 版本号:数字,支持小数点,如 11.12.0.1
  • 双下划线 __:分隔符,必须是两个下划线
  • 描述:脚本功能说明,单词间可用下划线分隔
-- 创建用户表
CREATE TABLE `user` (
    `id` BIGINT PRIMARY KEY AUTO_INCREMENT COMMENT '主键ID',
    `username` VARCHAR(50) NOT NULL COMMENT '用户名',
    `email` VARCHAR(100) NOT NULL COMMENT '邮箱',
    `password` VARCHAR(255) NOT NULL COMMENT '密码',
    `status` TINYINT DEFAULT 1 COMMENT '状态:1-正常,0-禁用',
    `create_time` DATETIME DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
    `update_time` DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
    UNIQUE KEY `uk_username` (`username`),
    UNIQUE KEY `uk_email` (`email`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='用户表';

-- 创建索引
CREATE INDEX `idx_status` ON `user` (`status`);
CREATE INDEX `idx_create_time` ON `user` (`create_time`);

(2)接着再创建第二个版本脚本 V1.1__add_user_data.sql,内容如下:
-- 插入默认管理员
INSERT INTO `user` (`username`, `email`, `password`, `status`)
VALUES ('admin', 'admin@example.com', '$2a$10$encrypted_password', 1);

(3)启动 Spring Boot 应用,Flyway 会自动执行如下步骤。
  • 检查数据库中是否存在 flyway_schema_history 表(不存在则创建)
  • 扫描 db/migration 目录下的迁移脚本
  • 比对已执行的迁移记录,执行未运行的脚本
  • 记录执行结果到历史表中

(4)待启动完毕,我们访问数据库可以看到相关的表和数据均成功创建完毕。

2,可重复执行脚本

(1)对于视图、存储过程这类可以重复执行的对象,使用 R 开头的脚本。每次启动时 Flyway 会对比校验和,如果脚本内容有变化就重新执行。这里创建第一个可重复执行脚本 R__create_user_view.sql,内容如下:
CREATE OR REPLACE VIEW `v_user_info` AS
SELECT id, username, email, status
FROM user
WHERE status = 1;

(2)启动项目可以看到视图已经成功创建。

(3)接着我对 R__create_user_view.sql 稍作修改:
CREATE OR REPLACE VIEW `v_user_info` AS
SELECT id, username
FROM user
WHERE status = 1;

(4)重启项目,可以看到视图也发生了变化,说明该脚本由于内容变化重新又执行了。

附:进阶用法

1,占位符替换

(1)Flyway 支持在 SQL 脚本中使用占位符,通过配置动态替换。这里我们在 application.ymlFlyway 配置中添加两个占位符变量:
  • table_prefix 用于表示表名前缀。
  • default_status 用于表示默认状态值。
# Flyway 配置
flyway:
  # 是否启用Flyway,默认true
  enabled: true
  # SQL脚本存放路径,默认classpath:db/migration
  locations: classpath:db/migration
  # 迁移脚本编码
  encoding: UTF-8
  # 元数据表名称,默认flyway_schema_history
  table: flyway_schema_history
  # 当数据库非空且没有元数据表时,是否自动创建基线
  baseline-on-migrate: true
  # 基线版本号,默认1
  baseline-version: 1
  # 占位符变量
  placeholders:
    table_prefix: hangge_
    default_status: 1

(2)接着我们的 SQL 脚本中就可以使用这两个占位符了。
CREATE TABLE `${table_prefix}role` (
    `id` bigint NOT NULL AUTO_INCREMENT,
    `role_name` varchar(50) NOT NULL,
    `status` tinyint DEFAULT ${default_status},
    PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

(3)启动项目执行脚本,查看数据可以可以发现占位符已经成功生效。

2,生产环境关键配置

spring:
  flyway:
    # 禁用clean命令,防止误操作清空数据库!生产环境必须设为true
    clean-disabled: true
    # 迁移失败时是否自动清理,生产环境关闭
    clean-on-validation-error: false
    # 校验不通过时是否终止启动,建议开启
    validate-on-migrate: true
    # 禁止乱序执行,保证版本顺序
    out-of-order: false
评论

全部评论(0)

回到顶部