From 08857b4c7f4d6708b4e94ff64aade8ef5d6c20e5 Mon Sep 17 00:00:00 2001 From: Phillip Webb Date: Wed, 5 Nov 2025 14:30:31 -0800 Subject: [PATCH] Cache SystemEnvironmentPropertyMapper configuration property names Add a static cache to `SystemEnvironmentPropertyMapper` for property source name to configuration property name conversion. This update should help ease object allocations for system environment names which are unlikely to change often. Closes gh-14121 --- .../source/SystemEnvironmentPropertyMapper.java | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/core/spring-boot/src/main/java/org/springframework/boot/context/properties/source/SystemEnvironmentPropertyMapper.java b/core/spring-boot/src/main/java/org/springframework/boot/context/properties/source/SystemEnvironmentPropertyMapper.java index 0c418952b24..404e6c439d9 100644 --- a/core/spring-boot/src/main/java/org/springframework/boot/context/properties/source/SystemEnvironmentPropertyMapper.java +++ b/core/spring-boot/src/main/java/org/springframework/boot/context/properties/source/SystemEnvironmentPropertyMapper.java @@ -19,9 +19,11 @@ package org.springframework.boot.context.properties.source; import java.util.ArrayList; import java.util.List; import java.util.Locale; +import java.util.Map; import java.util.function.BiPredicate; import org.springframework.boot.context.properties.source.ConfigurationPropertyName.ToStringFormat; +import org.springframework.util.ConcurrentReferenceHashMap; /** * {@link PropertyMapper} for system environment variables. Names are mapped by removing @@ -39,6 +41,8 @@ final class SystemEnvironmentPropertyMapper implements PropertyMapper { public static final PropertyMapper INSTANCE = new SystemEnvironmentPropertyMapper(); + private final Map propertySourceNameCache = new ConcurrentReferenceHashMap<>(); + @Override public List map(ConfigurationPropertyName configurationPropertyName) { List mapped = new ArrayList<>(4); @@ -57,7 +61,12 @@ final class SystemEnvironmentPropertyMapper implements PropertyMapper { @Override public ConfigurationPropertyName map(String propertySourceName) { - return convertName(propertySourceName); + ConfigurationPropertyName configurationPropertyName = this.propertySourceNameCache.get(propertySourceName); + if (configurationPropertyName == null) { + configurationPropertyName = convertName(propertySourceName); + this.propertySourceNameCache.put(propertySourceName, configurationPropertyName); + } + return configurationPropertyName; } private ConfigurationPropertyName convertName(String propertySourceName) {