锦囊1—读取XML文件转换为String

需求

当时有个需求是,前端要展示一个XML文件(具体是bpm2流程文件)的内容。一般来说,后端返回文件的下载URL,前端下载读取即可,但啥原因忘记了,还是由后端返回文件内容给前端。即读取XML文件,将其标签在内的所有内容转换为String来返回。

读取本地文件的demo

/**
 * 代码片段
 * 读取本地文件的demo
 */
try {
    // 读取 xml 文件
    File fileinput = new File("C:\\Users\\c-xiongb01\\Documents\\WXWork\\1688851135150110\\Cache\\File\\2021-12\\diagram.XML");
    DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
    DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
    Document doc = dBuilder.parse(fileinput);

    // 方法1:将xml文件转化为String
    StringWriter sw = new StringWriter();
    TransformerFactory tf = TransformerFactory.newInstance();
    Transformer transformer = tf.newTransformer();
    transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "no");
    transformer.setOutputProperty(OutputKeys.METHOD, "xml");
    transformer.setOutputProperty(OutputKeys.INDENT, "yes");
    transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
    transformer.transform(new DOMSource(doc), new StreamResult(sw));
    System.out.println(sw.toString());
    System.out.println("end");

    //方法二,和方法一类似,但格式与文件原本的样式不是一模一样
    //DOMSource domSource = new DOMSource(doc);
    //StringWriter writer = new StringWriter();
    //StreamResult result = new StreamResult(writer);
    //TransformerFactory tf = TransformerFactory.newInstance();
    //Transformer transformer = tf.newTransformer();
    //transformer.transform(domSource, result);
    //System.out.println(writer.toString());


} catch (Exception e) {
    log.error("getReviseBpmnFile 读取文件异常,url:" + reviseBpmnFile);
    throw new BusinessException("读取文件异常!");
}

读取远程文件的demo

/**
 * 代码片段
 * 读取远程文件的demo
 */
String reviseBpmnFile = "远程文件地址,比如oss的文件url";
String fileString = "";
try {

    //读取远程文件URl
    InputStream in = LoadFile.downLoadFile(reviseBpmnFile);
    //读取 xml 文件
    File fileinput = LoadFile.copyInputStreamToFile(in);

    DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
    DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
    Document doc = dBuilder.parse(fileinput);

    //将xml文件转化为String
    StringWriter sw = new StringWriter();
    TransformerFactory tf = TransformerFactory.newInstance();
    Transformer transformer = tf.newTransformer();
    transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "no");
    transformer.setOutputProperty(OutputKeys.METHOD, "xml");
    transformer.setOutputProperty(OutputKeys.INDENT, "yes");
    transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
    transformer.transform(new DOMSource(doc), new StreamResult(sw));
    fileString = sw.toString();
} catch (Exception e) {
    log.error("getReviseBpmnFile 读取文件异常,url:" + reviseBpmnFile);
    throw new BusinessException("读取文件异常!");
}



//LoadFile工具类
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;

public class LoadFile {

public static InputStream downLoadFile(String url) {
        try {
            URL file1 = new URL(url);
            HttpURLConnection httpConnection = (HttpURLConnection) file1.openConnection();
            InputStream input = httpConnection.getInputStream();
            return input;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 将InputStream流转化为File文件对象
     *
     * @param inputStream
     * @return
     * @throws IOException
     */
public static File copyInputStreamToFile(InputStream inputStream) throws IOException {
        File file = new File("README.md");//临时读取的文件,要保证路径存在
        try (FileOutputStream outputStream = new FileOutputStream(file)) {
            int read;
            byte[] bytes = new byte[1024];
            while ((read = inputStream.read(bytes)) != -1) {
                outputStream.write(bytes, 0, read);
            }
        }
        return file;
    }
}

思考

文件内容过大,Java 的String类型能够接收吗
程序员都知道,Java中的类型变量的容量是有限的,超过容量就会报异常。此接口完成之后,就当心文件内容过大,超过String的容量,因此就去查阅相关资料。

JDK8及其以前String使用char数组,JDK9及其以后使用Byte数组。

从编译角度,数组有效长度是【0-65565】但是第二个加粗的地方又解释了,因为虚拟机还需要1个字节的指令作为结束,所以其实真正的有效范围是【0-65564】。

从运行角度,类Integer我们可以看到Integer的最大范围是2^31, 由于数组是从0开始的,所以数组的最长的尝长度可以使【0~2^31 】通过计算是大概4GB。

这里读取的使BPM2流程土,一般流程图内容超过4GB的还是很少的。

上一篇:MyBatis课堂笔记


下一篇:web.xml配置详解