package io.micronaut.context.env;
import io.micronaut.context.exceptions.ConfigurationException;
import io.micronaut.core.io.ResourceLoader;
import io.micronaut.core.order.Ordered;
import io.micronaut.core.util.Toggleable;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.io.InputStream;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
public abstract class AbstractPropertySourceLoader implements PropertySourceLoader, Toggleable, Ordered {
public static final int DEFAULT_POSITION = EnvironmentPropertySource.POSITION - 100;
private static final Logger LOG = LoggerFactory.getLogger(AbstractPropertySourceLoader.class);
@Override
public int getOrder() {
return DEFAULT_POSITION;
}
@Override
public Optional<PropertySource> load(String resourceName, ResourceLoader resourceLoader) {
return load(resourceLoader, resourceName, getOrder());
}
@Override
public Optional<PropertySource> loadEnv(String resourceName, ResourceLoader resourceLoader, ActiveEnvironment activeEnvironment) {
return load(resourceLoader, resourceName + "-" + activeEnvironment.getName(), this.getOrder() + 1 + activeEnvironment.getPriority());
}
private Optional<PropertySource> load(ResourceLoader resourceLoader, String fileName, int order) {
if (isEnabled()) {
Set<String> extensions = getExtensions();
for (String ext : extensions) {
String fileExt = fileName + "." + ext;
Map<String, Object> finalMap = loadProperties(resourceLoader, fileName, fileExt);
if (!finalMap.isEmpty()) {
return Optional.of(createPropertySource(fileName, finalMap, order));
}
}
}
return Optional.empty();
}
protected MapPropertySource createPropertySource(String name, Map<String, Object> map, int order) {
return new MapPropertySource(name, map) {
@Override
public int getOrder() {
return order;
}
};
}
private Map<String, Object> loadProperties(ResourceLoader resourceLoader, String qualifiedName, String fileName) {
Optional<InputStream> config = readInput(resourceLoader, fileName);
if (config.isPresent()) {
if (LOG.isDebugEnabled()) {
LOG.debug("Found PropertySource for file name: " + fileName);
}
try (InputStream input = config.get()) {
return read(qualifiedName, input);
} catch (IOException e) {
throw new ConfigurationException("I/O exception occurred reading [" + fileName + "]: " + e.getMessage(), e);
}
} else {
if (LOG.isDebugEnabled()) {
LOG.debug("No PropertySource found for file name: " + fileName);
}
}
return Collections.emptyMap();
}
@Override
public Map<String, Object> read(String name, InputStream input) throws IOException {
Map<String, Object> finalMap = new LinkedHashMap<>();
processInput(name, input, finalMap);
return finalMap;
}
protected Optional<InputStream> readInput(ResourceLoader resourceLoader, String fileName) {
return resourceLoader.getResourceAsStream(fileName);
}
protected abstract void processInput(String name, InputStream input, Map<String, Object> finalMap) throws IOException;
protected void processMap(Map<String, Object> finalMap, Map map, String prefix) {
for (Object o : map.entrySet()) {
Map.Entry entry = (Map.Entry) o;
String key = entry.getKey().toString();
Object value = entry.getValue();
if (value instanceof Map && !((Map) value).isEmpty()) {
processMap(finalMap, (Map) value, prefix + key + '.');
} else {
finalMap.put(prefix + key, value);
}
}
}
}