CLIENT_MAP = new ConcurrentHashMap<>();
+ private static final Logger logger = LoggerFactory.getLogger(JaxWsDynamicClientUtil.class);
+
+ public static String send(String wsdlUrl, String namespaceUri, String operationName, Object[] params) {
+ logger.info("wsdlUrl:" + wsdlUrl + " ,namespaceUri: " + namespaceUri + " ,operationName:" + operationName + ",param:" + Arrays.toString(params));
+ try {
+ Client client = getClient(wsdlUrl);
+ Object[] result;
+ if (namespaceUri == null || namespaceUri.isEmpty()) {
+ result = client.invoke(operationName, params);
+ } else {
+ QName qName = new QName(namespaceUri, operationName);
+ result = client.invoke(qName, params);
+ }
+ logger.error("wsdlUrl:" + wsdlUrl + ",namespaceUri: " + namespaceUri + " ,operationName:" + operationName + ",param:" + Arrays.toString(params) + " 调用成功!_"+result);
+ if (result == null || result[0] == null) {
+ return null;
+ }
+ return String.valueOf(result[0]);
+ } catch (Exception ex) {
+ logger.error("wsdlUrl:" + wsdlUrl + ",namespaceUri: " + namespaceUri + " ,operationName:" + operationName + ",param:" + Arrays.toString(params) + " 调用失败了!_"+ex.getMessage(), ex);
+ return null;
+ }
+ }
+
+ public static Client getClient(String wsdlUrl) {
+ if (CLIENT_MAP.get(wsdlUrl) == null) {
+ synchronized (JaxWsDynamicClientUtil.class) {
+ if (CLIENT_MAP.get(wsdlUrl) == null) {
+ Client client = CLIENT_FACTORY.createClient(wsdlUrl);
+ setClientParam(client);
+ CLIENT_MAP.put(wsdlUrl, client);
+ }
+ }
+ }
+ return CLIENT_MAP.get(wsdlUrl);
+ }
+
+ private static void setClientParam(Client client) {
+ HTTPClientPolicy httpClientPolicy = new HTTPClientPolicy();
+ httpClientPolicy.setConnectionTimeout(30 * 1000);
+ httpClientPolicy.setAllowChunking(false);
+ httpClientPolicy.setReceiveTimeout(30 * 1000);
+ HTTPConduit clientConduit = (HTTPConduit) client.getConduit();
+ clientConduit.setClient(httpClientPolicy);
+ }
+}
diff --git a/src/main/java/com/docus/server/archive/utils/XmlUtil.java b/src/main/java/com/docus/server/archive/utils/XmlUtil.java
new file mode 100644
index 0000000..01d528b
--- /dev/null
+++ b/src/main/java/com/docus/server/archive/utils/XmlUtil.java
@@ -0,0 +1,857 @@
+/*
+ * Copyright (c) 2018-2028, DreamLu All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * Neither the name of the dreamlu.net developer nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ * Author: DreamLu 卢春梦 (596392912@qq.com)
+ */
+package com.docus.server.archive.utils;
+
+import com.docus.core.util.Exceptions;
+import com.docus.core.util.IoUtil;
+import org.springframework.lang.Nullable;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+import org.w3c.dom.NodeList;
+import org.xml.sax.InputSource;
+import org.xml.sax.SAXException;
+
+import javax.xml.namespace.QName;
+import javax.xml.parsers.DocumentBuilder;
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.parsers.ParserConfigurationException;
+import javax.xml.xpath.XPath;
+import javax.xml.xpath.XPathConstants;
+import javax.xml.xpath.XPathExpressionException;
+import javax.xml.xpath.XPathFactory;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.StringReader;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * xpath解析xml
+ *
+ *
+ * 文档地址:
+ * http://www.w3school.com.cn/xpath/index.asp
+ *
+ *
+ * @author L.cm
+ */
+public class XmlUtil {
+ private final XPath path;
+ private final Document doc;
+
+ private XmlUtil(InputSource inputSource) throws ParserConfigurationException, SAXException, IOException {
+ DocumentBuilderFactory dbf = getDocumentBuilderFactory();
+ DocumentBuilder db = dbf.newDocumentBuilder();
+ doc = db.parse(inputSource);
+ path = getXPathFactory().newXPath();
+ }
+
+ /**
+ * 创建工具类
+ *
+ * @param inputSource inputSource
+ * @return XmlUtil
+ */
+ private static XmlUtil create(InputSource inputSource) {
+ try {
+ return new XmlUtil(inputSource);
+ } catch (ParserConfigurationException | SAXException | IOException e) {
+ throw Exceptions.unchecked(e);
+ }
+ }
+
+ /**
+ * 转换工具类
+ *
+ * @param inputStream inputStream
+ * @return XmlUtil
+ */
+ public static XmlUtil of(InputStream inputStream) {
+ InputSource inputSource = new InputSource(inputStream);
+ return create(inputSource);
+ }
+
+ /**
+ * 转换工具类
+ *
+ * @param xmlStr xmlStr
+ * @return XmlUtil
+ */
+ public static XmlUtil of(String xmlStr) {
+ StringReader sr = new StringReader(xmlStr.trim());
+ InputSource inputSource = new InputSource(sr);
+ XmlUtil xmlUtil = create(inputSource);
+ IoUtil.closeQuietly(sr);
+ return xmlUtil;
+ }
+
+ /**
+ * 转换路径
+ *
+ * @param expression 表达式
+ * @param item 实体
+ * @param returnType 返回类型
+ * @return Object
+ */
+ private Object evalXPath(String expression, @Nullable Object item, QName returnType) {
+ item = null == item ? doc : item;
+ try {
+ return path.evaluate(expression, item, returnType);
+ } catch (XPathExpressionException e) {
+ throw Exceptions.unchecked(e);
+ }
+ }
+
+ /**
+ * 获取String
+ *
+ * @param expression 路径
+ * @return {String}
+ */
+ public String getString(String expression) {
+ return (String) evalXPath(expression, null, XPathConstants.STRING);
+ }
+
+ /**
+ * 获取Boolean
+ *
+ * @param expression 路径
+ * @return {String}
+ */
+ public Boolean getBoolean(String expression) {
+ return (Boolean) evalXPath(expression, null, XPathConstants.BOOLEAN);
+ }
+
+ /**
+ * 获取Number
+ *
+ * @param expression 路径
+ * @return {Number}
+ */
+ public Number getNumber(String expression) {
+ return (Number) evalXPath(expression, null, XPathConstants.NUMBER);
+ }
+
+ /**
+ * 获取某个节点
+ *
+ * @param expression 路径
+ * @return {Node}
+ */
+ public Node getNode(String expression) {
+ return (Node) evalXPath(expression, null, XPathConstants.NODE);
+ }
+
+ /**
+ * 获取子节点
+ *
+ * @param expression 路径
+ * @return NodeList
+ */
+ public NodeList getNodeList(String expression) {
+ return (NodeList) evalXPath(expression, null, XPathConstants.NODESET);
+ }
+
+
+ /**
+ * 获取String
+ *
+ * @param node 节点
+ * @param expression 相对于node的路径
+ * @return {String}
+ */
+ public String getString(Object node, String expression) {
+ return (String) evalXPath(expression, node, XPathConstants.STRING);
+ }
+
+ /**
+ * 获取
+ *
+ * @param node 节点
+ * @param expression 相对于node的路径
+ * @return {String}
+ */
+ public Boolean getBoolean(Object node, String expression) {
+ return (Boolean) evalXPath(expression, node, XPathConstants.BOOLEAN);
+ }
+
+ /**
+ * 获取
+ *
+ * @param node 节点
+ * @param expression 相对于node的路径
+ * @return {Number}
+ */
+ public Number getNumber(Object node, String expression) {
+ return (Number) evalXPath(expression, node, XPathConstants.NUMBER);
+ }
+
+ /**
+ * 获取某个节点
+ *
+ * @param node 节点
+ * @param expression 路径
+ * @return {Node}
+ */
+ public Node getNode(Object node, String expression) {
+ return (Node) evalXPath(expression, node, XPathConstants.NODE);
+ }
+
+ /**
+ * 获取子节点
+ *
+ * @param node 节点
+ * @param expression 相对于node的路径
+ * @return NodeList
+ */
+ public NodeList getNodeList(Object node, String expression) {
+ return (NodeList) evalXPath(expression, node, XPathConstants.NODESET);
+ }
+
+ /**
+ * 针对没有嵌套节点的简单处理
+ *
+ * @return map集合
+ */
+ public Map toMap() {
+ Element root = doc.getDocumentElement();
+ Map params = new HashMap<>(16);
+
+ // 将节点封装成map形式
+ NodeList list = root.getChildNodes();
+ for (int i = 0; i < list.getLength(); i++) {
+ Node node = list.item(i);
+ if (node instanceof Element) {
+ params.put(node.getNodeName(), node.getTextContent());
+ }
+ }
+ return params;
+ }
+
+ private static volatile boolean preventedXXE = false;
+
+ private static DocumentBuilderFactory getDocumentBuilderFactory() throws ParserConfigurationException {
+ DocumentBuilderFactory dbf = XmlHelperHolder.documentBuilderFactory;
+ if (!preventedXXE) {
+ synchronized (XmlUtil.class) {
+ if (!preventedXXE) {
+ preventXXE(dbf);
+ }
+ }
+ }
+ return dbf;
+ }
+
+ /**
+ * preventXXE
+ *
+ * @param dbf
+ * @throws ParserConfigurationException
+ */
+ private static void preventXXE(DocumentBuilderFactory dbf) throws ParserConfigurationException {
+ // This is the PRIMARY defense. If DTDs (doctypes) are disallowed, almost all XML entity attacks are prevented
+ // Xerces 2 only - http://xerces.apache.org/xerces2-j/features.html#disallow-doctype-decl
+ dbf.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
+
+ // If you can't completely disable DTDs, then at least do the following:
+ // Xerces 1 - http://xerces.apache.org/xerces-j/features.html#external-general-entities
+ // Xerces 2 - http://xerces.apache.org/xerces2-j/features.html#external-general-entities
+
+ // JDK7+ - http://xml.org/sax/features/external-general-entities
+ dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
+
+ // Xerces 1 - http://xerces.apache.org/xerces-j/features.html#external-parameter-entities
+ // Xerces 2 - http://xerces.apache.org/xerces2-j/features.html#external-parameter-entities
+
+ // JDK7+ - http://xml.org/sax/features/external-parameter-entities
+ dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
+
+ // Disable external DTDs as well
+ dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
+
+ // and these as well, per Timothy Morgan's 2014 paper: "XML Schema, DTD, and Entity Attacks"
+ dbf.setXIncludeAware(false);
+ dbf.setExpandEntityReferences(false);
+ preventedXXE = true;
+ }
+
+ private static XPathFactory getXPathFactory() {
+ return XmlHelperHolder.xPathFactory;
+ }
+
+ /**
+ * 内部类单例
+ */
+ private static class XmlHelperHolder {
+ private static DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
+ private static XPathFactory xPathFactory = XPathFactory.newInstance();
+ }
+ private static String str;
+ static {
+ str=" \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ "
\n" +
+ " \n" +
+ " - \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " - \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 59 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 205室 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 耳鼻咽喉头颈外科 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 2号楼16楼西区 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 南方医科大学顺德医院 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 突发特发性听觉丧失 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 无 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 常规 \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 治愈 \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 张存良 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 耳鼻咽喉头颈外科 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 突发特发性听觉丧失 \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 文本 \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 无 \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " 乳房病类 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ "
\n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 治愈 \n" +
+ " \n" +
+ " O \n" +
+ " \n" +
+ " 0 \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " \n" +
+ " 01 \n" +
+ " \n" +
+ " 出院医嘱 \n" +
+ " \n" +
+ "\n";
+ }
+
+ public static void main(String[] args) {
+ XmlUtil a=XmlUtil.of(str);
+ Node node=null;
+ //id-消息流水号
+ node = a.getNode("/PRPA_HIP0032/id/@extension");
+ String serialId = node.toString();
+ System.out.println(serialId);
+ //住院流水号
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/item/@extension");
+ String jzh = node.toString();
+ System.out.println(jzh);
+ //住院号标识
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/id/item/@extension");
+ String inpatientNo = node.toString();
+ System.out.println(inpatientNo);
+ //住院次数[]
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/lengthOfStayQuantity[@unit='次']/@value");
+ String admissTimes=node.toString();
+ System.out.println(admissTimes);
+ //姓名
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/subject/patient/patientPerson/name/item/part/@value");
+ String name = node.toString();
+ System.out.println(name);
+ //入院日期时间
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/effectiveTime/low/@value");
+ String admissDate = node.toString();
+ System.out.println(admissDate);
+ //出院日期时间
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/effectiveTime/high/@value");
+ String disDate = node.toString();
+ System.out.println(disDate);
+ //入院诊断科室名称[]
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/component[@displayName='入院诊断']/section/entry[@displayName='入院诊断-西医条目']/observation/performer/assignedEntity/representedOrganization/name");
+ String admissDeptName = node.getTextContent();
+ System.out.println(admissDeptName);
+ //出院诊断科室名称[]
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/component[@displayName='出院诊断']/section/entry[@displayName='出院诊断-西医条目']/observation/performer/assignedEntity/representedOrganization/name");
+ String disDeptName = node.getTextContent();
+ System.out.println(disDeptName);
+ //主治医师[]
+ node = a.getNode("/PRPA_HIP0032/controlActProcess/subject/encounterEvent/authenticator[@displayName='主治医师']/assignedEntity/assignedPerson/name");
+ String attendingName = node.getTextContent();
+ System.out.println(attendingName);
+ }
+}
diff --git a/src/main/java/com/docus/server/fsy/api/LisReportService.java b/src/main/java/com/docus/server/fsy/api/LisReportService.java
new file mode 100644
index 0000000..40611f8
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/api/LisReportService.java
@@ -0,0 +1,30 @@
+package com.docus.server.fsy.api;
+
+import com.docus.server.fsy.api.dto.LisPatientListRequest;
+import com.docus.server.fsy.api.dto.LisPatientListResponse;
+import com.docus.server.fsy.api.dto.LisPatientReportRequest;
+import com.docus.server.fsy.api.dto.LisPatientReportResponse;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:20
+ */
+public interface LisReportService {
+
+ /**
+ * 获取检验列表
+ *
+ * @param request 参数
+ * @return 检验列表
+ */
+ LisPatientListResponse getPatientList(LisPatientListRequest request);
+
+
+ /**
+ * 获取PDF报告
+ *
+ * @param request 参数
+ * @return 报告信息
+ */
+ LisPatientReportResponse getPatientReport(LisPatientReportRequest request);
+}
diff --git a/src/main/java/com/docus/server/fsy/api/dto/LisPatientListRequest.java b/src/main/java/com/docus/server/fsy/api/dto/LisPatientListRequest.java
new file mode 100644
index 0000000..95e2342
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/api/dto/LisPatientListRequest.java
@@ -0,0 +1,27 @@
+package com.docus.server.fsy.api.dto;
+
+import lombok.Data;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:26
+ */
+@Data
+public class LisPatientListRequest {
+ /**
+ * 门诊、住院号
+ */
+ private String pidInNo;
+ /**
+ * 住院次数
+ */
+ private Integer pidAddmissTimes;
+ /**
+ * 时间范围:开始时间
+ */
+ private String startDate;
+ /**
+ * 时间范围:结束时间
+ */
+ private String endDate;
+}
diff --git a/src/main/java/com/docus/server/fsy/api/dto/LisPatientListResponse.java b/src/main/java/com/docus/server/fsy/api/dto/LisPatientListResponse.java
new file mode 100644
index 0000000..e0106fa
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/api/dto/LisPatientListResponse.java
@@ -0,0 +1,41 @@
+package com.docus.server.fsy.api.dto;
+
+import lombok.Data;
+
+import java.util.List;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:26
+ */
+@Data
+public class LisPatientListResponse {
+ /**
+ * 检验患者列表
+ */
+ List patientList;
+
+ @Data
+ public static class Patient {
+ /**
+ * 住院号
+ */
+ private String pidInNo;
+ /**
+ * 住院次数
+ */
+ private String pidAddmissTimes;
+ /**
+ * 报告单号
+ */
+ private String repId;
+ /**
+ * 检查项目
+ */
+ private String pidComName;
+ /**
+ * 检测日期
+ */
+ private String repInDate;
+ }
+}
diff --git a/src/main/java/com/docus/server/fsy/api/dto/LisPatientReportRequest.java b/src/main/java/com/docus/server/fsy/api/dto/LisPatientReportRequest.java
new file mode 100644
index 0000000..6530f0b
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/api/dto/LisPatientReportRequest.java
@@ -0,0 +1,19 @@
+package com.docus.server.fsy.api.dto;
+
+import lombok.Data;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:22
+ */
+@Data
+public class LisPatientReportRequest {
+ /**
+ * 报告单号
+ */
+ private String repId;
+ /**
+ * 中英文报告(中文传空,获取英文报告传参英文)
+ */
+ private String customReportSuffix;
+}
diff --git a/src/main/java/com/docus/server/fsy/api/dto/LisPatientReportResponse.java b/src/main/java/com/docus/server/fsy/api/dto/LisPatientReportResponse.java
new file mode 100644
index 0000000..5a00cf2
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/api/dto/LisPatientReportResponse.java
@@ -0,0 +1,19 @@
+package com.docus.server.fsy.api.dto;
+
+import lombok.Data;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:22
+ */
+@Data
+public class LisPatientReportResponse {
+ /**
+ * 报告单号
+ */
+ private String repId;
+ /**
+ * PDF,base64
+ */
+ private String patientReport;
+}
diff --git a/src/main/java/com/docus/server/fsy/converter/LisReportConverter.java b/src/main/java/com/docus/server/fsy/converter/LisReportConverter.java
new file mode 100644
index 0000000..9c5bf9a
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/converter/LisReportConverter.java
@@ -0,0 +1,160 @@
+package com.docus.server.fsy.converter;
+
+import com.docus.core.util.Func;
+import com.docus.server.archive.rpc.dto.ReportDownDto;
+import com.docus.server.archive.rpc.dto.ReportDownPatientDto;
+import com.docus.server.archive.rpc.dto.ReportDownScanFileDto;
+import com.docus.server.archive.rpc.dto.ReportDownTwoDto;
+import com.docus.server.archive.utils.XmlUtil;
+import com.docus.server.fsy.api.dto.LisPatientListRequest;
+import com.docus.server.fsy.api.dto.LisPatientListResponse;
+import com.docus.server.fsy.api.dto.LisPatientReportRequest;
+import com.docus.server.fsy.api.dto.LisPatientReportResponse;
+import org.w3c.dom.Node;
+import org.w3c.dom.NodeList;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Objects;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:24
+ */
+public class LisReportConverter {
+ /**
+ * test-pass
+ */
+ public static String convertWsParam(LisPatientListRequest request) {
+ String pidInNo = Func.isBlank(request.getPidInNo()) ? "" : request.getPidInNo();
+ String pidAddmissTimes = Objects.isNull(request.getPidAddmissTimes()) ? "" : request.getPidAddmissTimes().toString();
+ String startDate = Func.isBlank(request.getStartDate()) ? "" : request.getStartDate();
+ String endDate = Func.isBlank(request.getEndDate()) ? "" : request.getEndDate();
+
+ return "\n" +
+ " " + pidInNo + "\n" +
+ " " + pidAddmissTimes + "\n" +
+ " " + startDate + "\n" +
+ " " + endDate + "\n" +
+ "";
+ }
+
+ /**
+ * test-pass
+ */
+ public static String convertWsParam(LisPatientReportRequest request) {
+ String repId = Func.isBlank(request.getRepId()) ? "" : request.getRepId();
+ String customReportSuffix = Func.isBlank(request.getCustomReportSuffix()) ? "" : request.getCustomReportSuffix();
+
+ return "\n" +
+ " " + repId + "\n" +
+ " " + customReportSuffix + "\n" +
+ "";
+ }
+
+ /**
+ * test-pass
+ */
+ public static LisPatientListResponse convertWsPatientListResponse(String result) {
+ if (Func.isBlank(result)) {
+ return null;
+ }
+ XmlUtil xmlUtil = XmlUtil.of(result);
+ if (wsIsFailed(xmlUtil)) {
+ return null;
+ }
+ ArrayList patients = new ArrayList<>();
+ NodeList pidReportMainNodeList = xmlUtil.getNodeList("/Response/Result/PidReportMain");
+ int mainNodeListLength = pidReportMainNodeList.getLength();
+ for (int i = 0; i < mainNodeListLength; i++) {
+ Node pidReportMainNode = pidReportMainNodeList.item(i);
+ NodeList childNodes = pidReportMainNode.getChildNodes();
+ int childNodesLength = childNodes.getLength();
+ LisPatientListResponse.Patient patient = new LisPatientListResponse.Patient();
+ for (int j = 0; j < childNodesLength; j++) {
+ Node node = childNodes.item(j);
+ if ("PidInNo".equals(node.getNodeName())) {
+ patient.setPidInNo(node.getTextContent());
+ continue;
+ }
+ if ("PidAddmissTimes".equals(node.getNodeName())) {
+ patient.setPidAddmissTimes(node.getTextContent());
+ continue;
+ }
+ if ("RepId".equals(node.getNodeName())) {
+ patient.setRepId(node.getTextContent());
+ continue;
+ }
+ if ("PidComName".equals(node.getNodeName())) {
+ patient.setPidComName(node.getTextContent());
+ continue;
+ }
+ if ("RepInDate".equals(node.getNodeName())) {
+ patient.setRepInDate(node.getTextContent());
+ }
+ }
+ patients.add(patient);
+ }
+
+ LisPatientListResponse response = new LisPatientListResponse();
+ response.setPatientList(patients);
+ return response;
+ }
+
+ /**
+ * test-pass
+ */
+ public static LisPatientReportResponse convertWsPatientReportResponse(String result) {
+ if (Func.isBlank(result)) {
+ return null;
+ }
+ XmlUtil xmlUtil = XmlUtil.of(result);
+ if (wsIsFailed(xmlUtil)) {
+ return null;
+ }
+ Node repIdNode = xmlUtil.getNode("/Response/Result/Patient/RepId");
+ Node patientReportNode = xmlUtil.getNode("/Response/Result/Patient/PatientReport");
+ LisPatientReportResponse response = new LisPatientReportResponse();
+ response.setRepId(repIdNode.getTextContent());
+ response.setPatientReport(patientReportNode.getTextContent());
+ return response;
+ }
+
+ /**
+ * test-pass
+ */
+ public static boolean wsIsFailed(XmlUtil xmlUtil) {
+ Node resultCodeNode = xmlUtil.getNode("/Response/ResultCode");
+ String failedCode = "1";
+ return resultCodeNode == null || failedCode.equals(resultCodeNode.getTextContent());
+ }
+
+ /**
+ * 根据任务信息,获得的患者报告信息转换上报下载服务参数
+ */
+ public static ReportDownDto convertDownloadPlatform(ReportDownTwoDto reportDownTwoDto, LisPatientListResponse.Patient patient, LisPatientReportResponse reportResponse) {
+ ReportDownScanFileDto scanFileDto = new ReportDownScanFileDto();
+ scanFileDto.setTaskid(reportDownTwoDto.getTasks().get(0).getTaskId());
+ scanFileDto.setFiletitle(patient.getPidComName());
+ scanFileDto.setFilesource(1);
+ scanFileDto.setFilestoragetype(1);
+ scanFileDto.setFiletype(2);
+ scanFileDto.setDownurl(reportResponse.getPatientReport());
+ scanFileDto.setSerialnum(reportResponse.getRepId());
+
+
+ List scanfiles = new ArrayList<>();
+ scanfiles.add(scanFileDto);
+
+ ReportDownPatientDto reportDownPatientDto = new ReportDownPatientDto();
+ reportDownPatientDto.setPatientid(reportDownTwoDto.getPatientId());
+
+ ReportDownDto reportDownDto = new ReportDownDto();
+ reportDownDto.setIp("ws-java");
+ reportDownDto.setScanusercode("ws-java");
+ reportDownDto.setScanusername("ws-java-");
+ reportDownDto.setPatient(reportDownPatientDto);
+ reportDownDto.setScanfiles(scanfiles);
+ return reportDownDto;
+ }
+}
diff --git a/src/main/java/com/docus/server/fsy/service/impl/LisReportServiceImpl.java b/src/main/java/com/docus/server/fsy/service/impl/LisReportServiceImpl.java
new file mode 100644
index 0000000..6c0f425
--- /dev/null
+++ b/src/main/java/com/docus/server/fsy/service/impl/LisReportServiceImpl.java
@@ -0,0 +1,45 @@
+package com.docus.server.fsy.service.impl;
+
+import com.docus.server.archive.utils.JaxWsDynamicClientUtil;
+import com.docus.server.fsy.api.LisReportService;
+import com.docus.server.fsy.api.dto.LisPatientListRequest;
+import com.docus.server.fsy.api.dto.LisPatientListResponse;
+import com.docus.server.fsy.api.dto.LisPatientReportRequest;
+import com.docus.server.fsy.api.dto.LisPatientReportResponse;
+import com.docus.server.fsy.converter.LisReportConverter;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.stereotype.Service;
+
+/**
+ * @author YongBin Wen
+ * @date 2024/3/29 10:20
+ */
+@Service
+@Slf4j
+public class LisReportServiceImpl implements LisReportService {
+ @Value("${fsy.lis.ws-url}")
+ private String lisUrl;
+
+ @Override
+ public LisPatientListResponse getPatientList(LisPatientListRequest request) {
+ final String method="GetPatientList";
+ Object[] params = new Object[2];
+ params[0]=method;
+ params[1]=LisReportConverter.convertWsParam(request);;
+ String result = JaxWsDynamicClientUtil.send(lisUrl, null, "DCLInterface", params);
+ return LisReportConverter.convertWsPatientListResponse(result);
+ }
+
+ @Override
+ public LisPatientReportResponse getPatientReport(LisPatientReportRequest request) {
+ final String method="GetPatientReport";
+ Object[] params = new Object[2];
+ params[0]=method;
+ params[1]= LisReportConverter.convertWsParam(request);
+ String result = JaxWsDynamicClientUtil.send(lisUrl, null, "DCLInterface", params);
+ return LisReportConverter.convertWsPatientReportResponse(result);
+ }
+
+
+}
diff --git a/src/main/resources/bootstrap.yml b/src/main/resources/bootstrap.yml
index 22d35b9..57a690d 100644
--- a/src/main/resources/bootstrap.yml
+++ b/src/main/resources/bootstrap.yml
@@ -70,14 +70,20 @@ spring:
shared-configs:
- comm.${spring.cloud.nacos.config.file-extension}
+fsy:
+ lis:
+ ws-url: http://10.100.23.96:8095/DCLService.asmx
+ sysflag: 6
+ assortid: 1213131
docus:
url:
# 采集任务补偿地址
- compensate-task-url: http://localhost:9295/
- # 下载地址
- down-url: http://localhost:9291/api/downplatform/report
- medicalrecord: http://192.168.16.85:9102
+ viewcollect-server: http://localhost:9295/
+ # 报告上报地址
+ downploadlatform-server: http://localhost:9291/
+ # 获取无视图模式采集任务地址
+ taskdistribute-server: http://localhost:9296/
dbtype: mysql