Database migration sử dụng Liquibase với Spring MVC

Bài viết được sự cho phép của tác giả Nguyễn Hữu Khanh

Trong bài viết trước, mình đã giới thiệu với các bạn về Liquibase, một thư viện giúp chúng ta hiện thực việc database migration cho một ứng dụng Java bất kỳ. Trong bài viết này, mình sẽ hướng dẫn các bạn hiện thực database migration sử dụng Liquibase với Spring MVC các bạn nhé!

  Chạy database migration khi deploy, nên hay không?
  Migrate từ hệ thống monolithic sang microservice - part 2

Đầu tiên, mình sẽ tạo mới một Spring MVC project sử dụng Spring Tool Suite 3 để làm ví dụ.

Kết quả:

Database migration sử dụng Liquibase với Spring MVC

Mình sẽ sử dụng Maven Jetty Plugin để chạy project này.

<plugin>
<groupId>org.eclipse.jetty</groupId>
<artifactId>jetty-maven-plugin</artifactId>
<version>9.4.40.v20210413</version>
<configuration>
<webApp>
<contextPath>/springmvc-liquibase</contextPath>
</webApp>
</configuration>
</plugin>

Kết quả khi mình chạy project này sẽ như sau:

Database migration sử dụng Liquibase với Spring MVC

Để làm việc với Liquibase, các bạn cần khai báo dependency của nó:

<dependency>
<groupId>org.liquibase</groupId>
<artifactId>liquibase-core</artifactId>
<version>4.3.4</version>
</dependency>

Để làm việc với database trong Spring, chúng ta cần thêm spring-orm dependency:

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>${org.springframework-version}</version>
</dependency>

Mình sẽ sử dụng PostgreSQL database trong ví dụ này:

<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>42.2.20</version>
</dependency>

Mặc định, Liquibase đã hỗ trợ việc integrate với Spring framework. Bằng cách khai báo bean của class SpringLiquibase trong Spring container, khi chạy ứng dụng có sử dụng Spring framwork lên, Liquibase sẽ tự động thực hiện việc database migration cho chúng ta các bạn nhé!

Các bạn có thể cấu hình bean của class SpringLiquibase trong Spring container sử dụng XML configuration (trong tập tin /src/main/webapp/WEB-INF/spring/root-context.xml) như sau:

<bean id="springLiquibase" class="liquibase.integration.spring.SpringLiquibase">
<property name="dataSource" ref="dataSource" />
<property name="changeLog" value="classpath:db-changelog.xml" />
</bean>

Nhiệm vụ của chúng ta là chỉ cần cấu hình bean cho phần dataSource và changeLog mà thôi!

Mình sẽ cấu hình dataSource cho database PostgreSQL trong Spring container (trong tập tin /src/main/webapp/WEB-INF/spring/root-context.xml) như sau:

<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="org.postgresql.Driver" />
<property name="url" value="jdbc:postgresql://localhost:5432/liquibase_example" />
<property name="username" value="khanh" />
<property name="password" value="1" />
</bean>

Việc cấu hình dataSource mình sẽ không đề cập chi tiết ở đây. Các bạn có thể đọc thêm bài viết này https://huongdanjava.com/vi/jpa-va-spring-framework.html các bạn nhé!

Từ value của changeLog trong cấu hình của SpringLiquibase ở trên, các bạn có thể hiểu là mình cần tạo tập tin changelog của Liquibase db-changelog.xml trong thư mục src/main/resources.

Mình sẽ định nghĩa nội dung tập tin changelog để thêm bảng clazz như sau:

<?xml version="1.0" encoding="UTF-8"?>
<databaseChangeLog
xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-4.0.xsd">

<changeSet id="1" author="khanh">
<createTable tableName="clazz">
<column name="id" type="BIGINT" autoIncrement="true">
<constraints primaryKey="true" nullable="false" />
</column>
<column name="name" type="VARCHAR(50)" />
</createTable>
</changeSet>
</databaseChangeLog>

Bây giờ, chạy lại ứng dụng, kiểm tra database, các bạn sẽ thấy kết quả như sau:

Database migration sử dụng Liquibase với Spring MVC