Stop included profiles overriding active profiles
Update `ConfigFileApplicationListener` so that `spring.profiles.include` properties do not override higher priority active profiles. This commit also changes when profiles get added to the environment. Profiles are now added to the environment at the time of profile processing so that they get logged in the order that they are processed. Closes gh-13151
This commit is contained in:
committed by
Phillip Webb
parent
60a4d67b13
commit
378c4c9535
@@ -328,6 +328,9 @@ public class ConfigFileApplicationListener
|
||||
initializeProfiles();
|
||||
while (!this.profiles.isEmpty()) {
|
||||
Profile profile = this.profiles.poll();
|
||||
if (profile != null && !profile.isDefaultProfile()) {
|
||||
addProfileToEnvironment(profile.getName());
|
||||
}
|
||||
load(profile, this::getPositiveProfileFilter,
|
||||
addToLoaded(MutablePropertySources::addLast, false));
|
||||
this.processedProfiles.add(profile);
|
||||
@@ -347,15 +350,13 @@ public class ConfigFileApplicationListener
|
||||
// first so that it is processed first and has lowest priority.
|
||||
this.profiles.add(null);
|
||||
Set<Profile> activatedViaProperty = getProfilesActivatedViaProperty();
|
||||
processOtherActiveProfiles(activatedViaProperty);
|
||||
this.profiles.addAll(getOtherActiveProfiles(activatedViaProperty));
|
||||
// Any pre-existing active profiles set via property sources (e.g.
|
||||
// System
|
||||
// properties) take precedence over those added in config files.
|
||||
// System properties) take precedence over those added in config files.
|
||||
addActiveProfiles(activatedViaProperty);
|
||||
if (this.profiles.size() == 1) { // only has null profile
|
||||
for (String defaultProfileName : this.environment.getDefaultProfiles()) {
|
||||
ConfigFileApplicationListener.Profile defaultProfile = new ConfigFileApplicationListener.Profile(
|
||||
defaultProfileName, true);
|
||||
Profile defaultProfile = new Profile(defaultProfileName, true);
|
||||
this.profiles.add(defaultProfile);
|
||||
}
|
||||
}
|
||||
@@ -373,19 +374,22 @@ public class ConfigFileApplicationListener
|
||||
return activeProfiles;
|
||||
}
|
||||
|
||||
private void processOtherActiveProfiles(Set<Profile> activatedViaProperty) {
|
||||
List<Profile> otherActiveProfiles = Arrays
|
||||
.stream(this.environment.getActiveProfiles()).map(Profile::new)
|
||||
.filter((o) -> !activatedViaProperty.contains(o))
|
||||
private List<Profile> getOtherActiveProfiles(Set<Profile> activatedViaProperty) {
|
||||
return Arrays.stream(this.environment.getActiveProfiles()).map(Profile::new)
|
||||
.filter((profile) -> !activatedViaProperty.contains(profile))
|
||||
.collect(Collectors.toList());
|
||||
this.profiles.addAll(otherActiveProfiles);
|
||||
}
|
||||
|
||||
void addActiveProfiles(Set<Profile> profiles) {
|
||||
if (this.activatedProfiles || profiles.isEmpty()) {
|
||||
if (profiles.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
addProfiles(profiles);
|
||||
if (this.activatedProfiles) {
|
||||
this.logger.debug("Profiles already activated, '" + profiles
|
||||
+ "' will not be applied");
|
||||
return;
|
||||
}
|
||||
this.profiles.addAll(profiles);
|
||||
if (this.logger.isDebugEnabled()) {
|
||||
this.logger.debug("Activated activeProfiles "
|
||||
+ StringUtils.collectionToCommaDelimitedString(profiles));
|
||||
@@ -394,13 +398,6 @@ public class ConfigFileApplicationListener
|
||||
removeUnprocessedDefaultProfiles();
|
||||
}
|
||||
|
||||
void addProfiles(Set<Profile> profiles) {
|
||||
for (Profile profile : profiles) {
|
||||
this.profiles.add(profile);
|
||||
addProfileToEnvironment(profile.getName());
|
||||
}
|
||||
}
|
||||
|
||||
private void removeUnprocessedDefaultProfiles() {
|
||||
this.profiles.removeIf(
|
||||
(profile) -> (profile != null && profile.isDefaultProfile()));
|
||||
@@ -526,7 +523,7 @@ public class ConfigFileApplicationListener
|
||||
for (Document document : documents) {
|
||||
if (filter.match(document)) {
|
||||
addActiveProfiles(document.getActiveProfiles());
|
||||
addProfiles(document.getIncludeProfiles());
|
||||
addIncludedProfiles(document.getIncludeProfiles());
|
||||
loaded.add(document);
|
||||
}
|
||||
}
|
||||
@@ -542,6 +539,13 @@ public class ConfigFileApplicationListener
|
||||
}
|
||||
}
|
||||
|
||||
private void addIncludedProfiles(Set<Profile> includeProfiles) {
|
||||
LinkedList<Profile> existingProfiles = new LinkedList<>(this.profiles);
|
||||
this.profiles.clear();
|
||||
this.profiles.addAll(includeProfiles);
|
||||
this.profiles.addAll(existingProfiles);
|
||||
}
|
||||
|
||||
private List<Document> loadDocuments(PropertySourceLoader loader, String name,
|
||||
Resource resource) throws IOException {
|
||||
DocumentsCacheKey cacheKey = new DocumentsCacheKey(loader, resource);
|
||||
|
||||
@@ -94,7 +94,7 @@ public class ConfigFileApplicationListenerYamlProfileNegationTests {
|
||||
application.setWebApplicationType(WebApplicationType.NONE);
|
||||
String configName = "--spring.config.name=cascadingprofiles";
|
||||
this.context = application.run(configName);
|
||||
assertVersionProperty(this.context, "E", "A", "B", "C", "E", "D");
|
||||
assertVersionProperty(this.context, "D", "A", "C", "E", "B", "D");
|
||||
assertThat(this.context.getEnvironment().getProperty("not-a")).isNull();
|
||||
assertThat(this.context.getEnvironment().getProperty("not-b")).isNull();
|
||||
assertThat(this.context.getEnvironment().getProperty("not-c")).isNull();
|
||||
|
||||
@@ -12,6 +12,7 @@ spring:
|
||||
include:
|
||||
- C
|
||||
- E
|
||||
version: A
|
||||
|
||||
---
|
||||
spring.profiles: B
|
||||
@@ -21,6 +22,19 @@ spring:
|
||||
include:
|
||||
- D
|
||||
- E
|
||||
version: B
|
||||
|
||||
---
|
||||
spring.profiles: C
|
||||
|
||||
version: C
|
||||
|
||||
|
||||
---
|
||||
spring.profiles: D
|
||||
|
||||
version: D
|
||||
|
||||
|
||||
---
|
||||
spring.profiles: E
|
||||
|
||||
Reference in New Issue
Block a user