diff --git a/archaius2-core/src/main/java/com/netflix/archaius/ConfigMapper.java b/archaius2-core/src/main/java/com/netflix/archaius/ConfigMapper.java index af44f9e9f..99afee960 100644 --- a/archaius2-core/src/main/java/com/netflix/archaius/ConfigMapper.java +++ b/archaius2-core/src/main/java/com/netflix/archaius/ConfigMapper.java @@ -15,19 +15,19 @@ */ package com.netflix.archaius; -import java.lang.reflect.Field; -import java.lang.reflect.Method; -import java.lang.reflect.Modifier; -import java.util.HashMap; -import java.util.Map; - -import org.apache.commons.lang3.text.StrSubstitutor; - import com.netflix.archaius.api.Config; import com.netflix.archaius.api.IoCContainer; import com.netflix.archaius.api.annotations.Configuration; import com.netflix.archaius.exceptions.MappingException; import com.netflix.archaius.interpolate.ConfigStrLookup; +import org.apache.commons.lang3.text.StrSubstitutor; + +import java.lang.reflect.Field; +import java.lang.reflect.Method; +import java.lang.reflect.Modifier; +import java.util.HashMap; +import java.util.Map; +import java.util.Optional; public class ConfigMapper { private static final IoCContainer NULL_IOC_CONTAINER = new IoCContainer() { @@ -111,18 +111,8 @@ public void mapConfig(T injectee, final Config config, IoCContainer ioc) thr String name = field.getName(); Class type = field.getType(); - Object value = null; - if (type.isInterface()) { - // TODO: Do Class.newInstance() if objName is a classname - String objName = config.getString(prefix + name, null); - if (objName != null) { - value = ioc.getInstance(objName, type); - } - } - else { - value = config.get(type, prefix + name, null); - } - + Object value = getValue(config, ioc, prefix, name, type); + if (value != null) { try { field.setAccessible(true); @@ -160,17 +150,8 @@ else if (name.startsWith("with") && name.length() > 4) { method.setAccessible(true); Class type = method.getParameterTypes()[0]; - Object value = null; - if (type.isInterface()) { - String objName = config.getString(prefix + name, null); - if (objName != null) { - value = ioc.getInstance(objName, type); - } - } - else { - value = config.get(type, prefix + name, null); - } - + Object value = getValue(config, ioc, prefix, name, type); + if (value != null) { try { method.invoke(injectee, value); @@ -190,4 +171,21 @@ else if (name.startsWith("with") && name.length() > 4) { } } } + + private Object getValue(Config config, IoCContainer ioc, String prefix, String name, Class type) { + if (type.isInterface()) { + Object rawProperty = config.getRawProperty(prefix + name); + if (rawProperty != null && type.isAssignableFrom(rawProperty.getClass())) { + return rawProperty; + } + + // TODO: Do Class.newInstance() if objName is a classname + String objName = config.getString(prefix + name, null); + if (objName != null) { + return ioc.getInstance(objName, type); + } + } + + return config.get(type, prefix + name, null); + } } diff --git a/archaius2-core/src/main/java/com/netflix/archaius/config/MapConfig.java b/archaius2-core/src/main/java/com/netflix/archaius/config/MapConfig.java index 7af034b39..6ce2bc334 100644 --- a/archaius2-core/src/main/java/com/netflix/archaius/config/MapConfig.java +++ b/archaius2-core/src/main/java/com/netflix/archaius/config/MapConfig.java @@ -41,10 +41,10 @@ public class MapConfig extends AbstractConfig { * @author elandau */ public static class Builder { - Map map = new HashMap(); - + Map map = new HashMap(); + public Builder put(String key, T value) { - map.put(key, value.toString()); + map.put(key, value); return this; } @@ -60,19 +60,18 @@ public static Builder builder() { public static MapConfig from(Properties props) { return new MapConfig(props); } - - public static MapConfig from(Map props) { + + public static MapConfig from(Map props) { return new MapConfig(props); } - - private Map props = new HashMap(); - + + private Map props = new HashMap(); + /** * Construct a MapConfig as a copy of the provided Map - * @param name * @param props */ - public MapConfig(Map props) { + public MapConfig(Map props) { this.props.putAll(props); this.props = Collections.unmodifiableMap(this.props); } diff --git a/archaius2-guice/src/test/java/com/netflix/archaius/guice/ArchaiusModuleTest.java b/archaius2-guice/src/test/java/com/netflix/archaius/guice/ArchaiusModuleTest.java index 86a34b2d5..73fd7a7c5 100644 --- a/archaius2-guice/src/test/java/com/netflix/archaius/guice/ArchaiusModuleTest.java +++ b/archaius2-guice/src/test/java/com/netflix/archaius/guice/ArchaiusModuleTest.java @@ -15,13 +15,7 @@ */ package com.netflix.archaius.guice; -import java.util.Properties; - -import javax.inject.Inject; - -import org.junit.Assert; -import org.junit.Test; - +import com.google.common.collect.Lists; import com.google.inject.AbstractModule; import com.google.inject.Guice; import com.google.inject.Injector; @@ -45,6 +39,13 @@ import com.netflix.archaius.config.MapConfig; import com.netflix.archaius.exceptions.MappingException; import com.netflix.archaius.visitor.PrintStreamVisitor; +import org.junit.Assert; +import org.junit.Test; + +import javax.inject.Inject; +import java.util.Date; +import java.util.List; +import java.util.Properties; public class ArchaiusModuleTest { @@ -63,6 +64,8 @@ public static class MyServiceConfig { private Boolean bool_value; private Double double_value; private Property fast_int; + private List int_list; + private Date date; private Named named; public void setStr_value(String value) { @@ -342,4 +345,27 @@ public TestProxyConfig getProxyConfig(ConfigProxyFactory factory) { Assert.assertArrayEquals(new String[]{"foo", "bar"}, configProxy.getStringArray()); Assert.assertArrayEquals(new Integer[]{1,2}, configProxy.getIntArray()); } + + @Test + public void testObjectInjection() throws MappingException { + Date date = new Date(100); + final Config config = MapConfig.builder() + .put("env", "prod") + .put("prefix-prod.int_list", Lists.newArrayList(1, 2, 3)) + .put("prefix-prod.date", date) + .build(); + + Injector injector = Guice.createInjector( + new ArchaiusModule() { + @Override + protected void configureArchaius() { + bindApplicationConfigurationOverride().toInstance(config); + } + }); + + MyServiceConfig serviceConfig = injector.getInstance(MyServiceConfig.class); + Assert.assertEquals(Lists.newArrayList(1, 2, 3), serviceConfig.int_list); + Assert.assertEquals(date, serviceConfig.date); + } + }