@@ -107,12 +107,15 @@ class MpConfigImpl implements Config {
107107
108108 @ Override
109109 public ConfigValue getConfigValue (String key ) {
110+ String profiledKey = null ;
111+ if (configProfile != null ) {
112+ profiledKey = "%" + configProfile + "." + key ;
113+ }
110114 if (configProfile == null ) {
111- return findConfigValue (key )
115+ return findConfigValue (key , Optional . empty () )
112116 .orElseGet (() -> new ConfigValueImpl (key , null , null , null , 0 ));
113117 }
114- return findConfigValue ("%" + configProfile + "." + key )
115- .or (() -> findConfigValue (key ))
118+ return findConfigValue (key , Optional .of (profiledKey ))
116119 .orElseGet (() -> new ConfigValueImpl (key , null , null , null , 0 ));
117120 }
118121
@@ -126,70 +129,88 @@ public <T> T getValue(String propertyName, Class<T> propertyType) {
126129 @ SuppressWarnings ("unchecked" )
127130 @ Override
128131 public <T > Optional <T > getOptionalValue (String propertyName , Class <T > propertyType ) {
132+ String profiledPropertyName = null ;
133+ if (configProfile != null ) {
134+ profiledPropertyName = "%" + configProfile + "." + propertyName ;
135+ }
129136 if (configProfile == null ) {
130- return optionalValue (propertyName , propertyType );
137+ return optionalValue (propertyName , propertyType , Optional . empty () );
131138 }
132139
133- return optionalValue ("%" + configProfile + "." + propertyName , propertyType )
134- .or (() -> optionalValue (propertyName , propertyType ));
140+ return optionalValue (propertyName , propertyType , Optional .of (profiledPropertyName ));
135141 }
136142
137143 @ SuppressWarnings ("unchecked" )
138- private <T > Optional <T > optionalValue (String propertyName , Class <T > propertyType ) {
139- // let's resolve arrays
140- if (propertyType .isArray ()) {
141- Class <?> componentType = propertyType .getComponentType ();
142- // first try to see if we have a direct value
143- Optional <String > optionalValue = getOptionalValue (propertyName , String .class );
144- if (optionalValue .isPresent ()) {
145- try {
146- return Optional .of ((T ) toArray (propertyName , optionalValue .get (), componentType ));
147- } catch (NoSuchElementException e ) {
148- return Optional .empty ();
149- }
144+ private <T > Optional <T > arrayValue (String propertyName , Class <T > propertyType ) {
145+ Class <?> componentType = propertyType .getComponentType ();
146+ // first try to see if we have a direct value
147+ Optional <String > optionalValue = getOptionalValue (propertyName , String .class );
148+ if (optionalValue .isPresent ()) {
149+ try {
150+ return Optional .of ((T ) toArray (propertyName , optionalValue .get (), componentType ));
151+ } catch (NoSuchElementException e ) {
152+ return Optional .empty ();
150153 }
154+ }
151155
152- /*
153- we also support indexed value
154- e.g. for key "my.list" you can have both:
155- my.list=12,13,14
156- or (not and):
157- my.list.0=12
158- my.list.1=13
159- */
160-
161- String indexedConfigKey = propertyName + ".0" ;
162- optionalValue = getOptionalValue (indexedConfigKey , String .class );
163- if (optionalValue .isPresent ()) {
164- List <Object > result = new LinkedList <>();
165-
166- // first element is already in
167- result .add (convert (indexedConfigKey , componentType , optionalValue .get ()));
168-
169- // hardcoded limit to lists of 1000 elements
170- for (int i = 1 ; i < 1000 ; i ++) {
171- indexedConfigKey = propertyName + "." + i ;
172- optionalValue = getOptionalValue (indexedConfigKey , String .class );
173- if (optionalValue .isPresent ()) {
174- result .add (convert (indexedConfigKey , componentType , optionalValue .get ()));
175- } else {
176- // finish the iteration on first missing index
177- break ;
178- }
156+ /*
157+ we also support indexed value
158+ e.g. for key "my.list" you can have both:
159+ my.list=12,13,14
160+ or (not and):
161+ my.list.0=12
162+ my.list.1=13
163+ */
164+
165+ String indexedConfigKey = propertyName + ".0" ;
166+ optionalValue = getOptionalValue (indexedConfigKey , String .class );
167+ if (optionalValue .isPresent ()) {
168+ List <Object > result = new LinkedList <>();
169+
170+ // first element is already in
171+ result .add (convert (indexedConfigKey , componentType , optionalValue .get ()));
172+
173+ // hardcoded limit to lists of 1000 elements
174+ for (int i = 1 ; i < 1000 ; i ++) {
175+ indexedConfigKey = propertyName + "." + i ;
176+ optionalValue = getOptionalValue (indexedConfigKey , String .class );
177+ if (optionalValue .isPresent ()) {
178+ result .add (convert (indexedConfigKey , componentType , optionalValue .get ()));
179+ } else {
180+ // finish the iteration on first missing index
181+ break ;
179182 }
180- Object array = Array .newInstance (componentType , result .size ());
181- for (int i = 0 ; i < result .size (); i ++) {
182- Object component = result .get (i );
183- Array .set (array , i , component );
184- }
185- return Optional .of ((T ) array );
186- } else {
187- return Optional .empty ();
188183 }
184+ Object array = Array .newInstance (componentType , result .size ());
185+ for (int i = 0 ; i < result .size (); i ++) {
186+ Object component = result .get (i );
187+ Array .set (array , i , component );
188+ }
189+ return Optional .of ((T ) array );
189190 } else {
190- return findConfigValue (propertyName )
191+ return Optional .empty ();
192+ }
193+ }
194+
195+ private <T > Optional <T > optionalValue (String propertyName , Class <T > propertyType , Optional <String > profiledPropertyName ) {
196+ // let's resolve arrays
197+ if (propertyType .isArray ()) {
198+ Optional <T > array = Optional .empty ();
199+ if (profiledPropertyName .isPresent ()) {
200+ // Try first with profiled property
201+ array = arrayValue (profiledPropertyName .get (), propertyType );
202+ }
203+ if (array .isEmpty ()) {
204+ array = arrayValue (propertyName , propertyType );
205+ }
206+ return array ;
207+ } else {
208+ Optional <ConfigValue > configVal = findConfigValue (propertyName , profiledPropertyName );
209+ String name = configVal .isPresent () ? configVal .get ().getName () : null ;
210+ return configVal
191211 .map (ConfigValue ::getValue )
192- .map (it -> convert (propertyName , propertyType , it ));
212+ .map (it -> convert (name , propertyType , it ));
213+
193214 }
194215 }
195216
@@ -313,35 +334,47 @@ private <T> T convert(String propertyName, Class<T> type, String value) {
313334 }
314335 }
315336
316- private Optional <ConfigValue > findConfigValue (String propertyName ) {
337+ private Optional <ConfigValue > findConfigValue (String propertyName , Optional < String > profiledPropertyName ) {
317338 for (ConfigSource source : sources ) {
318- String value = source .getValue (propertyName );
339+ String selectedProperty = null ;
340+ String value = null ;
341+ if (profiledPropertyName .isPresent ()) {
342+ // Try profiled property first
343+ selectedProperty = profiledPropertyName .get ();
344+ value = source .getValue (profiledPropertyName .get ());
345+ }
346+ if (value == null ) {
347+ selectedProperty = propertyName ;
348+ value = source .getValue (propertyName );
349+ }
319350
320351 if (null == value ) {
321352 // not in this one
322353 continue ;
323354 }
324-
355+ String rawValue = value ;
356+ String name = source .getName ();
357+ int ordinal = source .getOrdinal ();
358+ final String propName = selectedProperty ;
325359 if (value .isEmpty ()) {
326360 if (LOGGER .isLoggable (Level .TRACE )) {
327- LOGGER .log (Level .TRACE , "Found property " + propertyName
361+ LOGGER .log (Level .TRACE , "Found property " + propName
328362 + " in source " + source .getName ()
329363 + " and it is empty (removed)" );
330364 }
331- return Optional .empty ( );
365+ return Optional .of ( new ConfigValueImpl ( propName , null , rawValue , name , ordinal ) );
332366 }
333367
334368 if (LOGGER .isLoggable (Level .TRACE )) {
335- LOGGER .log (Level .TRACE , "Found property " + propertyName + " in source " + source .getName ());
369+ LOGGER .log (Level .TRACE , "Found property " + propName + " in source " + source .getName ());
336370 }
337- String rawValue = value ;
371+
338372 try {
339- return applyFilters (propertyName , value )
340- .map (it -> resolveReferences (propertyName , it ))
341- .map (it -> new ConfigValueImpl (propertyName , it , rawValue , source . getName (), source . getOrdinal () ));
373+ return applyFilters (propName , value )
374+ .map (it -> resolveReferences (propName , it ))
375+ .map (it -> new ConfigValueImpl (propName , it , rawValue , name , ordinal ));
342376 } catch (NoSuchElementException e ) {
343- // Property expression does not resolve
344- return Optional .empty ();
377+ return Optional .of (new ConfigValueImpl (propName , null , rawValue , name , ordinal ));
345378 }
346379 }
347380
0 commit comments