java操作XML文档转为JSON数据格式
一、使用的maven依赖
org.dom4jdom4j2.1.3
二、代码实现
import com.alibaba.fastjson2.JSONArray;import com.alibaba.fastjson2.JSONObject;import com.ruoyi.common.utils.StringUtils;import org.dom4j.*;import org.dom4j.Document;import org.dom4j.Element;import org.dom4j.io.SAXReader;import java.io.*;import java.util.*;public class XMLParse{//文件路径static String path = "D:\\DevelopWorkspace\\MY\\opensource-framework\\RuoYi-Vue\\doc\\DataSourceConfig.xml";public static void main(String[] args) throws Exception {//1、读取文件并转换为Document文档对象Document doc = new SAXReader().read(new File(path));//2、使用asXML()方法将DOM文档对象转换为字符串String s = doc.asXML();//3、调用自定义的方法转换为JSON数据格式JSONObject jsonObject = startXMLToJSON(s);//4、输出结果System.out.println(jsonObject);}/** * 自定义*/public static JSONObject startXMLToJSON(String xml){//1、定义JSON对象保存结果JSONObject result = new JSONObject();try {//2、使用DocumentHelper.parseText()转换为DOM文档对象Document document = DocumentHelper.parseText(xml);//3、获取DOM文档根节点Element rootElement = document.getRootElement();//4、调用自定义的方法转换为JSON数据格式parseJson(rootElement,result);} catch (DocumentException e) {e.printStackTrace();}return result;}public static void parseJson(Element element,JSONObject result){//1、获取子节点列表List elements = element.elements();//2、循环子节点列表获取数据for (Element e:elements) {//3、有数据则获取if (!e.elements().isEmpty() && !e.getText().isEmpty()){//4、定义另一个JSON对象保存子节点JSON数据JSONObject cjson = new JSONObject();//5、此处调用自身继续方法继续循环取值,知道遍历完所有字节点数据parseJson(e,cjson);if (!cjson.isEmpty()){//6、添加到JSON对象result.put(e.getName(),cjson);}}else {if (!e.getText().isEmpty()){//6、添加到JSON对象result.put(e.getName(),e.getText());}}}} }
Debug流程源码解析
1、SAXReader加载XML文件,创建DOM文档对象
//1、读取文件并转换为Document文档对象Document doc = new SAXReader().read(new File(path));
①、调用SAXReader.read(File file)方法
阐述:
【注释意思】:从给定的文件参数中读取文档:
1、file–是要读取的文件。
2、返回:新创建的Document实例
3、抛出:DocumentException–如果在解析过程中发生错误
【执行步骤】:
1、使用new InputSource(new FileInputStream(file))获取文件输入流对象source
2、校验字符编码,此处并没有设置
3、file.getAbsolutePath()获取文件file的绝对路径
4、文件路径path不为空则统一文件路径的分隔符/
5、最后将文件输入流对象source作为参数调用read(source)方法
Reads a Document from the given FileParams:file – is the File to read from.Returns:the newly created Document instanceThrows:DocumentException – if an error occurs during parsing.public Document read(File file) throws DocumentException {try {/* * We cannot convert the file to an URL because if the filename * contains '#' characters, there will be problems with the URL in * the InputSource (because a URL like * http://myhost.com/index#anchor is treated the same as * http://myhost.com/index) Thanks to Christian Oetterli */ //1、使用new InputSource(new FileInputStream(file))获取文件输入流对象sourceInputSource source = new InputSource(new FileInputStream(file));//2、校验字符编码,此处并没有设置if (this.encoding != null) {source.setEncoding(this.encoding);}//3、file.getAbsolutePath()获取文件file的绝对路径String path = file.getAbsolutePath();//4、文件路径path不为空则统一文件路径的分隔符/if (path != null) {// Code taken from Ant FileUtilsStringBuffer sb = new StringBuffer("file://");// add an extra slash for filesystems with drive-specifiersif (!path.startsWith(File.separator)) {sb.append("/");}path = path.replace('\\', '/');sb.append(path);source.setSystemId(sb.toString());}//5、最后将文件输入流对象source作为参数调用read(source)方法return read(source);} catch (FileNotFoundException e) {throw new DocumentException(e.getMessage(), e);}}
②调用read(InputSource in)方法
阐述:
【注释意思】:使用SAXParams从给定的InputSource读取文档:
1、in–要读取的InputSource。
2、返回:新创建的Document实例
3、抛出:DocumentException–如果在解析过程中发生错误。
public Document read(InputSource in) throws DocumentException {try {XMLReader reader = getXMLReader();reader = installXMLFilter(reader);EntityResolver thatEntityResolver = this.entityResolver;if (thatEntityResolver == null) {thatEntityResolver = createDefaultEntityResolver(in.getSystemId());this.entityResolver = thatEntityResolver;}reader.setEntityResolver(thatEntityResolver);SAXContentHandler contentHandler = createContentHandler(reader);contentHandler.setEntityResolver(thatEntityResolver);contentHandler.setInputSource(in);boolean internal = isIncludeInternalDTDDeclarations();boolean external = isIncludeExternalDTDDeclarations();contentHandler.setIncludeInternalDTDDeclarations(internal);contentHandler.setIncludeExternalDTDDeclarations(external);contentHandler.setMergeAdjacentText(isMergeAdjacentText());contentHandler.setStripWhitespaceText(isStripWhitespaceText());contentHandler.setIgnoreComments(isIgnoreComments());reader.setContentHandler(contentHandler);configureReader(reader, contentHandler);reader.parse(in);return contentHandler.getDocument();} catch (Exception e) {if (e instanceof SAXParseException) {// e.printStackTrace();SAXParseException parseException = (SAXParseException) e;String systemId = parseException.getSystemId();if (systemId == null) {systemId = "";}String message = "Error on line "+ parseException.getLineNumber() + " of document "+ systemId + " : " + parseException.getMessage();throw new DocumentException(message, e);} else {throw new DocumentException(e.getMessage(), e);}}}
2、Document使用asXML()方法将DOM文档对象转换为字符串,该方法继承接口Node
阐述:
【注释意思】:
asXML返回该节点的文本XML表示。
1、返回:此节点的XML表示形式
2、接口返回数据类型:String
3、接口实现类 AbstractDocument
【执行步骤】:
1、使用OutputFormat定义输出XML文件流格式
2、StringWriter作为字符串输出缓冲区
3、创建XMLWriter并输出对象
4、最后返回输出到StringWriter的字符串
/** * * asXML
returns the textual XML representation of this node. *
** @return the XML representation of this node */String asXML();
public String asXML() {//1、使用OutputFormat定义输出XML文件流格式OutputFormat format = new OutputFormat();//2、定义编码格式,建议使用UTF-8format.setEncoding(encoding);try {//3、创建StringWriter作为字符串输出缓冲区StringWriter out = new StringWriter();//4、创建XMLWriter并输出对象XMLWriter writer = new XMLWriter(out, format);writer.write(this);writer.flush();//5、最后返回输出到StringWriter的字符串return out.toString();} catch (IOException e) {throw new RuntimeException("IOException while generating textual "+ "representation: " + e.getMessage());}}
2、DocumentHelper.parseText(String text)把字符串转换为DOM对象
阐述:
【注释意思】:
<code>parseText</code>将给定的文本解析为XML文档返回新创建的文档。param 1、text要解析的XML文本
2、返回一个新解析的文档
2、如果无法解析文档,则@throws DocumentException
【执行步骤】:
1、使用OutputFormat定义输出XML文件流格式
2、StringWriter作为字符串输出缓冲区
3、创建XMLWriter并输出对象
4、最后返回输出到StringWriter的字符串
/** * * parseText
parses the given text as an XML document and * returns the newly created Document. *
** @param text *the XML text to be parsed ** @return a newly parsed Document ** @throws DocumentException * if the document could not be parsed */public static Document parseText(String text) throws DocumentException {Document result = null;//1、创建SAXReaderSAXReader reader = new SAXReader();//2、换取编码格式String encoding = getEncoding(text);//3、使用输入流读取需要解析的字符串文本InputSource source = new InputSource(new StringReader(text));//4、设置编码格式source.setEncoding(encoding);//使用read(InputSource in)方法读取解析result = reader.read(source);// if the XML parser doesn't provide a way to retrieve the encoding,// specify it manually//如果XML解析器不提供检索编码的方法,手动指定if (result.getXMLEncoding() == null) {result.setXMLEncoding(encoding);}return result;}