TypeSafe#ConfigList 的使用被封死在包访问权限,所幸 TypeSafe 源码为纯 Java 且 0 依赖,直接下载源码,在他们的包里放了一个 typesafe.config.impl.ParseableWrapper 代理了 parseValue()方法出来,解决了问题,主要受 github 启发。
接下来的问题变得异常简单,通常 JSON 类被解析无非是基本类型包装类,String,List 和 Map,前两个直接 toString 转一下,后面的递归处理即可。
public final Map<String,String> parse(String key, String value){
LinkedHashMap<String, String> ret = new LinkedHashMap<>();
if(!isConfigList(value)){
ret.put(key,value);
return ret;
}
List<Object> configs = parseValue(value).unwrapped();
for(int i=0; i<configs.size(); i++){
Object o = configs.get(i);
String wrapKey = wrapKey(key, i);
ret.putAll(keyObjectToMap(wrapKey,o));
}
return ret;
}
private Map<String,String> keyObjectToMap(String key, Object o){
final LinkedHashMap<String, String> ret = new LinkedHashMap<>();
if(Objects.isNull(o)){
ret.put(key,null);
return ret;
}
switch (ObjectType.from(o.getClass())){
case HASHMAP:{
((HashMap) o).forEach((k, v)->{
String newKey = key.concat(".").concat(k.toString());
ret.putAll(keyObjectToMap(newKey, v));
});
}break;
case ARRAYLIST:{
ret.putAll(parse(key,o.toString()));
}break;
case OTHER:{
ret.put(key, o.toString());
}break;
}
return ret;
}
private enum ObjectType {
HASHMAP, ARRAYLIST, OTHER;
static ObjectType from(Class clz){
if(HashMap.class.isAssignableFrom(clz)){
return HASHMAP;
}else if (clz.isAssignableFrom(ArrayList.class)){
return ARRAYLIST;
}else {
return OTHER;
}
}
}
在这个目录稍微改一下源码解决了问题
/Users/xuzeng/Documents/usr/Java/itconfig/spring-greenwich-test/src/main/java/com/liulishuo/typesafe
TypeSafe 一个令人尴尬的事情就是使用了 HashMap 和 HashSet,违反了配置的正常顺序。为此,修改了四处为 LinkedHashMap/Set 已解决问题。