簡單的分類
簡單的說配置文件的獲取方式可以分爲以下四種:
平常我們使用到的配置方式主要是local configuration,也就是配置文件放在resource中,log4j會自動查找到該文件然後解析。
整體的流程
圖看上去比較複雜,我們平時在resource文件下配置的配置文件,是從[配置文件字符串是否null ==> 是]之後的流程開始的,也就是流程圖的下半部分,我們來看看這部分的代碼。
代碼分析
private Configuration getConfiguration(final LoggerContext loggerContext, final boolean isTest, final String name) {
//這裏的name是指的context hash之後的字符串
final boolean named = Strings.isNotEmpty(name);
final ClassLoader loader = LoaderUtil.getThreadContextClassLoader();
//getFactories方法獲取的是ConfigurationFactory初始化的時候默認加載的用於解析配置文件的工廠類,分四種:
//PropertyConfigruationFactory
//JsonConfigruationFactory
//XmlConfigruationFactory
//YamlConfigruationFactory
for (final ConfigurationFactory factory : getFactories()) {
String configName;
final String prefix = isTest ? TEST_PREFIX : DEFAULT_PREFIX;
final String [] types = factory.getSupportedTypes();
if (types == null) {
continue;
}
//每一個配置工廠可能支持多個擴展名,譬如Yaml文件就有兩種:.yaml, .yml
for (final String suffix : types) {
if (suffix.equals(ALL_TYPES)) {
continue;
}
//test,context name主要就是用在此處拼接配置文件的名字,就只是如此而已
configName = named ? prefix + name + suffix : prefix + suffix;
//根據名字和當前的classloader加載配置文件
final ConfigurationSource source = ConfigurationSource.fromResource(configName, loader);
if (source != null) {
if (!factory.isActive()) {
LOGGER.warn("Found configuration file {} for inactive ConfigurationFactory {}", configName, factory.getClass().getName());
}
//調用配置工廠來解析配置文件
return factory.getConfiguration(loggerContext, source);
}
}
}
return null;
}
流程可以簡單的變成下邊這個這樣:
小結
log4j2在讀取配置文件方面比我做的工作比我想象中的要多的多~,不過仔細去看源碼的話,發現這塊代碼寫的好像不是很好,不是很容易讀。