package com.mastfrog.giulius; import com.google.inject.AbstractModule; import com.google.inject.Binder; import com.google.inject.Guice; import com.google.inject.Inject; import com.google.inject.Injector; import com.google.inject.Key; import com.google.inject.Provider; import com.google.inject.Stage; import com.google.inject.name.Named; import com.google.inject.name.Names; import java.util.Enumeration; import java.util.Properties; import org.junit.Test; import static org.junit.Assert.*; /** * * @author Tim Boudreau */ public class MutabilityTest { @Test public void test() { M m = new M(); Injector i = Guice.createInjector(Stage.PRODUCTION, m); T t = i.getInstance(T.class); assertEquals("This is a", t.a); m.p.setProperty("a", "Changed!"); T t2 = i.getInstance(T.class); assertEquals("Changed!", t2.a); R r = i.getInstance(R.class); assertEquals(23, r.skidoo); } static class M extends AbstractModule { final Properties p = new Properties(); M() { p.setProperty("a", "This is a"); p.setProperty("b", "This is b"); p.setProperty("skidoo", "" + 23); } @Override protected void configure() { bindProperties(binder(), p); } } public static void bindProperties(Binder binder, Properties properties) { binder = binder.skipSources(Names.class); // use enumeration to include the default properties for (Enumeration<?> e = properties.propertyNames(); e.hasMoreElements();) { String propertyName = (String) e.nextElement(); Named n = Names.named(propertyName); PropertyProvider p = new PropertyProvider(propertyName, properties); binder.bind(Key.get(String.class, n)).toProvider(p); binder.bind(Key.get(Integer.class, n)).toProvider(new IntProvider(p)); binder.bind(Key.get(Boolean.class, n)).toProvider(new BooleanProvider(p)); } } private static class IntProvider implements Provider<Integer> { private final Provider<String> p; IntProvider(Provider<String> p) { this.p = p; } @Override public Integer get() { String s = p.get(); return s == null ? null : Integer.parseInt(p.get()); } } private static class BooleanProvider implements Provider<Boolean> { private final Provider<String> p; BooleanProvider(Provider<String> p) { this.p = p; } @Override public Boolean get() { String s = p.get(); return s == null ? false : Boolean.valueOf(s); } } private static class PropertyProvider implements Provider<String> { private final String key; private final Properties props; PropertyProvider(String key, Properties props) { this.key = key; this.props = props; } @Override public String get() { return props.getProperty(key); } } static class T { private final String a; private final String b; @Inject T(@Named("a") String a, @Named("a") String b) { this.a = a; this.b = b; } } static class Q { private final String c; Q(@Named("c") String c) { this.c = c; } } static class R { final int skidoo; @Inject R(@Named("skidoo") int skidoo) { this.skidoo = skidoo; } } }