Commit 95ccd760 authored by Andy Wilkinson's avatar Andy Wilkinson

Merge pull request #5344 from Eddú Meléndez

* gh-5344:
  Polish "Upgrade to Flyway 4.0"
  Upgrade to Flyway 4.0
parents 15639d39 4ea7dc6f
/* /*
* Copyright 2012-2016 the original author or authors. * Copyright 2012-2017 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
...@@ -18,6 +18,7 @@ package org.springframework.boot.autoconfigure.flyway; ...@@ -18,6 +18,7 @@ package org.springframework.boot.autoconfigure.flyway;
import java.util.Collections; import java.util.Collections;
import java.util.HashSet; import java.util.HashSet;
import java.util.List;
import java.util.Set; import java.util.Set;
import javax.annotation.PostConstruct; import javax.annotation.PostConstruct;
...@@ -26,6 +27,7 @@ import javax.sql.DataSource; ...@@ -26,6 +27,7 @@ import javax.sql.DataSource;
import org.flywaydb.core.Flyway; import org.flywaydb.core.Flyway;
import org.flywaydb.core.api.MigrationVersion; import org.flywaydb.core.api.MigrationVersion;
import org.flywaydb.core.api.callback.FlywayCallback;
import org.springframework.beans.factory.ObjectProvider; import org.springframework.beans.factory.ObjectProvider;
import org.springframework.boot.autoconfigure.AutoConfigureAfter; import org.springframework.boot.autoconfigure.AutoConfigureAfter;
...@@ -61,6 +63,7 @@ import org.springframework.util.ObjectUtils; ...@@ -61,6 +63,7 @@ import org.springframework.util.ObjectUtils;
* @author Vedran Pavic * @author Vedran Pavic
* @author Stephane Nicoll * @author Stephane Nicoll
* @author Jacques-Etienne Beaudet * @author Jacques-Etienne Beaudet
* @author Eddú Meléndez
* @since 1.1.0 * @since 1.1.0
*/ */
@Configuration @Configuration
...@@ -92,15 +95,20 @@ public class FlywayAutoConfiguration { ...@@ -92,15 +95,20 @@ public class FlywayAutoConfiguration {
private final FlywayMigrationStrategy migrationStrategy; private final FlywayMigrationStrategy migrationStrategy;
private List<FlywayCallback> flywayCallbacks;
public FlywayConfiguration(FlywayProperties properties, public FlywayConfiguration(FlywayProperties properties,
ResourceLoader resourceLoader, ObjectProvider<DataSource> dataSource, ResourceLoader resourceLoader, ObjectProvider<DataSource> dataSource,
@FlywayDataSource ObjectProvider<DataSource> flywayDataSource, @FlywayDataSource ObjectProvider<DataSource> flywayDataSource,
ObjectProvider<FlywayMigrationStrategy> migrationStrategy) { ObjectProvider<FlywayMigrationStrategy> migrationStrategy,
ObjectProvider<List<FlywayCallback>> flywayCallbacks) {
this.properties = properties; this.properties = properties;
this.resourceLoader = resourceLoader; this.resourceLoader = resourceLoader;
this.dataSource = dataSource.getIfUnique(); this.dataSource = dataSource.getIfUnique();
this.flywayDataSource = flywayDataSource.getIfAvailable(); this.flywayDataSource = flywayDataSource.getIfAvailable();
this.migrationStrategy = migrationStrategy.getIfAvailable(); this.migrationStrategy = migrationStrategy.getIfAvailable();
this.flywayCallbacks = flywayCallbacks
.getIfAvailable(() -> Collections.emptyList());
} }
@PostConstruct @PostConstruct
...@@ -140,6 +148,8 @@ public class FlywayAutoConfiguration { ...@@ -140,6 +148,8 @@ public class FlywayAutoConfiguration {
else { else {
flyway.setDataSource(this.dataSource); flyway.setDataSource(this.dataSource);
} }
flyway.setCallbacks(this.flywayCallbacks
.toArray(new FlywayCallback[this.flywayCallbacks.size()]));
flyway.setLocations(this.properties.getLocations().toArray(new String[0])); flyway.setLocations(this.properties.getLocations().toArray(new String[0]));
return flyway; return flyway;
} }
......
...@@ -16,6 +16,7 @@ ...@@ -16,6 +16,7 @@
package org.springframework.boot.autoconfigure.flyway; package org.springframework.boot.autoconfigure.flyway;
import java.sql.Connection;
import java.util.Arrays; import java.util.Arrays;
import java.util.Collections; import java.util.Collections;
import java.util.HashMap; import java.util.HashMap;
...@@ -25,12 +26,14 @@ import javax.sql.DataSource; ...@@ -25,12 +26,14 @@ import javax.sql.DataSource;
import org.flywaydb.core.Flyway; import org.flywaydb.core.Flyway;
import org.flywaydb.core.api.MigrationVersion; import org.flywaydb.core.api.MigrationVersion;
import org.flywaydb.core.api.callback.FlywayCallback;
import org.hibernate.engine.transaction.jta.platform.internal.NoJtaPlatform; import org.hibernate.engine.transaction.jta.platform.internal.NoJtaPlatform;
import org.junit.After; import org.junit.After;
import org.junit.Before; import org.junit.Before;
import org.junit.Rule; import org.junit.Rule;
import org.junit.Test; import org.junit.Test;
import org.junit.rules.ExpectedException; import org.junit.rules.ExpectedException;
import org.mockito.InOrder;
import org.springframework.beans.factory.BeanCreationException; import org.springframework.beans.factory.BeanCreationException;
import org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoConfiguration; import org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoConfiguration;
...@@ -43,12 +46,16 @@ import org.springframework.context.annotation.Bean; ...@@ -43,12 +46,16 @@ import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary; import org.springframework.context.annotation.Primary;
import org.springframework.core.Ordered; import org.springframework.core.Ordered;
import org.springframework.core.annotation.Order;
import org.springframework.core.env.MapPropertySource; import org.springframework.core.env.MapPropertySource;
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter;
import org.springframework.stereotype.Component; import org.springframework.stereotype.Component;
import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.inOrder;
import static org.mockito.Mockito.mock;
/** /**
* Tests for {@link FlywayAutoConfiguration}. * Tests for {@link FlywayAutoConfiguration}.
...@@ -57,6 +64,7 @@ import static org.assertj.core.api.Assertions.assertThat; ...@@ -57,6 +64,7 @@ import static org.assertj.core.api.Assertions.assertThat;
* @author Phillip Webb * @author Phillip Webb
* @author Andy Wilkinson * @author Andy Wilkinson
* @author Vedran Pavic * @author Vedran Pavic
* @author Eddú Meléndez
*/ */
public class FlywayAutoConfigurationTests { public class FlywayAutoConfigurationTests {
...@@ -246,6 +254,23 @@ public class FlywayAutoConfigurationTests { ...@@ -246,6 +254,23 @@ public class FlywayAutoConfigurationTests {
"classpath:db/vendors/h2", "classpath:db/changelog"); "classpath:db/vendors/h2", "classpath:db/changelog");
} }
@Test
public void callbacksAreConfiguredAndOrdered() throws Exception {
registerAndRefresh(EmbeddedDataSourceConfiguration.class,
FlywayAutoConfiguration.class, PropertyPlaceholderAutoConfiguration.class,
CallbackConfiguration.class);
assertThat(this.context.getBeansOfType(Flyway.class)).hasSize(1);
Flyway flyway = this.context.getBean(Flyway.class);
FlywayCallback callbackOne = this.context.getBean("callbackOne",
FlywayCallback.class);
FlywayCallback callbackTwo = this.context.getBean("callbackTwo",
FlywayCallback.class);
assertThat(flyway.getCallbacks()).containsExactly(callbackTwo, callbackOne);
InOrder orderedCallbacks = inOrder(callbackOne, callbackTwo);
orderedCallbacks.verify(callbackTwo).beforeMigrate(any(Connection.class));
orderedCallbacks.verify(callbackOne).beforeMigrate(any(Connection.class));
}
private void registerAndRefresh(Class<?>... annotatedClasses) { private void registerAndRefresh(Class<?>... annotatedClasses) {
this.context.register(annotatedClasses); this.context.register(annotatedClasses);
this.context.refresh(); this.context.refresh();
...@@ -325,4 +350,21 @@ public class FlywayAutoConfigurationTests { ...@@ -325,4 +350,21 @@ public class FlywayAutoConfigurationTests {
} }
@Configuration
static class CallbackConfiguration {
@Bean
@Order(1)
public FlywayCallback callbackOne() {
return mock(FlywayCallback.class);
}
@Bean
@Order(0)
public FlywayCallback callbackTwo() {
return mock(FlywayCallback.class);
}
}
} }
...@@ -73,7 +73,7 @@ ...@@ -73,7 +73,7 @@
<ehcache.version>2.10.3</ehcache.version> <ehcache.version>2.10.3</ehcache.version>
<ehcache3.version>3.2.0</ehcache3.version> <ehcache3.version>3.2.0</ehcache3.version>
<embedded-mongo.version>1.50.5</embedded-mongo.version> <embedded-mongo.version>1.50.5</embedded-mongo.version>
<flyway.version>3.2.1</flyway.version> <flyway.version>4.0.3</flyway.version>
<freemarker.version>2.3.25-incubating</freemarker.version> <freemarker.version>2.3.25-incubating</freemarker.version>
<elasticsearch.version>2.4.4</elasticsearch.version> <elasticsearch.version>2.4.4</elasticsearch.version>
<glassfish-el.version>3.0.0</glassfish-el.version> <glassfish-el.version>3.0.0</glassfish-el.version>
......
...@@ -1952,8 +1952,12 @@ Boot will call `Flyway.migrate()` to perform the database migration. If you woul ...@@ -1952,8 +1952,12 @@ Boot will call `Flyway.migrate()` to perform the database migration. If you woul
more control, provide a `@Bean` that implements more control, provide a `@Bean` that implements
{sc-spring-boot-autoconfigure}/flyway/FlywayMigrationStrategy.{sc-ext}[`FlywayMigrationStrategy`]. {sc-spring-boot-autoconfigure}/flyway/FlywayMigrationStrategy.{sc-ext}[`FlywayMigrationStrategy`].
TIP: If you want to make use of http://flywaydb.org/documentation/callbacks.html[Flyway Flyway supports SQL and Java http://flywaydb.org/documentation/callbacks.html[callbacks].
callbacks], those scripts should also live in the `classpath:db/migration` folder. To use SQL-based callbacks, place the callback scripts in the `classpath:db/migration`
folder. To use Java-based callbacks, create one or more beans that implement
`FlywayCallback` or, preferably, extend `BaseFlywayCallback`. Any such beans will be
automatically registered with `Flyway`. They can be ordered using `@Order` or by
implementing `Ordered`.
By default Flyway will autowire the (`@Primary`) `DataSource` in your context and By default Flyway will autowire the (`@Primary`) `DataSource` in your context and
use that for migrations. If you like to use a different `DataSource` you can create use that for migrations. If you like to use a different `DataSource` you can create
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment