diff --git a/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironment.java b/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironment.java index 68ff61f1d1c..f8a9f961d51 100644 --- a/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironment.java +++ b/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironment.java @@ -17,6 +17,7 @@ package org.springframework.boot.context.config; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.LinkedHashSet; @@ -59,6 +60,7 @@ import org.springframework.util.StringUtils; * * @author Phillip Webb * @author Madhura Bhave + * @author Nan Chiu */ class ConfigDataEnvironment { @@ -213,16 +215,18 @@ class ConfigDataEnvironment { private void addInitialImportContributors(List initialContributors, ConfigDataLocation[] locations) { - for (int i = locations.length - 1; i >= 0; i--) { - if (ConfigDataLocation.isNotEmpty(locations[i])) { - initialContributors.add(createInitialImportContributor(locations[i])); - } - } + addInitialImportContributors(initialContributors, + Arrays.stream(locations).filter(ConfigDataLocation::isNotEmpty).toList()); } - private ConfigDataEnvironmentContributor createInitialImportContributor(ConfigDataLocation location) { - this.logger.trace(LogMessage.format("Adding initial config data import from location '%s'", location)); - return ConfigDataEnvironmentContributor.ofInitialImport(location, this.environment.getConversionService()); + private void addInitialImportContributors(List initialContributors, + List locations) { + if (!locations.isEmpty()) { + this.logger.trace(LogMessage.format("Adding initial config data import from locations %s", locations)); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImports(locations, + this.environment.getConversionService()); + initialContributors.add(contributor); + } } /** diff --git a/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributor.java b/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributor.java index c4cb3160a62..980a8eb6045 100644 --- a/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributor.java +++ b/core/spring-boot/src/main/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributor.java @@ -56,6 +56,7 @@ import org.springframework.util.CollectionUtils; * * @author Phillip Webb * @author Madhura Bhave + * @author Nan Chiu */ class ConfigDataEnvironmentContributor implements Iterable { @@ -401,14 +402,13 @@ class ConfigDataEnvironmentContributor implements Iterable initialImports, ConversionService conversionService) { - List imports = Collections.singletonList(initialImport); - ConfigDataProperties properties = new ConfigDataProperties(imports, null); + ConfigDataProperties properties = new ConfigDataProperties(initialImports, null); return new ConfigDataEnvironmentContributor(Kind.INITIAL_IMPORT, null, null, false, null, null, properties, null, null, conversionService); } diff --git a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorTests.java b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorTests.java index eaa2a601ce7..b4a965098f3 100644 --- a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorTests.java +++ b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorTests.java @@ -47,11 +47,14 @@ import static org.mockito.Mockito.mock; * @author Phillip Webb * @author Madhura Bhave * @author Scott Frederick + * @author Nan Chiu */ class ConfigDataEnvironmentContributorTests { private static final ConfigDataLocation TEST_LOCATION = ConfigDataLocation.of("test"); + private static final List TEST_LOCATIONS = List.of(TEST_LOCATION); + private final ConfigDataActivationContext activationContext = new ConfigDataActivationContext( CloudPlatform.KUBERNETES, null); @@ -59,14 +62,14 @@ class ConfigDataEnvironmentContributorTests { @Test void getKindReturnsKind() { - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(TEST_LOCATION, + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImports(TEST_LOCATIONS, this.conversionService); assertThat(contributor.getKind()).isEqualTo(Kind.INITIAL_IMPORT); } @Test void isActiveWhenPropertiesIsNullReturnsTrue() { - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(TEST_LOCATION, + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImports(TEST_LOCATIONS, this.conversionService); assertThat(contributor.isActive(null)).isTrue(); } @@ -291,12 +294,12 @@ class ConfigDataEnvironmentContributorTests { } @Test - void ofInitialImportCreatedInitialImportContributor() { - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(TEST_LOCATION, + void ofInitialImportsCreatedInitialImportContributor() { + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImports(TEST_LOCATIONS, this.conversionService); assertThat(contributor.getKind()).isEqualTo(Kind.INITIAL_IMPORT); assertThat(contributor.getResource()).isNull(); - assertThat(contributor.getImports()).containsExactly(TEST_LOCATION); + assertThat(contributor.getImports()).isEqualTo(TEST_LOCATIONS); assertThat(contributor.isActive(this.activationContext)).isTrue(); assertThat(contributor.getPropertySource()).isNull(); assertThat(contributor.getConfigurationPropertySource()).isNull(); diff --git a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorsTests.java b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorsTests.java index d47db76aa2a..f19044dfd02 100644 --- a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorsTests.java +++ b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentContributorsTests.java @@ -91,8 +91,8 @@ class ConfigDataEnvironmentContributorsTests { @Test void createCreatesWithInitialContributors() { - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, List.of(contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); @@ -123,8 +123,8 @@ class ConfigDataEnvironmentContributorsTests { new ConfigData(List.of(propertySource))); given(this.importer.resolveAndLoad(eq(this.activationContext), any(), any(), eq(locations))) .willReturn(imported); - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, List.of(contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); @@ -155,8 +155,8 @@ class ConfigDataEnvironmentContributorsTests { new ConfigData(List.of(secondPropertySource))); given(this.importer.resolveAndLoad(eq(this.activationContext), any(), any(), eq(secondLocations))) .willReturn(secondImported); - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, List.of(contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); @@ -184,8 +184,8 @@ class ConfigDataEnvironmentContributorsTests { new ConfigData(List.of(propertySource))); given(this.importer.resolveAndLoad(eq(this.activationContext), any(), any(), eq(locations))) .willReturn(imported); - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, Arrays.asList(existingContributor, contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); @@ -215,8 +215,8 @@ class ConfigDataEnvironmentContributorsTests { new ConfigData(List.of(secondPropertySource))); given(this.importer.resolveAndLoad(eq(this.activationContext), any(), any(), eq(secondLocations))) .willReturn(secondImported); - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, List.of(contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); @@ -243,8 +243,8 @@ class ConfigDataEnvironmentContributorsTests { new ConfigData(List.of(propertySource))); given(this.importer.resolveAndLoad(eq(this.activationContext), any(), any(), eq(locations))) .willReturn(imported); - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, Arrays.asList(existingContributor, contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); @@ -269,8 +269,8 @@ class ConfigDataEnvironmentContributorsTests { new ConfigData(List.of(propertySource))); given(this.importer.resolveAndLoad(eq(this.activationContext), any(), any(), eq(locations))) .willReturn(imported); - ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor.ofInitialImport(LOCATION_1, - this.conversionService); + ConfigDataEnvironmentContributor contributor = ConfigDataEnvironmentContributor + .ofInitialImports(List.of(LOCATION_1), this.conversionService); ConfigDataEnvironmentContributors contributors = new ConfigDataEnvironmentContributors(this.logFactory, this.bootstrapContext, Arrays.asList(existingContributor, contributor), this.conversionService, ConfigDataEnvironmentUpdateListener.NONE); diff --git a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentPostProcessorIntegrationTests.java b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentPostProcessorIntegrationTests.java index ed7460ceff3..1b7d1f30a00 100644 --- a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentPostProcessorIntegrationTests.java +++ b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentPostProcessorIntegrationTests.java @@ -79,6 +79,7 @@ import static org.assertj.core.api.Assertions.assertThatNoException; * * @author Madhura Bhave * @author Phillip Webb + * @author Nan Chiu */ class ConfigDataEnvironmentPostProcessorIntegrationTests { @@ -332,6 +333,25 @@ class ConfigDataEnvironmentPostProcessorIntegrationTests { assertThat(property).isEqualTo("frommyprofilepropertiesfile"); } + @Test + @WithResource(name = "testproperties-1.properties", content = """ + my.property=fromtestproperties-1.properties + """) + @WithResource(name = "testproperties-1-myprofile.properties", content = """ + my.property=fromtestproperties-1-myprofile.properties + """) + @WithResource(name = "testproperties-2.properties", content = """ + my.property=fromtestproperties-2.properties + """) + void runWhenHasImportPropertyWithProfileSpecificFileTakesPrecedence() { + ConfigurableApplicationContext context = this.application.run( + "--spring.config.import=classpath:testproperties-1.properties,classpath:testproperties-2.properties", + "--spring.profiles.active=myprofile"); + ConfigurableEnvironment environment = context.getEnvironment(); + String property = environment.getProperty("my.property"); + assertThat(property).isEqualTo("fromtestproperties-1-myprofile.properties"); + } + @Test void runWhenHasLocalFileLoadsWithLocalFileTakingPrecedenceOverClasspath() throws Exception { File localFile = new File(new File("."), "application.properties"); diff --git a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentTests.java b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentTests.java index 47bca02441d..23afe0260d0 100644 --- a/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentTests.java +++ b/core/spring-boot/src/test/java/org/springframework/boot/context/config/ConfigDataEnvironmentTests.java @@ -146,7 +146,7 @@ class ConfigDataEnvironmentTests { .map(ConfigDataEnvironmentContributor::getImports) .map(Object::toString) .toArray(); - assertThat(imports).containsExactly("[i2]", "[i1]", "[a2]", "[a1]", "[l2]", "[l1]"); + assertThat(imports).containsExactly("[i1, i2]", "[a1, a2]", "[l1, l2]"); } @Test