@Override
  public AppSettings load() {
    Properties p = loadPropertiesFile(homeDir);
    Set<String> keysOverridableFromEnv = stream(ProcessProperties.Property.values()).map(ProcessProperties.Property::getKey)
      .collect(Collectors.toSet());
    keysOverridableFromEnv.addAll(p.stringPropertyNames());

    // 1st pass to load static properties
    Props staticProps = reloadProperties(keysOverridableFromEnv, p);
    keysOverridableFromEnv.addAll(getDynamicPropertiesKeys(staticProps));

    // 2nd pass to load dynamic properties like `ldap.*.url` or `ldap.*.baseDn` which keys depend on values of static
    // properties loaded in 1st step
    Props props = reloadProperties(keysOverridableFromEnv, p);

    new ProcessProperties(serviceLoaderWrapper).completeDefaults(props);
    stream(consumers).forEach(c -> c.accept(props));
    return new AppSettingsImpl(props);
  }
@Test
  public void load_properties_from_env() throws Exception {
    when(system.getenv()).thenReturn(ImmutableMap.of(
      "SONAR_DASHED_PROPERTY", "2",
      "SONAR_JDBC_URL", "some_jdbc_url",
      "SONAR_EMBEDDEDDATABASE_PORT", "8765"));
    when(system.getenv("SONAR_DASHED_PROPERTY")).thenReturn("2");
    when(system.getenv("SONAR_JDBC_URL")).thenReturn("some_jdbc_url");
    when(system.getenv("SONAR_EMBEDDEDDATABASE_PORT")).thenReturn("8765");
    File homeDir = temp.newFolder();
    File propsFile = new File(homeDir, "conf/sonar.properties");
    FileUtils.write(propsFile, "sonar.dashed-property=1", UTF_8);
    AppSettingsLoaderImpl underTest = new AppSettingsLoaderImpl(system, new String[0], homeDir, serviceLoaderWrapper);

    AppSettings settings = underTest.load();

    assertThat(settings.getProps().rawProperties()).contains(
      entry("sonar.dashed-property", "2"),
      entry("sonar.jdbc.url", "some_jdbc_url"),
      entry("sonar.embeddedDatabase.port", "8765"));
  }