文章目录


为了大家快速理解报文解析是做什么的?


简单的给大家按照企业的解析思路,给大家做了一个需求实战的真实流程,解析的报文每个厂商都不一样,因此,我自己造了一个xml报文,但是解析过程都是一样的!

1. 工具类

package com.gblfy.test.util;

import org.w3c.dom.Document;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import java.io.*;
import java.util.ArrayList;
import java.util.List;

public class XmlFileDealUtils {
/**
* 获取本地目录下的文件名
*
* @param localPath 本地文件目录
* @param fileName 本地文件名
* @throws Exception
*/
public static void getLocalFileNme(String localPath, String fileName) throws Exception {
List<String> fileNames = getCurrentDirAllFileList(localPath, fileName);
System.out.println(fileNames.size());
if (fileNames != null) {
for (String ff : fileNames) {
System.out.println("File name under directory : " + ff);
// 5.解析指定目录下的指定xml报文文件
analysisInputMsg(localPath, fileName);
}
}
}

/**
* 解析本地xml文件
*
* @param localPath
* @param fileName
* @throws Exception
*/
public static void analysisInputMsg(String localPath, String fileName) throws Exception {
// 创建一个DocumentBuilderFactory的对象
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
// 创建一个DocumentBuilder的对象
try {
// 创建DocumentBuilder对象
DocumentBuilder db = dbf.newDocumentBuilder();
// 通过DocumentBuilder对象的parser方法加载books.xml文件到当前项目下
// Document document = db.parse("books.xml");
Document document = db.parse("D:" + File.separator + "dd" + File.separator + "books20190222.xml");
// 获取所有book节点的集合
NodeList bookList = document.getElementsByTagName("book");
// 通过nodelist的getLength()方法可以获取bookList的长度
System.out.println("一共有" + bookList.getLength() + "本书");
// 遍历每一个book节点
for (int i = 0; i < bookList.getLength(); i++) {
System.out.println("=================下面开始遍历第" + (i + 1) + "本书的内容=================");
// 通过 item(i)方法 获取一个book节点,nodelist的索引值从0开始
Node book = bookList.item(i);
// 获取book节点的所有属性集合
NamedNodeMap attrs = book.getAttributes();
System.out.println("第 " + (i + 1) + "本书共有" + attrs.getLength() + "个属性");
// 遍历book的属性
for (int j = 0; j < attrs.getLength(); j++) {
// 通过item(index)方法获取book节点的某一个属性
Node attr = attrs.item(j);
// 获取属性名
System.out.print("属性名:" + attr.getNodeName());
// 获取属性值
System.out.println("--属性值" + attr.getNodeValue());
}
// 解析book节点的子节点
NodeList childNodes = book.getChildNodes();
// 遍历childNodes获取每个节点的节点名和节点值
System.out.println("第" + (i + 1) + "本书共有" + childNodes.getLength() + "个子节点");
for (int k = 0; k < childNodes.getLength(); k++) {
// 区分出text类型的node以及element类型的node
if (childNodes.item(k).getNodeType() == Node.ELEMENT_NODE) {
// 获取了element类型节点的节点名
System.out.print("第" + (k + 1) + "个节点的节点名:" + childNodes.item(k).getNodeName());
// 获取了element类型节点的节点值
System.out.println("--节点值是:" + childNodes.item(k).getFirstChild().getNodeValue());
// System.out.println("--节点值是:" + childNodes.item(k).getTextContent());
}
}
System.out.println("======================结束遍历第" + (i + 1) + "本书的内容=================");
}
} catch (ParserConfigurationException e) {
e.printStackTrace();
} catch (SAXException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}

/**
* 写请求报文至本地目录文件
*
* @param localFilePath 文件的绝对路径
* @param content 文件内容
* @param encoding 文件内容编码
* @throws IOException
*/
public static void write(String localFilePath, String fileNme, String content, String encoding) throws IOException {
boolean flag = createDir(localFilePath);
System.out.println("****" + flag);
File file = new File(localFilePath + fileNme);
file.delete();
file.createNewFile();
BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(file), encoding));
writer.write(content);
writer.close();
}

/**
* 本地创建文件夹
*
* @param destDirName
* @return
* @author gblfy
*/
public static boolean createDir(String destDirName) {
File dir = new File(destDirName);
if (!dir.exists()) {// 本地目录不存在创建
dir.mkdirs();
return true;
}
System.out.println("#本地目录已存在!:" + destDirName);
return false;
}

/**
* 遍历本地目录当前日期下面文件列表
*
* @param localFilePath
* @return
* @throws Exception
*/
public static List<String> getCurrentDirAllFileList(String localFilePath, String fileName) throws Exception {
List<String> list = new ArrayList<String>();
// 获得指定目录下所有文件名
File file = new File(localFilePath);
File[] listFiles = null;
listFiles = file.listFiles();
if (listFiles != null && listFiles.length > 0) {
for (File ff : listFiles) {
if (ff.isFile() && ff.getName().equals(fileName)) {
list.add(ff.getName());
}
}
}
return list;
}

/**
* 本地保存报文
*
* @param fileName
* @param fileContext
* @param writeTempFielPath
* @return
* @author guobin
*/
public static boolean saveLocal(String fileName, String fileContext, String writeTempFielPath) throws IOException {
BufferedWriter bw = null;
try {
File f = new File(writeTempFielPath + File.separator + fileName);
bw = new BufferedWriter(new FileWriter(f, true));
bw.write(fileContext.replaceAll("\n", "\r\n"));
bw.flush();
return true;
} catch (Exception e) {
e.printStackTrace();
System.out.println("#本地保存报文失败" + "[" + fileName + "]");
} finally {
bw.close();
}
return false;
}

/**
* 根据当前日期生成文件备份子目录 传入格式:2018-11-16 返回格式:20181116
*
* @param inputDate 日期
* @return 字符串
*/
public static String getSubDir(String inputDate) {

StringBuffer bufSubDir = new StringBuffer();
bufSubDir.append(inputDate.substring(0, 4));
bufSubDir.append(inputDate.substring(5, 7));
bufSubDir.append(inputDate.substring(8, 10));
return bufSubDir.toString();
}

}

2. 测试类

package com.sinosoft.fis.test.demo;

import com.sinosoft.fis.test.util.XmlFileDealUtils;

import java.io.File;

/**
* xml报文需求实战
* <p>
* 1.服务方接收 xml 文件。
* 2.接收报文后,将文件写到指定目录。
* 3.对本地的xml报文文件解析,取出每一个节点信息,进行数据落库操作。
*/
public class WriteFileAnalysisInputMsg {


/**
* 根据需求,将请求报文,保存到本地
* 1. 文件名日期格式处理
* 2.拼接本地保存的文件名
* 3.将接收的报文写到本地指定目录
* 4.获取指定目录下的文件名
* 5.解析指定目录下的指定xml报文文件
*/
public static void main(String[] args) throws Exception {

//第三方发送的xml报文
String content = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\r\n" + "<bookstore>\r\n"
+ " <book id=\"1\">\r\n" + " <name>钢铁是怎样炼成的</name>\r\n" + " <author>奥斯特洛夫斯基</author>\r\n"
+ " <year>2014</year>\r\n" + " <price>89</price>\r\n" + " </book>\r\n"
+ " <book id=\"2\">\r\n" + " <name>安徒生童话</name>\r\n" + " <year>2004</year>\r\n"
+ " <price>77</price>\r\n" + " <language>English</language>\r\n" + " </book> \r\n"
+ "</bookstore>";


//1. 文件名日期格式处理
String inputDate = "2019-02-22";
inputDate = XmlFileDealUtils.getSubDir(inputDate);
//2.拼接本地保存的文件名
String fileName = "books" + inputDate + ".xml";
String localFilePath = "D:" + File.separator + "dd" + File.separator;
// 3.将接收的报文写到本地指定目录
XmlFileDealUtils.write(localFilePath, fileName, content, "utf-8");
// 4.获取指定目录下的文件名
XmlFileDealUtils.getLocalFileNme(localFilePath, fileName);
}
}

3. 工具发送报文

<?xml version="1.0" encoding="UTF-8"?>
<bookstore>
<book id="1">
<name>钢铁是怎样炼成的</name>
<author>奥斯特洛夫斯基</author>
<year>2014</year>
<price>89</price>
</book>
<book id="2">
<name>安徒生童话</name>
<year>2004</year>
<price>77</price>
<language>English</language>
</book>
</bookstore>