我需要检索其键以不同前缀开头的所有属性(例如,所有以“ log4j.appender。开头的属性”),并编写以下代码(使用Java 8的流和lamda)。
public static Map<String,Object> getPropertiesStartingWith( ConfigurableEnvironment aEnv,
String aKeyPrefix )
{
Map<String,Object> result = new HashMap<>();
Map<String,Object> map = getAllProperties( aEnv );
for (Entry<String, Object> entry : map.entrySet())
{
String key = entry.getKey();
if ( key.startsWith( aKeyPrefix ) )
{
result.put( key, entry.getValue() );
}
}
return result;
}
public static Map<String,Object> getAllProperties( ConfigurableEnvironment aEnv )
{
Map<String,Object> result = new HashMap<>();
aEnv.getPropertySources().forEach( ps -> addAll( result, getAllProperties( ps ) ) );
return result;
}
public static Map<String,Object> getAllProperties( PropertySource<?> aPropSource )
{
Map<String,Object> result = new HashMap<>();
if ( aPropSource instanceof CompositePropertySource)
{
CompositePropertySource cps = (CompositePropertySource) aPropSource;
cps.getPropertySources().forEach( ps -> addAll( result, getAllProperties( ps ) ) );
return result;
}
if ( aPropSource instanceof EnumerablePropertySource<?> )
{
EnumerablePropertySource<?> ps = (EnumerablePropertySource<?>) aPropSource;
Arrays.asList( ps.getPropertyNames() ).forEach( key -> result.put( key, ps.getProperty( key ) ) );
return result;
}
myLog.debug( "Given PropertySource is instanceof " + aPropSource.getClass().getName()
+ " and cannot be iterated" );
return result;
}
private static void addAll( Map<String, Object> aBase, Map<String, Object> aToBeAdded )
{
for (Entry<String, Object> entry : aToBeAdded.entrySet())
{
if ( aBase.containsKey( entry.getKey() ) )
{
continue;
}
aBase.put( entry.getKey(), entry.getValue() );
}
}
请注意,起点是ConfigurableEnvironment,它能够返回嵌入的PropertySources(ConfigurableEnvironment是Environment的直接后代)。您可以通过以下方式自动接线:
@Autowired
private ConfigurableEnvironment myEnv;
如果您不使用非常特殊的属性源(例如JndiPropertySource,它通常在spring自动配置中不使用),则可以检索环境中保存的所有属性。
该实现依赖于spring本身提供并采用第一个发现的属性的迭代顺序,所有后来发现的具有相同名称的所有属性都将被丢弃。这应该确保与直接向环境请求属性(返回第一个找到的属性)的行为相同。
还请注意,如果返回的属性包含$ {...}运算符的别名,则尚未解析。如果要解决特定的密钥,则必须再次直接询问环境:
myEnv.getProperty( key );