From b5b68896013d2594e89b1740643a660ca8b1b583 Mon Sep 17 00:00:00 2001 From: michael Date: Thu, 20 Dec 2018 10:59:02 +0100 Subject: [PATCH] Allow easy customization of EmbeddedMongo DownloadConfig See gh-15496 --- .../EmbeddedMongoAutoConfiguration.java | 47 ++++++++++++++----- ...dMongoDownloadConfigBuilderCustomizer.java | 38 +++++++++++++++ .../EmbeddedMongoAutoConfigurationTests.java | 38 +++++++++++++++ 3 files changed, 110 insertions(+), 13 deletions(-) create mode 100644 spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoDownloadConfigBuilderCustomizer.java diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfiguration.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfiguration.java index afc8d0f4edf..66bed00bdb9 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfiguration.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfiguration.java @@ -39,6 +39,7 @@ import de.flapdoodle.embed.mongo.distribution.Version; import de.flapdoodle.embed.mongo.distribution.Versions; import de.flapdoodle.embed.process.config.IRuntimeConfig; import de.flapdoodle.embed.process.config.io.ProcessOutput; +import de.flapdoodle.embed.process.config.store.IDownloadConfig; import de.flapdoodle.embed.process.distribution.GenericVersion; import de.flapdoodle.embed.process.io.Processors; import de.flapdoodle.embed.process.io.Slf4jLevel; @@ -48,6 +49,7 @@ import de.flapdoodle.embed.process.store.ArtifactStoreBuilder; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.ObjectProvider; import org.springframework.boot.autoconfigure.AutoConfigureBefore; import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; @@ -202,24 +204,43 @@ public class EmbeddedMongoAutoConfiguration { @ConditionalOnMissingBean(IRuntimeConfig.class) static class RuntimeConfigConfiguration { + private static Logger EMBEDDED_MONGO_LOGGER = LoggerFactory + .getLogger(RuntimeConfigConfiguration.class.getPackage().getName() + + ".EmbeddedMongo"); + @Bean - public IRuntimeConfig embeddedMongoRuntimeConfig() { - Logger logger = LoggerFactory - .getLogger(getClass().getPackage().getName() + ".EmbeddedMongo"); + public IRuntimeConfig embeddedMongoRuntimeConfig( + IDownloadConfig embeddedMongoDownloadConfig) { ProcessOutput processOutput = new ProcessOutput( - Processors.logTo(logger, Slf4jLevel.INFO), - Processors.logTo(logger, Slf4jLevel.ERROR), Processors.named( - "[console>]", Processors.logTo(logger, Slf4jLevel.DEBUG))); - return new RuntimeConfigBuilder().defaultsWithLogger(Command.MongoD, logger) - .processOutput(processOutput).artifactStore(getArtifactStore(logger)) - .build(); + Processors.logTo(EMBEDDED_MONGO_LOGGER, Slf4jLevel.INFO), + Processors.logTo(EMBEDDED_MONGO_LOGGER, Slf4jLevel.ERROR), + Processors.named("[console>]", + Processors.logTo(EMBEDDED_MONGO_LOGGER, Slf4jLevel.DEBUG))); + return new RuntimeConfigBuilder() + .defaultsWithLogger(Command.MongoD, EMBEDDED_MONGO_LOGGER) + .processOutput(processOutput) + .artifactStore(getArtifactStore(embeddedMongoDownloadConfig)).build(); } - private ArtifactStoreBuilder getArtifactStore(Logger logger) { + @Bean + @ConditionalOnMissingBean + public IDownloadConfig embeddedMongoDownloadConfig( + ObjectProvider downloadConfigBuilderCustomizer) { + DownloadConfigBuilder downloadConfigBuilder = new DownloadConfigBuilder() + .defaultsForCommand(Command.MongoD); + + downloadConfigBuilder + .progressListener(new Slf4jProgressListener(EMBEDDED_MONGO_LOGGER)); + + downloadConfigBuilderCustomizer.stream() + .forEach((c) -> c.customize(downloadConfigBuilder)); + + return downloadConfigBuilder.build(); + } + + private ArtifactStoreBuilder getArtifactStore(IDownloadConfig downloadConfig) { return new ExtractedArtifactStoreBuilder().defaults(Command.MongoD) - .download(new DownloadConfigBuilder() - .defaultsForCommand(Command.MongoD) - .progressListener(new Slf4jProgressListener(logger)).build()); + .download(downloadConfig); } } diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoDownloadConfigBuilderCustomizer.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoDownloadConfigBuilderCustomizer.java new file mode 100644 index 00000000000..2211dede5a5 --- /dev/null +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoDownloadConfigBuilderCustomizer.java @@ -0,0 +1,38 @@ +/* + * Copyright 2012-2018 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.springframework.boot.autoconfigure.mongo.embedded; + +import de.flapdoodle.embed.mongo.config.DownloadConfigBuilder; + +/** + * Callback interface that can be implemented by beans wishing to customize the + * EmbeddedMongo {@link DownloadConfigBuilder} outcome whilst retaining default + * auto-configuration. + * + * @author Michael Gmeiner + * @since 2.2.0 + */ +@FunctionalInterface +public interface EmbeddedMongoDownloadConfigBuilderCustomizer { + + /** + * Customize the {@link DownloadConfigBuilder}. + * @param downloadConfigBuilder the {@link DownloadConfigBuilder} to customize + */ + void customize(DownloadConfigBuilder downloadConfigBuilder); + +} diff --git a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfigurationTests.java b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfigurationTests.java index bb73d990133..d17fa4b04b8 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfigurationTests.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/embedded/EmbeddedMongoAutoConfigurationTests.java @@ -22,10 +22,13 @@ import java.util.EnumSet; import java.util.stream.Collectors; import com.mongodb.MongoClient; +import de.flapdoodle.embed.mongo.config.DownloadConfigBuilder; import de.flapdoodle.embed.mongo.config.IMongodConfig; import de.flapdoodle.embed.mongo.config.Storage; import de.flapdoodle.embed.mongo.distribution.Feature; import de.flapdoodle.embed.mongo.distribution.Version; +import de.flapdoodle.embed.process.config.store.IDownloadConfig; +import de.flapdoodle.embed.process.io.progress.Slf4jProgressListener; import org.bson.Document; import org.junit.After; import org.junit.Rule; @@ -180,6 +183,30 @@ public class EmbeddedMongoAutoConfigurationTests { .isEqualTo("testing"); } + @Test + public void defaultDownloadConfiguration() { + load(); + IDownloadConfig downloadConfig = this.context.getBean(IDownloadConfig.class); + + assertThat(downloadConfig.getDownloadPath().getClass().getSimpleName()) + .isEqualTo("PlatformDependentDownloadPath"); + assertThat(downloadConfig.getUserAgent()).isEqualTo( + "Mozilla/5.0 (compatible; Embedded MongoDB; +https://github.com/flapdoodle-oss/embedmongo.flapdoodle.de)"); + assertThat(downloadConfig.getProgressListener()) + .isInstanceOf(Slf4jProgressListener.class); + } + + @Test + public void customizedDownloadConfiguration() { + load(TestEmbeddedMongoDownloadConfigBuilderCustomizer.class); + + IDownloadConfig downloadConfig = this.context.getBean(IDownloadConfig.class); + assertThat(downloadConfig.getDownloadPath().getPath(null)).isEqualTo("test"); + assertThat(downloadConfig.getUserAgent()).isEqualTo("Test User Agent"); + assertThat(downloadConfig.getProgressListener()) + .isInstanceOf(Slf4jProgressListener.class); + } + private void assertVersionConfiguration(String configuredVersion, String expectedVersion) { this.context = new AnnotationConfigApplicationContext(); @@ -227,4 +254,15 @@ public class EmbeddedMongoAutoConfigurationTests { } + private static class TestEmbeddedMongoDownloadConfigBuilderCustomizer + implements EmbeddedMongoDownloadConfigBuilderCustomizer { + + @Override + public void customize(DownloadConfigBuilder downloadConfigBuilder) { + downloadConfigBuilder.downloadPath("test"); + downloadConfigBuilder.userAgent("Test User Agent"); + } + + } + }