说明
[1]、使用 dom4j + jackson 的 jar包。
[2]、支持多级节点的 xml 字符串,支持 list 。
[3]、xml 转 json 类型的字符串, xml 转 map 。
代码
import org.dom4j.Document;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;
/**
* xml 解析
**/
public class XmlParser {
/**
* xml 格式字符串转换成map,包括List
**/
public static Map<String, Object> xmlToListMap(String xml) throw Exception {
Map<String, Object> map = new HashMap<>();
// 解析字符串
Document doc = DocumentHelper.parseText(xml);
// 获取根节点
Element rootElement = doc.getRootElement();
// 获取根节点下所有节点
XmlParser.elementToMap(map, rootElement, false);
return map;
}
/**
* xml 格式字符串转换成String,包括List
**/
public static String xmlToString(String xml) throws Exception {
Map<String, Object> map = new HashMap<>();
// 解析字符串
Document doc = DocumentHelper.parseText(xml);
// 获取根节点
Element rootElement = doc.getRootElement();
// 获取根节点下所有节点
XmlParser.elementToMap(map, rootElement, false);
return Jackson.toJsonString(map);
}
/**
* 使用递归调用,将多层级 xml 转为 map
**/
public static void elementToMap(Map<String, Object> map, Element rootElement,
boolean isArray) throws Exception {
// 获取当前节点的子节点
List<Element> childElement = rootElement.elements();
/** 1、如果有子级节点 */
if (childElement.size() > 0) {
List<String> keys = new ArrayList<>();
for (Element e : childElement) {
keys.add(e.getName());
}
List<String> repeatKeys = new ArrayList<>();
/** 找出重复的key 值 */
StringBuilder build = new StringBuilder();
for (String str : keys) {
// 如果不存在返回 -1
if (build.indexOf(","+str+",") > -1) {
repeatKeys.add(str);
} else {
build.append(",").append(str).append(",");
}
}
Map<String, Object> tempMap = new HashMap<>();
/** 1.1、如果当前节点是数组 */
if (isArray) {
List<Map<String, Object>> listMap = new ArrayList<>();
/** 循环子级节点 */
elementChildToMap(childElement, repeatKeys, tempMap);
listMap.add(tempMap);
map.put(rootElement.getName(), listMap);
/** 1.2、如果当前节点不是数组 */
} else {
/** 循环子级节点 */
elementChildToMap(childElement, repeatKeys, tempMap);
map.put(rootElement.getName(), tempMap);
}
/** 2、如果没有子级节点,则将当前节点添加到map */
} else {
map.put(rootElement.getName(), rootElement.getText());
}
}
/**
* 循环子级节点
**/
public static void elementChildToMap(List<Element> childElement, List<String> repeatKeys,
Map<String, Object> tempMap) throws Excepton {
for (Element e : childElement) {
// 获取子级节点的 key
String key = e.getName();
boolean duplicate = false;
if (null != repeatKeys && !repeatKeys.isEmpty()) {
for (String str : repeatKeys) {
if (str.equals(key))
duplicate = true;
}
}
elementToMap(tempMap, e, duplicate);
}
}
}