Codersee

Add Flyway To An Existing Spring Boot Project

The image is a featured image of Add Flyway to An Existing Spring Boot Project article and consist of Flyway logo in the foreground and a programmer room in the blurred background.

1. Introduction

In this article, which is a continuation of a Flyway series we will learn how to add Flyway to an existing Spring Boot Project.

If you are not sure what this tool can bring to your project, then check out my first post on Flyway with Spring Boot, where you can find all the necessary information.

2. Project Setup

This time, we won’t spend time preparing a sample project (well, if you are here then there’s a 95% chance that you already have some project).

Nevertheless, if you don’t have one, but still would like to learn how to add a flyway to an existing Spring Boot project, then no worries. You can find an example project in this GitHub repository.

Note: If you use the project from the linked repository, then please run the script.sql file (can be found in /resources/sql directory) against your database, before you start the application.

3. Strategy For Adding Flyway To Existing Spring Boot Project

Before we start anything, I just wanted to emphasize that we should always create a backup, before performing any operations on our databases. Regardless of how widely used, or well-tested the tool is, something can always go wrong and we have to be ready to roll out plan B.

3.1 Add Flyway Dependency

As the first thing (after the backup!), let’s add the necessary dependency to our Spring Boot project.

For gradle, it will look as follows:

implementation 'org.flywaydb:flyway-core:9.8.3'

On the other hand, when working with Maven, we need to add these lines:

<dependency>
  <groupId>org.flywaydb</groupId>
  <artifactId>flyway-core</artifactId>
  <version>9.8.3</version>
</dependency>

3.2 Verify Spring Boot App

Nextly, let’s run our Spring Boot application and verify, whether anything changed:

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'flywayInitializer' defined in class path resource [org/springframework/boot/autoconfigure/flyway/FlywayAutoConfiguration$FlywayConfiguration.class]: Found non-empty schema(s) "custom_schema" but no schema history table. Use baseline() or set baselineOnMigrate to true to initialize the schema history table.
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1751) ~[spring-beans-6.0.2.jar:6.0.2]

As we can clearly see, Flyway throws a pretty descriptive message:

Found non-empty schema(s) “custom_schema” but no schema history table. Use baseline() or set baselineOnMigrate to true to initialize the schema history table.

And basically, this error clearly states what we need to do when adding a Flyway to an existing project. But before that, we have to take care of a couple of things.

3.3 Generate Production Database DDL

Firstly, we have to generate an SQL script containing the DDL our production database, including:

  • procedures
  • views,
  • triggers etc…

I won’t go into details here, because DDL script generation depends on the database you are using. Nevertheless, it can be done pretty easily with tools like DataGrip, DBeaver, or pg_dump.
Image shows two ebooks people can get for free after joining newsletter

And when the SQL script with DDL is ready, let’s save it in the Flyway migrations directory (in Spring Boot the default one is resources/db/migration). Of course, we have to remember about the Flyway files naming convention, so the file name should be something, like V1__my_custom_init_script.sql.

3.4 Clear Irrelevant Data

If you have only one database instance in your project, then feel free to skip this point. Otherwise, we have to make sure that the generated DDL script will work in every other environment. And we can achieve it in two ways:

  • if we don’t care about the data in other environments- then we can run the Flyway clean command.
  • however, if we do actually care about the data in our non-production environments, then there’s no other choice than to manually verify and align other database structures with the main one.

The choice here is yours and will depend on many factors, like the importance of test data, amount of environments, etc.

Nevertheless, if you would like to clean your database before adding a Flyway to your existing project, then you can do that with the following:

flyway -defaultSchema="custom_schema" \
  -url="jdbc:postgresql://{URL}:{PORT}/{DB_NAME}" \
  -cleanDisabled="false" \
  -user="{USERNAME}" \
  clean

Please keep in mind that with this command, we will be prompted to enter the password manually (and alternatively, we can pass the -password flag).

3.5 Add Flyway To Existing Spring Boot Project

Finally, with all that being done, we can return to the Spring Boot project and make the necessary changes.

Let’s navigate to the application.yaml file and insert these settings:

spring:
  flyway:
    baselineOnMigrate: true
    defaultSchema: "custom_schema" # not necessary, but most likely you'll want to point to a specific schema

As we can see, with baselineOnMigrate set to true, we instruct Flyway to automatically call baseline when migration is executed against a non-empty schema. Additionally, we set the defaultSchema value, but this is totally optional.

As a result, the flyway_schema_history table is added to our schema:

Image presents screenshot with flyway_schema_history table structure, which was added when we add Flyway to existing Spring Boot project.

and populated with precisely one record.

Please remember that the baselineOnMigrate set to true is only required once- when we do the initial deployment and can be removed after that.

3.6 Add Flyway Using Commands

Basically, with all of the above being done we are finished and can enjoy the benefits of Flyway in our project.

However, if you would like to learn how to add Flyway to an existing project using CLI, then you can do exactly the same with the following command:

flyway -defaultSchema="custom_schema" \ 
-url="jdbc:postgresql://{HOST}:{PORT}/{DB_NAME}" \
-user="USERNAME" \
-baselineOnMigrate="true" \
-locations="filesystem:." migrate

Or, alternatively, run baseline only:

flyway -defaultSchema="custom_schema" \ 
-url="jdbc:postgresql://{HOST}:{PORT}/{DB_NAME}" \
-user="USERNAME" \
-locations="filesystem:." baseline

And then the migrate command:

flyway -defaultSchema="custom_schema" \ 
-url="jdbc:postgresql://{HOST}:{PORT}/{DB_NAME}" \
-user="USERNAME" \
-locations="filesystem:." migrate

These commands might be useful if you would like to extract migrations to a separate directory (and/or repository).

4. Add Flyway To An Existing Spring Boot Project Summary

And that would be all in this article about how to add Flyway to an existing Spring Boot project. If you’d like to get to know Flyway better, then I highly encourage you to visit their documentation.

Let me know in the comments section in case of any questions 🙂

Leave a Reply

Your email address will not be published. Required fields are marked *

Categories

Author

Hi there! 👋

Hi there! 👋

My name is Piotr and I've created Codersee to share my knowledge about Kotlin, Spring Framework, and other related topics through practical, step-by-step guides. Always eager to chat and exchange knowledge.

Master Backend With Kotlin

Subscribe To My Newsletter

Get 3 Free Ebooks and weekly dose of backend knowledge

To make Codersee work, we log user data. By using our site, you agree to our Privacy Policy and Terms of Use.