GuiceUtils { static void expandProperties( @Nonnull final Binder binder, @Nonnull final Properties properties) { for (final String name : properties.stringPropertyNames()) { boolean appliedSubstitution; do { appliedSubstitution = false; final String value = properties.getProperty(name); if ((value != null) && !value.trim().isEmpty()) { final Matcher matchFullSpec = REGEX_FULL_ENVVAR.matcher(value); if (matchFullSpec.find()) { final String matchedAssignment = value.substring(matchFullSpec.start(), matchFullSpec.end()); final Matcher matchedName = REGEX_ONLY_NAME.matcher(matchedAssignment); if (matchedName.find() && (matchedName.groupCount() == 2)) { final String envVarName = matchedName.group(1); final String suppliedDefaultValue = (matchedName.group(2) == null) ? null : matchedName.group(2).substring(2); if (envVarName.matches(".*?[${}].*")) { final String msg = "Property " + name + " uses incorrect environment variables name syntax: " + envVarName; LOG.error("{}", msg); binder.addError(msg); properties.remove(name); } else { @SuppressWarnings("CallToSystemGetenv") final String valueFromEnv = System.getenv(envVarName); final String valueToBeUsed; if (valueFromEnv == null) { if (suppliedDefaultValue == null) { valueToBeUsed = null; } else { valueToBeUsed = suppliedDefaultValue; } } else { valueToBeUsed = valueFromEnv; } if (valueToBeUsed == null) { properties.remove(name); } else { final String substitutedString = matchFullSpec.replaceFirst(valueToBeUsed); properties.setProperty(name, substitutedString); appliedSubstitution = true; } } } } else { if (value.contains("${")) { final String msg = "Property " + name + " uses incorrect nesting: " + name; LOG.error("{}", msg); binder.addError(msg); properties.remove(name); } } } } while (appliedSubstitution); } } private  GuiceUtils(); static void bindProperties(
            @Nonnull final Binder binder,
            @Nonnull final String primaryPropertySourceUrl,
            @Nonnull final String... secondaryPropertySourceUrls);  }
@SuppressWarnings({"rawtypes", "unchecked"}) @Test public void testExpandProperties() throws IOException, NamingException { LOG.info("testExpandProperties"); final Binder binder = Mockito.mock(Binder.class); Mockito.when(binder.skipSources(Names.class)).thenReturn(binder); Mockito.when(binder.bind(Mockito.any(Key.class))).thenReturn(Mockito.mock(LinkedBindingBuilder.class)); final Properties props = new Properties(); GuiceUtils.loadUrl(props, "classpath:" + PROPERTY_FILE_ENVVAR); GuiceUtils.expandProperties(binder, props); Mockito.verify(binder, Mockito.times(4)).addError(Mockito.any(String.class)); Assert.assertEquals(10, props.size()); final String homeValue = System.getenv("HOME"); Assert.assertEquals(homeValue, props.getProperty("envVarExists")); Assert.assertEquals(homeValue + 'y', props.getProperty("envVarExistsFront")); Assert.assertEquals("x" + homeValue + 'y', props.getProperty("envVarExistsMid")); Assert.assertEquals("x" + homeValue, props.getProperty("envVarExistsEnd")); Assert.assertEquals(null, props.getProperty("envVarDoesNotExist")); Assert.assertEquals("", props.getProperty("envVarDefaultValueUndefined")); Assert.assertEquals("{empty}", props.getProperty("envVarDefaultValueEmpty")); Assert.assertEquals("x", props.getProperty("envVarDefaultValueNonEmpty")); Assert.assertEquals(null, props.getProperty("envVarSyntaxError1")); Assert.assertEquals(null, props.getProperty("envVarSyntaxError2")); Assert.assertEquals(null, props.getProperty("envVarSyntaxError3")); Assert.assertEquals(null, props.getProperty("envVarSyntaxError4")); Assert.assertEquals("12", props.getProperty("envVarTwo1")); Assert.assertEquals("1-2", props.getProperty("envVarTwo2")); }