/configuration/src/test/java/com/proofpoint/configuration/TestConfig.java

https://github.com/ssindkar/platform · Java · 222 lines · 187 code · 19 blank · 16 comment · 6 complexity · 78f7e32dce58b8774ea3681ea12c5d12 MD5 · raw file

  1. /*
  2. * Copyright 2010 Proofpoint, Inc.
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. package com.proofpoint.configuration;
  17. import com.google.common.collect.ImmutableMap;
  18. import com.google.common.collect.ImmutableMap.Builder;
  19. import com.google.common.collect.ImmutableSet;
  20. import com.google.inject.CreationException;
  21. import com.google.inject.Guice;
  22. import com.google.inject.Injector;
  23. import com.google.inject.Key;
  24. import com.google.inject.Module;
  25. import com.google.inject.PrivateBinder;
  26. import com.google.inject.Scopes;
  27. import com.google.inject.spi.Message;
  28. import com.proofpoint.configuration.ConfigBinder.PrefixConfigBindingBuilder;
  29. import org.testng.annotations.BeforeMethod;
  30. import org.testng.annotations.Test;
  31. import javax.inject.Inject;
  32. import java.util.Collections;
  33. import java.util.List;
  34. import java.util.Map;
  35. import java.util.Map.Entry;
  36. import static com.google.inject.name.Names.named;
  37. import static com.proofpoint.configuration.ConfigBinder.bindConfig;
  38. import static org.testng.Assert.assertEquals;
  39. import static org.testng.Assert.fail;
  40. public class TestConfig
  41. {
  42. private ImmutableMap<String,String> properties;
  43. @Test
  44. public void testConfig()
  45. {
  46. Injector injector = createInjector(properties, createModule(Config1.class, null));
  47. verifyConfig(injector.getInstance(Config1.class));
  48. }
  49. @Test
  50. public void testPrefixConfigTypes()
  51. {
  52. Injector injector = createInjector(prefix("prefix", properties), createModule(Config1.class, "prefix"));
  53. verifyConfig(injector.getInstance(Config1.class));
  54. }
  55. @Test
  56. public void testConfigMapSimple()
  57. {
  58. Map<String,String> properties = ImmutableMap.<String, String>builder()
  59. .put("map.key1", "value1")
  60. .put("map.key2", "value2")
  61. .build();
  62. Injector injector = createInjector(properties, createModule(ConfigMapSimple.class, null));
  63. final ConfigMapSimple mapSimple = injector.getInstance(ConfigMapSimple.class);
  64. assertEquals(mapSimple.getMap(), ImmutableMap.of("key1", "value1", "key2", "value2"));
  65. }
  66. @Test
  67. public void testConfigMapComplex()
  68. {
  69. final ImmutableSet<Integer> keys = ImmutableSet.of(1, 2, 3, 5, 8);
  70. final Builder<String, String> builder = ImmutableMap.builder();
  71. for (Integer key : keys) {
  72. for (Entry<String, String> entry : properties.entrySet()) {
  73. builder.put("map." + key + "." + entry.getKey(), entry.getValue());
  74. }
  75. }
  76. Injector injector = createInjector(builder.build(), createModule(ConfigMapComplex.class, null));
  77. final ConfigMapComplex mapComplex = injector.getInstance(ConfigMapComplex.class);
  78. assertEquals(mapComplex.getMap().keySet(), keys);
  79. for (Config1 config1 : mapComplex.getMap().values()) {
  80. verifyConfig(config1);
  81. }
  82. }
  83. @Test
  84. public void testPrivateBinder()
  85. {
  86. Module module = binder -> {
  87. PrivateBinder privateBinder = binder.newPrivateBinder();
  88. privateBinder.install(createModule(Config1.class, null));
  89. privateBinder.bind(ExposeConfig.class).in(Scopes.SINGLETON);
  90. privateBinder.expose(ExposeConfig.class);
  91. };
  92. Injector injector = createInjector(properties, module);
  93. verifyConfig(injector.getInstance(ExposeConfig.class).config1);
  94. }
  95. @Test
  96. public void testPrivateBinderDifferentPrefix()
  97. {
  98. Module module = binder -> {
  99. PrivateBinder privateBinder = binder.newPrivateBinder();
  100. privateBinder.install(createModule(Config1.class, null));
  101. privateBinder.bind(ExposeConfig.class).annotatedWith(named("no-prefix")).to(ExposeConfig.class).in(Scopes.SINGLETON);
  102. privateBinder.expose(Key.get(ExposeConfig.class, named("no-prefix")));
  103. privateBinder = binder.newPrivateBinder();
  104. privateBinder.install(createModule(Config1.class, "prefix"));
  105. privateBinder.bind(ExposeConfig.class).annotatedWith(named("prefix")).to(ExposeConfig.class).in(Scopes.SINGLETON);
  106. privateBinder.expose(Key.get(ExposeConfig.class, named("prefix")));
  107. };
  108. properties = ImmutableMap.<String, String>builder()
  109. .putAll(properties)
  110. .put("prefix.stringOption", "a prefix string")
  111. .build();
  112. Injector injector = createInjector(properties, module);
  113. verifyConfig(injector.getInstance(Key.get(ExposeConfig.class, named("no-prefix"))).config1);
  114. assertEquals(injector.getInstance(Key.get(ExposeConfig.class, named("prefix"))).config1.getStringOption(), "a prefix string");
  115. }
  116. private static void verifyConfig(Config1 config)
  117. {
  118. assertEquals("a string", config.getStringOption());
  119. assertEquals(true, config.getBooleanOption());
  120. assertEquals(Boolean.TRUE, config.getBoxedBooleanOption());
  121. assertEquals(Byte.MAX_VALUE, config.getByteOption());
  122. assertEquals(Byte.valueOf(Byte.MAX_VALUE), config.getBoxedByteOption());
  123. assertEquals(Short.MAX_VALUE, config.getShortOption());
  124. assertEquals(Short.valueOf(Short.MAX_VALUE), config.getBoxedShortOption());
  125. assertEquals(Integer.MAX_VALUE, config.getIntegerOption());
  126. assertEquals(Integer.valueOf(Integer.MAX_VALUE), config.getBoxedIntegerOption());
  127. assertEquals(Long.MAX_VALUE, config.getLongOption());
  128. assertEquals(Long.valueOf(Long.MAX_VALUE), config.getBoxedLongOption());
  129. assertEquals(Float.MAX_VALUE, config.getFloatOption(), 0);
  130. assertEquals(Float.MAX_VALUE, config.getBoxedFloatOption());
  131. assertEquals(Double.MAX_VALUE, config.getDoubleOption(), 0);
  132. assertEquals(Double.MAX_VALUE, config.getBoxedDoubleOption());
  133. assertEquals(MyEnum.FOO, config.getMyEnumOption());
  134. assertEquals(config.getValueClassOption().getValue(), "a value class");
  135. }
  136. @Test
  137. public void testDetectsNoConfigAnnotations()
  138. {
  139. try {
  140. Injector injector = createInjector(Collections.emptyMap(), createModule(ConfigWithNoAnnotations.class, null));
  141. injector.getInstance(ConfigWithNoAnnotations.class);
  142. fail("Expected exception due to missing @Config annotations");
  143. }
  144. catch (CreationException e) {
  145. // do nothing
  146. }
  147. }
  148. private static Injector createInjector(Map<String, String> properties, Module module)
  149. {
  150. ConfigurationFactory configurationFactory = new ConfigurationFactory(properties);
  151. List<Message> messages = new ConfigurationValidator(configurationFactory).validate(module);
  152. return Guice.createInjector(new ConfigurationModule(configurationFactory), module, new ValidationErrorModule(messages));
  153. }
  154. private static <T> Module createModule(final Class<T> configClass, final String prefix)
  155. {
  156. return binder -> {
  157. PrefixConfigBindingBuilder<T> builder = bindConfig(binder).bind(configClass);
  158. if (prefix != null) {
  159. builder.prefixedWith(prefix);
  160. }
  161. };
  162. }
  163. @BeforeMethod
  164. protected void setUp()
  165. {
  166. properties = ImmutableMap.<String, String>builder()
  167. .put("stringOption", "a string")
  168. .put("booleanOption", "true")
  169. .put("boxedBooleanOption", "true")
  170. .put("byteOption", Byte.toString(Byte.MAX_VALUE))
  171. .put("boxedByteOption", Byte.toString(Byte.MAX_VALUE))
  172. .put("shortOption", Short.toString(Short.MAX_VALUE))
  173. .put("boxedShortOption", Short.toString(Short.MAX_VALUE))
  174. .put("integerOption", Integer.toString(Integer.MAX_VALUE))
  175. .put("boxedIntegerOption", Integer.toString(Integer.MAX_VALUE))
  176. .put("longOption", Long.toString(Long.MAX_VALUE))
  177. .put("boxedLongOption", Long.toString(Long.MAX_VALUE))
  178. .put("floatOption", Float.toString(Float.MAX_VALUE))
  179. .put("boxedFloatOption", Float.toString(Float.MAX_VALUE))
  180. .put("doubleOption", Double.toString(Double.MAX_VALUE))
  181. .put("boxedDoubleOption", Double.toString(Double.MAX_VALUE))
  182. .put("myEnumOption", MyEnum.FOO.toString())
  183. .put("valueClassOption", "a value class")
  184. .build();
  185. }
  186. private Map<String, String> prefix(String prefix, Map<String, String> properties)
  187. {
  188. Builder<String, String> builder = ImmutableMap.builder();
  189. for (Entry<String, String> entry : properties.entrySet()) {
  190. builder.put(prefix + "." + entry.getKey(), entry.getValue());
  191. }
  192. return builder.build();
  193. }
  194. private static class ExposeConfig
  195. {
  196. public final Config1 config1;
  197. @Inject
  198. private ExposeConfig(Config1 config1)
  199. {
  200. this.config1 = config1;
  201. }
  202. }
  203. }