From c5d6bc298b470fcf934a7308d14ddf7dbccb8270 Mon Sep 17 00:00:00 2001 From: huzhengkao <562572218@qq.com> Date: Fri, 6 Jun 2025 15:22:24 +0800 Subject: [PATCH] =?UTF-8?q?=E6=96=B0=E5=A2=9E=E5=92=8C=E5=AE=8C=E5=96=84?= =?UTF-8?q?=E4=B8=9A=E5=8A=A1=E6=95=B0=E6=8D=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../d2d/provtest/ProvTestClient.java | 2 +- .../d2d/provtest/config/CertConfig.java | 18 ++ .../controller/ProvTestServerController.java | 94 +---------- .../provtest/domain/AbroadPharmaBaseInfo.java | 139 ++++++++++++++++ ...armaceuticalProductionLicenseBaseInfo.java | 156 ++++++++++++++++++ .../d2d/provtest/entity/BaseEntity.java | 2 +- .../d2d/provtest/generator/CodeGenerator.java | 6 +- .../mapper/AbroadPharmaBaseInfoMapper.java | 16 ++ ...uticalProductionLicenseBaseInfoMapper.java | 16 ++ .../service/IAbroadPharmaBaseInfoService.java | 16 ++ ...ticalProductionLicenseBaseInfoService.java | 16 ++ .../provtest/service/XmlParserService.java | 13 +- .../handle/business/SubType1011Handler.java | 7 +- .../handle/business/SubType1012Handler.java | 74 +++++++++ .../handle/business/SubType1013Handler.java | 73 ++++++++ .../impl/AbroadPharmaBaseInfoServiceImpl.java | 20 +++ ...lProductionLicenseBaseInfoServiceImpl.java | 20 +++ .../d2d/provtest/utils/CertManager.java | 125 ++++++++++++++ .../d2d/provtest/utils/KeyStoreUtil.java | 10 +- .../provtest/utils/LocalDateDeserializer.java | 23 +++ src/main/resources/application.yml | 10 +- .../mapper/AbroadPharmaBaseInfoMapper.xml | 5 + ...euticalProductionLicenseBaseInfoMapper.xml | 5 + target/classes/application.yml | 7 +- .../d2d/provtest/ProvTestClient.class | Bin 7248 -> 7248 bytes .../controller/ProvTestServerController.class | Bin 8262 -> 5750 bytes .../d2d/provtest/entity/BaseEntity.class | Bin 4402 -> 4415 bytes .../provtest/service/XmlParserService.class | Bin 8454 -> 9039 bytes .../d2d/provtest/utils/KeyStoreUtil.class | Bin 11106 -> 11106 bytes 29 files changed, 764 insertions(+), 109 deletions(-) create mode 100644 src/main/java/com/alihealth/d2d/provtest/config/CertConfig.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/domain/AbroadPharmaBaseInfo.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/domain/PharmaceuticalProductionLicenseBaseInfo.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/mapper/AbroadPharmaBaseInfoMapper.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/service/IAbroadPharmaBaseInfoService.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/service/IPharmaceuticalProductionLicenseBaseInfoService.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1012Handler.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1013Handler.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/service/impl/AbroadPharmaBaseInfoServiceImpl.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/service/impl/PharmaceuticalProductionLicenseBaseInfoServiceImpl.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/utils/CertManager.java create mode 100644 src/main/java/com/alihealth/d2d/provtest/utils/LocalDateDeserializer.java create mode 100644 src/main/resources/mapper/AbroadPharmaBaseInfoMapper.xml create mode 100644 src/main/resources/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.xml diff --git a/src/main/java/com/alihealth/d2d/provtest/ProvTestClient.java b/src/main/java/com/alihealth/d2d/provtest/ProvTestClient.java index 49cbf1a..5ab860d 100644 --- a/src/main/java/com/alihealth/d2d/provtest/ProvTestClient.java +++ b/src/main/java/com/alihealth/d2d/provtest/ProvTestClient.java @@ -60,7 +60,7 @@ public class ProvTestClient { public static void main(String[] args) throws Exception { //数据文件内容主业务类型 10:基础信息数据 20:应用信息数据 //subType数据文件内容子业务类型 详见:数据类型字典表 基本信息(1011-1019、9001-9002) 应用信息(2011-2020、2051-2053) - testProv("1011"); + testProv("1013"); } diff --git a/src/main/java/com/alihealth/d2d/provtest/config/CertConfig.java b/src/main/java/com/alihealth/d2d/provtest/config/CertConfig.java new file mode 100644 index 0000000..c5027b7 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/config/CertConfig.java @@ -0,0 +1,18 @@ +package com.alihealth.d2d.provtest.config; + +import lombok.Data; +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.stereotype.Component; + +/** + * @author Jason 证书配置 + * @date 2025年06月06日 14:09:26 + */ +@Component +@ConfigurationProperties(prefix = "cert") +@Data +public class CertConfig { + private String path; + private String password; + private String algorithm; +} diff --git a/src/main/java/com/alihealth/d2d/provtest/controller/ProvTestServerController.java b/src/main/java/com/alihealth/d2d/provtest/controller/ProvTestServerController.java index e5adde7..e7579b4 100644 --- a/src/main/java/com/alihealth/d2d/provtest/controller/ProvTestServerController.java +++ b/src/main/java/com/alihealth/d2d/provtest/controller/ProvTestServerController.java @@ -2,6 +2,7 @@ package com.alihealth.d2d.provtest.controller; import cn.hutool.core.date.DateUtil; import com.alibaba.fastjson.JSON; +import com.alihealth.d2d.provtest.config.CertConfig; import com.alihealth.d2d.provtest.domain.DomesticDrugProductionApplyInfo; import com.alihealth.d2d.provtest.domain.DomesticPharmaBaseInfo; import com.alihealth.d2d.provtest.domain.ReceiveDataLog; @@ -46,18 +47,9 @@ import java.util.Map; public class ProvTestServerController { Logger logger = LoggerFactory.getLogger(getClass()); - /** - * 证书地址 - */ - private static final String PFX_FILE_PATH = "D:\\ynyp\\药品追溯\\d2d\\yunnan.pfx"; - /** - * 证书密码 - */ - private static final String PFX_PASSWORD = "12345678"; - /** - * 加密算法 - */ - private static final String algorithm = "RSA"; + + @Autowired + private CertManager certManager; @Autowired @@ -104,12 +96,12 @@ public class ProvTestServerController { EventPojo eventPojo = JSON.parseObject(event, EventPojo.class); //获取私钥 - String privateKey = getPrivateKey(); + String privateKey = certManager.getPrivateKey(); logger.info("privateKey:{}",privateKey); - String de = testDecrypt(privateKey,eventPojo.getData()); + String de = certManager.testDecrypt(privateKey,eventPojo.getData()); String xml = StreamUtil.getUnStreamContent(de); logger.info("解密之后的文件内容:{}", xml); @@ -125,18 +117,6 @@ public class ProvTestServerController { log.setVer(ver); receiveDataLogService.save(log); - //解析xml - // List list= XmlStringParser.parseVaccineManufacturers(xml,eventPojo.getSubType()); - - //解析并保存数据 -// XmlStringParser.parseXml(xml, "1011", data -> { -// domesticPharmaBaseInfoService.save((DomesticPharmaBaseInfo) data); -// }); - -// List producers = xmlParserService.parseXml1( -// xml, -// DomesticPharmaBaseInfo.class -// ); //解析并处理数据 processingService.processEvent(eventPojo, xml,eventId); @@ -149,67 +129,5 @@ public class ProvTestServerController { } - /** - * 私钥解密 - * @param key - * @param data - * @return - * @throws NoSuchAlgorithmException - * @throws InvalidKeyException - * @throws NoSuchPaddingException - * @throws InvalidKeySpecException - * @throws BadPaddingException - * @throws IllegalBlockSizeException - * @throws IOException - */ - public static String testDecrypt(String key,String data) throws NoSuchAlgorithmException, InvalidKeyException, NoSuchPaddingException, InvalidKeySpecException, IllegalBlockSizeException, BadPaddingException, IOException{ - byte[] decode = java.util.Base64.getDecoder().decode(key); - RSAPrivateKey priKey = (RSAPrivateKey) KeyFactory.getInstance(algorithm).generatePrivate(new PKCS8EncodedKeySpec(decode)); - //RSA解密 - Cipher ci = Cipher.getInstance(algorithm); - ci.init(Cipher.DECRYPT_MODE, priKey); - - byte[] bytes = java.util.Base64.getDecoder().decode(data); - int inputLen = bytes.length; - int offLen = 0; - int i = 0; - ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); - while(inputLen - offLen > 0){ - byte[] cache; - if(inputLen - offLen > 128){ - cache = ci.doFinal(bytes,offLen,128); - }else{ - cache = ci.doFinal(bytes,offLen,inputLen - offLen); - } - byteArrayOutputStream.write(cache); - i++; - offLen = 128 * i; - - } - byteArrayOutputStream.close(); - byte[] byteArray = byteArrayOutputStream.toByteArray(); - return new String(byteArray); - } - - /** - * 获取私钥 - * @return - * @throws Exception - */ - private static String getPrivateKey() throws Exception { - KeyStore keyStore = KeyStoreUtil.loadKetStore(PFX_FILE_PATH,PFX_PASSWORD); - return Base64.encode(KeyStoreUtil.getPrivateKey(keyStore, PFX_PASSWORD).getEncoded()); - } - - /** - * 获取公钥 - * @return - * @throws Exception - */ - private static String getPublicKey() throws Exception { - KeyStore keyStore = KeyStoreUtil.loadKetStore(PFX_FILE_PATH,PFX_PASSWORD); - PublicKey publicKey = KeyStoreUtil.getPublicKey(keyStore); - return Base64.encode(publicKey.getEncoded()); - } } diff --git a/src/main/java/com/alihealth/d2d/provtest/domain/AbroadPharmaBaseInfo.java b/src/main/java/com/alihealth/d2d/provtest/domain/AbroadPharmaBaseInfo.java new file mode 100644 index 0000000..c3fa22d --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/domain/AbroadPharmaBaseInfo.java @@ -0,0 +1,139 @@ +package com.alihealth.d2d.provtest.domain; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import lombok.Data; +import lombok.Getter; +import lombok.Setter; + +import java.io.Serializable; +import java.time.LocalDateTime; + +/** + *

+ * 境外药品生产企业基本信息数据子集 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +@Data +@TableName("abroad_pharma_base_info") +public class AbroadPharmaBaseInfo implements Serializable { + + private static final long serialVersionUID = 1L; + + /** + * 主键ID + */ + @TableId(value = "id", type = IdType.AUTO) + private Long id; + + /** + * 事件流水号 + */ + private String eventId; + + /** + * 境外药品生产企业代码 + */ + @JacksonXmlProperty(localName = "JWYPSCQYDM") + private String jwypscqydm; + + /** + * 境外药品生产企业名称(中文) + */ + @JacksonXmlProperty(localName = "JWYPSCQYMCZW") + private String jwypscqymczw; + + /** + * 境外药品生产企业名称(英文) + */ + @JacksonXmlProperty(localName = "JWYPSCQYMCYW") + private String jwypscqymcyw; + + /** + * 境外药品生产企业地址(中文) + */ + @JacksonXmlProperty(localName = "JWYPSCQYDZZW") + private String jwypscqydzzw; + + /** + * 境外药品生产企业地址(英文) + */ + @JacksonXmlProperty(localName = "JWYPSCQYDZYW") + private String jwypscqydzyw; + + /** + * 境外药品生产企业国家(或地区) + */ + @JacksonXmlProperty(localName = "JWYPSCQYGJHDQ") + private String jwypscqygjhdq; + + /** + * 境外药品生产企业国家或地区(中文) + */ + @JacksonXmlProperty(localName = "JWYPSCQYGJHDQZW") + private String jwypscqygjhdqzw; + + /** + * 境外药品生产企业国家或地区(英文) + */ + @JacksonXmlProperty(localName = "JWYPSCQYGJHDQYW") + private String jwypscqygjhdqyw; + + /** + * 固定电话号码 + */ + @JacksonXmlProperty(localName = "GDDHHM") + private String gddhhm; + + /** + * 传真号码 + */ + @JacksonXmlProperty(localName = "CZHM") + private String czhm; + + /** + * 电子信箱 + */ + @JacksonXmlProperty(localName = "DZXX") + private String dzxx; + + /** + * 企业网址 + */ + @JacksonXmlProperty(localName = "QYWZ") + private String qywz; + + /** + * 联系人 + */ + @JacksonXmlProperty(localName = "LXR") + private String lxr; + + /** + * 联系电话 + */ + @JacksonXmlProperty(localName = "LXDH") + private String lxdh; + + /** + * 创建时间 + */ + private LocalDateTime createTime; + + /** + * 更新时间 + */ + private LocalDateTime updateTime; + + /** + * 是否删除(0-否 1-是) + */ + private Integer isDeleted; + + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/domain/PharmaceuticalProductionLicenseBaseInfo.java b/src/main/java/com/alihealth/d2d/provtest/domain/PharmaceuticalProductionLicenseBaseInfo.java new file mode 100644 index 0000000..82fc9b8 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/domain/PharmaceuticalProductionLicenseBaseInfo.java @@ -0,0 +1,156 @@ +package com.alihealth.d2d.provtest.domain; + +import com.alihealth.d2d.provtest.utils.LocalDateDeserializer; +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import com.fasterxml.jackson.databind.annotation.JsonDeserialize; +import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import lombok.Getter; +import lombok.Setter; + +import java.io.Serializable; +import java.time.LocalDate; +import java.time.LocalDateTime; + +/** + *

+ * 药品生产许可证基本信息数据子集 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +@Getter +@Setter +@TableName("pharmaceutical_production_license_base_info") +public class PharmaceuticalProductionLicenseBaseInfo implements Serializable { + + private static final long serialVersionUID = 1L; + + /** + * 主键ID + */ + @TableId(value = "id", type = IdType.AUTO) + private Long id; + + /** + * 事件流水号 + */ + private String eventId; + + /** + * 生产许可证编号 + */ + @JacksonXmlProperty(localName = "SCXKZBH") + private String scxkzbh; + + /** + * 境内药品生产企业名称 + */ + @JacksonXmlProperty(localName = "JNYPSCQYMC") + private String jnypscqymc; + + /** + * 统一社会信用代码 + */ + @JacksonXmlProperty(localName = "TYSHXYDM") + private String tyshxydm; + + /** + * 注册地址 + */ + @JacksonXmlProperty(localName = "ZCDZ") + private String zcdz; + + /** + * 法定代表人 + */ + @JacksonXmlProperty(localName = "FDDBR") + private String fddbr; + + /** + * 企业负责人 + */ + @JacksonXmlProperty(localName = "QYFZR") + private String qyfzr; + + /** + * 质量负责人 + */ + @JacksonXmlProperty(localName = "ZLFZR") + private String zlfzr; + + /** + * 分类码 + */ + @JacksonXmlProperty(localName = "FLM") + private String flm; + + /** + * 有效期 + */ + @JacksonXmlProperty(localName = "YXQ") + @JsonDeserialize(using = LocalDateDeserializer.class) + private LocalDate yxq; + + /** + * 生产地址 + */ + @JacksonXmlProperty(localName = "SCDZ") + private String scdz; + + /** + * 生产范围 + */ + @JacksonXmlProperty(localName = "SCFW") + private String scfw; + + /** + * 发证机关 + */ + @JacksonXmlProperty(localName = "FZJG") + private String fzjg; + + /** + * 签发人 + */ + @JacksonXmlProperty(localName = "QFR") + private String qfr; + + /** + * 签发日期 + */ + @JacksonXmlProperty(localName = "QFRQ") + @JsonDeserialize(using = LocalDateDeserializer.class) + private LocalDate qfrq; + + /** + * 日常监督管理机构 + */ + @JacksonXmlProperty(localName = "RCJDGLJG") + private String rcjdgljg; + + /** + * 投诉举报电话 + */ + @JacksonXmlProperty(localName = "SCJBDH") + private String scjbdh; + + /** + * 创建时间 + */ + private LocalDateTime createTime; + + /** + * 更新时间 + */ + private LocalDateTime updateTime; + + /** + * 是否删除(0-否 1-是) + */ + private Integer isDeleted; + + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/entity/BaseEntity.java b/src/main/java/com/alihealth/d2d/provtest/entity/BaseEntity.java index 580236e..552ed59 100644 --- a/src/main/java/com/alihealth/d2d/provtest/entity/BaseEntity.java +++ b/src/main/java/com/alihealth/d2d/provtest/entity/BaseEntity.java @@ -17,7 +17,7 @@ import java.time.LocalDateTime; //@MappedSuperclass @Data public abstract class BaseEntity> implements XmlEntity{ - @TableId(type = IdType.AUTO) // 明确指定使用数据库自增 + @TableId(value = "id", type = IdType.AUTO) // 明确指定使用数据库自增 private Long id; @Column(name = "event_id") diff --git a/src/main/java/com/alihealth/d2d/provtest/generator/CodeGenerator.java b/src/main/java/com/alihealth/d2d/provtest/generator/CodeGenerator.java index f709987..658cba7 100644 --- a/src/main/java/com/alihealth/d2d/provtest/generator/CodeGenerator.java +++ b/src/main/java/com/alihealth/d2d/provtest/generator/CodeGenerator.java @@ -16,6 +16,7 @@ import java.nio.file.Paths; public class CodeGenerator { public static void main(String[] args) { + String tables="pharmaceutical_production_license_base_info";// 生成多个指定表,逗号分隔 FastAutoGenerator.create("jdbc:mysql://47.109.202.121:3306/supervisionx_trace_data", "root", "TCCT3.1415926") .globalConfig(builder -> builder .author("Jason") @@ -23,7 +24,7 @@ public class CodeGenerator { .commentDate("yyyy-MM-dd") ) .packageConfig(builder -> builder - .parent("com.alihealth.d2d.provtest.generator") + .parent("com.alihealth.d2d.provtest.generator.temp") .entity("domain") .mapper("mapper") .service("service") @@ -31,11 +32,12 @@ public class CodeGenerator { .xml("mapper.xml") ) .strategyConfig(builder -> builder + .addInclude(tables) .entityBuilder() .enableLombok() ) .templateEngine(new FreemarkerTemplateEngine()) .execute(); - + System.out.println("数据表"+tables+"--------生成实体成功!!"); } } diff --git a/src/main/java/com/alihealth/d2d/provtest/mapper/AbroadPharmaBaseInfoMapper.java b/src/main/java/com/alihealth/d2d/provtest/mapper/AbroadPharmaBaseInfoMapper.java new file mode 100644 index 0000000..8478391 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/mapper/AbroadPharmaBaseInfoMapper.java @@ -0,0 +1,16 @@ +package com.alihealth.d2d.provtest.mapper; + +import com.alihealth.d2d.provtest.domain.AbroadPharmaBaseInfo; +import com.baomidou.mybatisplus.core.mapper.BaseMapper; + +/** + *

+ * 境外药品生产企业基本信息数据子集 Mapper 接口 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +public interface AbroadPharmaBaseInfoMapper extends BaseMapper { + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.java b/src/main/java/com/alihealth/d2d/provtest/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.java new file mode 100644 index 0000000..cda7e78 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.java @@ -0,0 +1,16 @@ +package com.alihealth.d2d.provtest.mapper; + +import com.alihealth.d2d.provtest.domain.PharmaceuticalProductionLicenseBaseInfo; +import com.baomidou.mybatisplus.core.mapper.BaseMapper; + +/** + *

+ * 药品生产许可证基本信息数据子集 Mapper 接口 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +public interface PharmaceuticalProductionLicenseBaseInfoMapper extends BaseMapper { + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/service/IAbroadPharmaBaseInfoService.java b/src/main/java/com/alihealth/d2d/provtest/service/IAbroadPharmaBaseInfoService.java new file mode 100644 index 0000000..2a05142 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/service/IAbroadPharmaBaseInfoService.java @@ -0,0 +1,16 @@ +package com.alihealth.d2d.provtest.service; + +import com.alihealth.d2d.provtest.domain.AbroadPharmaBaseInfo; +import com.baomidou.mybatisplus.extension.service.IService; + +/** + *

+ * 境外药品生产企业基本信息数据子集 服务类 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +public interface IAbroadPharmaBaseInfoService extends IService { + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/service/IPharmaceuticalProductionLicenseBaseInfoService.java b/src/main/java/com/alihealth/d2d/provtest/service/IPharmaceuticalProductionLicenseBaseInfoService.java new file mode 100644 index 0000000..6a893c7 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/service/IPharmaceuticalProductionLicenseBaseInfoService.java @@ -0,0 +1,16 @@ +package com.alihealth.d2d.provtest.service; + +import com.alihealth.d2d.provtest.domain.PharmaceuticalProductionLicenseBaseInfo; +import com.baomidou.mybatisplus.extension.service.IService; + +/** + *

+ * 药品生产许可证基本信息数据子集 服务类 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +public interface IPharmaceuticalProductionLicenseBaseInfoService extends IService { + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/service/XmlParserService.java b/src/main/java/com/alihealth/d2d/provtest/service/XmlParserService.java index 5360b8e..16c0a29 100644 --- a/src/main/java/com/alihealth/d2d/provtest/service/XmlParserService.java +++ b/src/main/java/com/alihealth/d2d/provtest/service/XmlParserService.java @@ -3,8 +3,11 @@ package com.alihealth.d2d.provtest.service; import com.alihealth.d2d.provtest.domain.DomesticPharmaBaseInfo; import com.alihealth.d2d.provtest.entity.VTTSBasic; import com.alihealth.d2d.provtest.entity.VTTSEventS; +import com.fasterxml.jackson.core.JsonProcessingException; import com.fasterxml.jackson.databind.JavaType; import com.fasterxml.jackson.dataformat.xml.XmlMapper; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import org.springframework.stereotype.Service; import javax.xml.bind.*; @@ -24,6 +27,7 @@ import java.util.stream.Collectors; */ @Service public class XmlParserService { + protected final Logger log = LoggerFactory.getLogger(getClass()); private static final Map, JAXBContext> CONTEXT_CACHE = new ConcurrentHashMap<>(); @@ -38,12 +42,17 @@ public class XmlParserService { * @param * @throws IOException */ - public VTTSBasic parseDataXml(String xml, Class dataType) throws IOException { + public VTTSBasic parseDataXml(String xml, Class dataType) { JavaType type = xmlMapper.getTypeFactory().constructParametricType( VTTSBasic.class, dataType ); - return xmlMapper.readValue(xml, type); + try { + return xmlMapper.readValue(xml, type); + } catch (JsonProcessingException e) { + log.error("数据解析错误:"+e.getMessage()); + throw new RuntimeException(e); + } } /** diff --git a/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1011Handler.java b/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1011Handler.java index cb92189..b5513e9 100644 --- a/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1011Handler.java +++ b/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1011Handler.java @@ -52,15 +52,10 @@ public class SubType1011Handler extends AbstractEventDataHandler result = null; - try { - result = xmlParserService.parseDataXml( + VTTSBasic result = xmlParserService.parseDataXml( xml, DomesticPharmaBaseInfo.class ); - } catch (IOException e) { - throw new RuntimeException(e); - } List list = result.getDataset(); if(list!=null && !list.isEmpty()){ list.stream() diff --git a/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1012Handler.java b/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1012Handler.java new file mode 100644 index 0000000..e261cb8 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1012Handler.java @@ -0,0 +1,74 @@ +package com.alihealth.d2d.provtest.service.handle.business; + +import com.alihealth.d2d.provtest.domain.AbroadPharmaBaseInfo; +import com.alihealth.d2d.provtest.domain.DomesticPharmaBaseInfo; +import com.alihealth.d2d.provtest.entity.EventBody; +import com.alihealth.d2d.provtest.entity.InstanceDetail; +import com.alihealth.d2d.provtest.entity.ItemDetail; +import com.alihealth.d2d.provtest.entity.VTTSBasic; +import com.alihealth.d2d.provtest.service.IAbroadPharmaBaseInfoService; +import com.alihealth.d2d.provtest.service.IDomesticPharmaBaseInfoService; +import com.alihealth.d2d.provtest.service.XmlParserService; +import com.alihealth.d2d.provtest.service.handle.AbstractEventDataHandler; +import com.alihealth.d2d.provtest.service.handle.EventSubType; +import com.baomidou.mybatisplus.extension.service.IService; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import java.io.IOException; +import java.util.List; + +/** + * @author Jason 境外药品生产企业基本信息数据子集 + * @date 2025年06月05日 11:14:43 + */ +@Service +@EventSubType("1012") +public class SubType1012Handler extends AbstractEventDataHandler { + protected final Logger log = LoggerFactory.getLogger(getClass()); + + @Autowired + private IAbroadPharmaBaseInfoService service; + + @Autowired + private XmlParserService xmlParserService; + + @Override + protected Class getEntityClass() { + return AbroadPharmaBaseInfo.class; + } + + @Override + protected IService getService() { + return service; + } + + @Override + protected AbroadPharmaBaseInfo convertToEntity(EventBody eventBody, ItemDetail item, InstanceDetail instance) { + return null; + } + + @Override + public String getSubType() { + return "1012"; + } + + @Override + public void handleBase(String xml,String eventId) { + VTTSBasic result = xmlParserService.parseDataXml( + xml, + AbroadPharmaBaseInfo.class + ); + List list = result.getDataset(); + if(list!=null && !list.isEmpty()){ + list.stream() + .forEach(item -> { + item.setEventId(eventId); + }); + getService().saveBatch(list); + log.info("数据类型:"+getSubType()+",入库的数据条数:{}", list.size()); + } + } +} diff --git a/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1013Handler.java b/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1013Handler.java new file mode 100644 index 0000000..0e01be1 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/service/handle/business/SubType1013Handler.java @@ -0,0 +1,73 @@ +package com.alihealth.d2d.provtest.service.handle.business; + +import com.alihealth.d2d.provtest.domain.AbroadPharmaBaseInfo; +import com.alihealth.d2d.provtest.domain.PharmaceuticalProductionLicenseBaseInfo; +import com.alihealth.d2d.provtest.entity.EventBody; +import com.alihealth.d2d.provtest.entity.InstanceDetail; +import com.alihealth.d2d.provtest.entity.ItemDetail; +import com.alihealth.d2d.provtest.entity.VTTSBasic; +import com.alihealth.d2d.provtest.service.IAbroadPharmaBaseInfoService; +import com.alihealth.d2d.provtest.service.IPharmaceuticalProductionLicenseBaseInfoService; +import com.alihealth.d2d.provtest.service.XmlParserService; +import com.alihealth.d2d.provtest.service.handle.AbstractEventDataHandler; +import com.alihealth.d2d.provtest.service.handle.EventSubType; +import com.baomidou.mybatisplus.extension.service.IService; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import java.util.List; + +/** + * @author Jason 药品生产许可证基本信息数据子集 + * @date 2025年06月05日 11:14:43 + */ +@Service +@EventSubType("1013") +public class SubType1013Handler extends AbstractEventDataHandler { + protected final Logger log = LoggerFactory.getLogger(getClass()); + + @Autowired + private IPharmaceuticalProductionLicenseBaseInfoService service; + + @Autowired + private XmlParserService xmlParserService; + + @Override + protected Class getEntityClass() { + return PharmaceuticalProductionLicenseBaseInfo.class; + } + + @Override + protected IService getService() { + return service; + } + + @Override + protected PharmaceuticalProductionLicenseBaseInfo convertToEntity(EventBody eventBody, ItemDetail item, InstanceDetail instance) { + return null; + } + + @Override + public String getSubType() { + return "1013"; + } + + @Override + public void handleBase(String xml,String eventId) { + VTTSBasic result = xmlParserService.parseDataXml( + xml, + PharmaceuticalProductionLicenseBaseInfo.class + ); + List list = result.getDataset(); + if(list!=null && !list.isEmpty()){ + list.stream() + .forEach(item -> { + item.setEventId(eventId); + }); + getService().saveBatch(list); + log.info("数据类型:"+getSubType()+",入库的数据条数:{}", list.size()); + } + } +} diff --git a/src/main/java/com/alihealth/d2d/provtest/service/impl/AbroadPharmaBaseInfoServiceImpl.java b/src/main/java/com/alihealth/d2d/provtest/service/impl/AbroadPharmaBaseInfoServiceImpl.java new file mode 100644 index 0000000..e65591b --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/service/impl/AbroadPharmaBaseInfoServiceImpl.java @@ -0,0 +1,20 @@ +package com.alihealth.d2d.provtest.service.impl; + +import com.alihealth.d2d.provtest.domain.AbroadPharmaBaseInfo; +import com.alihealth.d2d.provtest.mapper.AbroadPharmaBaseInfoMapper; +import com.alihealth.d2d.provtest.service.IAbroadPharmaBaseInfoService; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import org.springframework.stereotype.Service; + +/** + *

+ * 境外药品生产企业基本信息数据子集 服务实现类 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +@Service +public class AbroadPharmaBaseInfoServiceImpl extends ServiceImpl implements IAbroadPharmaBaseInfoService { + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/service/impl/PharmaceuticalProductionLicenseBaseInfoServiceImpl.java b/src/main/java/com/alihealth/d2d/provtest/service/impl/PharmaceuticalProductionLicenseBaseInfoServiceImpl.java new file mode 100644 index 0000000..f6860af --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/service/impl/PharmaceuticalProductionLicenseBaseInfoServiceImpl.java @@ -0,0 +1,20 @@ +package com.alihealth.d2d.provtest.service.impl; + +import com.alihealth.d2d.provtest.domain.PharmaceuticalProductionLicenseBaseInfo; +import com.alihealth.d2d.provtest.mapper.PharmaceuticalProductionLicenseBaseInfoMapper; +import com.alihealth.d2d.provtest.service.IPharmaceuticalProductionLicenseBaseInfoService; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import org.springframework.stereotype.Service; + +/** + *

+ * 药品生产许可证基本信息数据子集 服务实现类 + *

+ * + * @author Jason + * @since 2025-06-06 + */ +@Service +public class PharmaceuticalProductionLicenseBaseInfoServiceImpl extends ServiceImpl implements IPharmaceuticalProductionLicenseBaseInfoService { + +} diff --git a/src/main/java/com/alihealth/d2d/provtest/utils/CertManager.java b/src/main/java/com/alihealth/d2d/provtest/utils/CertManager.java new file mode 100644 index 0000000..b7bf3e0 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/utils/CertManager.java @@ -0,0 +1,125 @@ +package com.alihealth.d2d.provtest.utils; + +import com.alihealth.d2d.provtest.config.CertConfig; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; + +import javax.annotation.PostConstruct; +import javax.crypto.BadPaddingException; +import javax.crypto.Cipher; +import javax.crypto.IllegalBlockSizeException; +import javax.crypto.NoSuchPaddingException; +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.security.*; +import java.security.interfaces.RSAPrivateKey; +import java.security.spec.InvalidKeySpecException; +import java.security.spec.PKCS8EncodedKeySpec; + +/** + * @author Jason 证书管理 + * @date 2025年06月06日 14:24:09 + */ +@Component +public class CertManager { + + private static volatile String privateKey; + + private static volatile String publicKey; + + @Autowired + private CertConfig certConfig; + + + /** + * 私钥解密 + * @param key + * @param data + * @return + * @throws NoSuchAlgorithmException + * @throws InvalidKeyException + * @throws NoSuchPaddingException + * @throws InvalidKeySpecException + * @throws BadPaddingException + * @throws IllegalBlockSizeException + * @throws IOException + */ + public String testDecrypt(String key,String data) throws NoSuchAlgorithmException, InvalidKeyException, NoSuchPaddingException, InvalidKeySpecException, IllegalBlockSizeException, BadPaddingException, IOException{ + byte[] decode = java.util.Base64.getDecoder().decode(key); + RSAPrivateKey priKey = (RSAPrivateKey) KeyFactory.getInstance(certConfig.getAlgorithm()).generatePrivate(new PKCS8EncodedKeySpec(decode)); + //RSA解密 + Cipher ci = Cipher.getInstance(certConfig.getAlgorithm()); + ci.init(Cipher.DECRYPT_MODE, priKey); + + + byte[] bytes = java.util.Base64.getDecoder().decode(data); + int inputLen = bytes.length; + int offLen = 0; + int i = 0; + ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); + while(inputLen - offLen > 0){ + byte[] cache; + if(inputLen - offLen > 128){ + cache = ci.doFinal(bytes,offLen,128); + }else{ + cache = ci.doFinal(bytes,offLen,inputLen - offLen); + } + byteArrayOutputStream.write(cache); + i++; + offLen = 128 * i; + + } + byteArrayOutputStream.close(); + byte[] byteArray = byteArrayOutputStream.toByteArray(); + return new String(byteArray); + } + + + @PostConstruct + public synchronized void init() throws Exception { + if (privateKey == null) { + privateKey = initPrivateKey(); + } + if(publicKey == null) { + publicKey = initPublicKey(); + } + } + + + + + /** + * 获取私钥 + * @return + * @throws Exception + */ + public String initPrivateKey() throws Exception { + KeyStore keyStore = KeyStoreUtil.loadKetStore(certConfig.getPath(),certConfig.getPassword()); + return Base64.encode(KeyStoreUtil.getPrivateKey(keyStore, certConfig.getPassword()).getEncoded()); + } + + public String getPrivateKey() { + if (privateKey == null) { + throw new IllegalStateException("获取私钥失败,证书未初始化"); + } + return privateKey; + } + + /** + * 获取公钥 + * @return + * @throws Exception + */ + public String initPublicKey() throws Exception { + KeyStore keyStore = KeyStoreUtil.loadKetStore(certConfig.getPath(),certConfig.getPassword()); + PublicKey publicKey = KeyStoreUtil.getPublicKey(keyStore); + return Base64.encode(publicKey.getEncoded()); + } + + public String getPublicKey() { + if (publicKey == null) { + throw new IllegalStateException("获取公钥失败,证书未初始化"); + } + return publicKey; + } +} diff --git a/src/main/java/com/alihealth/d2d/provtest/utils/KeyStoreUtil.java b/src/main/java/com/alihealth/d2d/provtest/utils/KeyStoreUtil.java index b475af5..15c92fe 100644 --- a/src/main/java/com/alihealth/d2d/provtest/utils/KeyStoreUtil.java +++ b/src/main/java/com/alihealth/d2d/provtest/utils/KeyStoreUtil.java @@ -77,7 +77,6 @@ public class KeyStoreUtil { * 获取私钥 * * @param keyStore - * @param keyAlias * @param pfxPassword * @return */ @@ -103,7 +102,6 @@ public class KeyStoreUtil { * 获取公钥 * * @param keyStore - * @param keyAlias * @return */ public static PublicKey getPublicKey(KeyStore keyStore) { @@ -183,7 +181,7 @@ public class KeyStoreUtil { /** * 私钥解密 * - * @param data + * @param encodestr * @param privateKey * @return * @throws Exception @@ -201,7 +199,6 @@ public class KeyStoreUtil { * 验证Certificate是否过期或无效 * * @param keyStore - * @param keyAlias * @param date * 当前时间 * @return @@ -265,8 +262,8 @@ public class KeyStoreUtil { * 验证签名 * * @param keyStore - * @param pfxPassword * @param dataStr + * @param signStr * @return */ public static boolean verfySignature(KeyStore keyStore, String dataStr, @@ -294,9 +291,8 @@ public class KeyStoreUtil { /** * 验证签名使用公钥 * - * @param keyStore - * @param pfxPassword * @param dataStr + * @param signStr * @return */ public static boolean verfySignatureWithPublic(byte[] publicKeyArr, diff --git a/src/main/java/com/alihealth/d2d/provtest/utils/LocalDateDeserializer.java b/src/main/java/com/alihealth/d2d/provtest/utils/LocalDateDeserializer.java new file mode 100644 index 0000000..ec3a592 --- /dev/null +++ b/src/main/java/com/alihealth/d2d/provtest/utils/LocalDateDeserializer.java @@ -0,0 +1,23 @@ +package com.alihealth.d2d.provtest.utils; + +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.databind.DeserializationContext; +import com.fasterxml.jackson.databind.JsonDeserializer; + +import java.io.IOException; +import java.time.LocalDate; +import java.time.format.DateTimeFormatter; + +/** + * @author Jason + * @date 2025年06月06日 15:06:07 + */ +public class LocalDateDeserializer extends JsonDeserializer { + private static final DateTimeFormatter FORMATTER = DateTimeFormatter.ofPattern("yyyyMMdd"); + + @Override + public LocalDate deserialize(JsonParser p, DeserializationContext ctxt) throws IOException { + String dateStr = p.getText(); + return LocalDate.parse(dateStr, FORMATTER); + } +} \ No newline at end of file diff --git a/src/main/resources/application.yml b/src/main/resources/application.yml index ddb3b10..51c2a60 100644 --- a/src/main/resources/application.yml +++ b/src/main/resources/application.yml @@ -31,4 +31,12 @@ logging: org.springframework: WARN com.alihealth.d2d.provtest: DEBUG mybatis: DEBUG - com.baomidou.mybatisplus: DEBUG \ No newline at end of file + com.baomidou.mybatisplus: DEBUG + +cert: + #本地 + #path: D:\ynyp\药品追溯\d2d\yunnan.pfx + #服务器 + path: /data/cert/d2d/yunnan.pfx + password: 12345678 + algorithm: RSA diff --git a/src/main/resources/mapper/AbroadPharmaBaseInfoMapper.xml b/src/main/resources/mapper/AbroadPharmaBaseInfoMapper.xml new file mode 100644 index 0000000..7c6204e --- /dev/null +++ b/src/main/resources/mapper/AbroadPharmaBaseInfoMapper.xml @@ -0,0 +1,5 @@ + + + + + diff --git a/src/main/resources/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.xml b/src/main/resources/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.xml new file mode 100644 index 0000000..88257ce --- /dev/null +++ b/src/main/resources/mapper/PharmaceuticalProductionLicenseBaseInfoMapper.xml @@ -0,0 +1,5 @@ + + + + + diff --git a/target/classes/application.yml b/target/classes/application.yml index ddb3b10..f668f59 100644 --- a/target/classes/application.yml +++ b/target/classes/application.yml @@ -31,4 +31,9 @@ logging: org.springframework: WARN com.alihealth.d2d.provtest: DEBUG mybatis: DEBUG - com.baomidou.mybatisplus: DEBUG \ No newline at end of file + com.baomidou.mybatisplus: DEBUG + +cert: + path: D:\ynyp\药品追溯\d2d\yunnan.pfx + password: 12345678 + algorithm: RSA diff --git a/target/classes/com/alihealth/d2d/provtest/ProvTestClient.class b/target/classes/com/alihealth/d2d/provtest/ProvTestClient.class index 4d9f32ce3eb8796afda7c6ceb292a522fa4beaac..54e23355a27bea09f501b5847bbaba8f8b0e028d 100644 GIT binary patch delta 14 Vcmca$alvAP4?CmrW?yz@Q2;7V1ZMyM delta 14 Vcmca$alvAP4?CmbW?yz@Q2;7J1Z4mK diff --git a/target/classes/com/alihealth/d2d/provtest/controller/ProvTestServerController.class b/target/classes/com/alihealth/d2d/provtest/controller/ProvTestServerController.class index dc6420f2dc584d4a9dbfa32de2692e66eae8f2c1..b6465f7a64122324e8bcb9fd809afb4ac2045a70 100644 GIT binary patch delta 1704 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 RDE|U`=>}%PFXu-n`eQXrP8$FK diff --git a/target/classes/com/alihealth/d2d/provtest/entity/BaseEntity.class b/target/classes/com/alihealth/d2d/provtest/entity/BaseEntity.class index 1d98fbc6888911d5a96c855ab66bfec8a6bf8956..1f62ee13bd995e6a28583ee64048e2474df29a79 100644 GIT binary patch literal 4415 zcmbVO>vI!T6hE8pW;e-(hCqQx6_Bc>52C23X{kVYRa>YuRKN#rleJmc?1p4h!1r5x zG2gbH4Uv$R5$=C1f-6WedMPR1gd+s^Ed*0{X{Q1vMzYx(wbR|wM zRbr&l`8Z{$%2bU%9)Id8Eyb~3;Lk+{Tw>}a{=CeeSD5#zO0UJKm#P}Q&g&cec~hge zGeyIt(vu9oBJHc z^$gE)oti|W(*?JjT`=6TRdnmw@}&hxY8AU)%Nk8wHgDkER1vzACBv?p63O1B3YL+Z zIzCm*1C7)2z7zRl5~=2r>3CD{HXZVI&Z}C!zjye|i`j};r)aM-u{ghJ_Nv>XoA5abP_t7(tKE2=pYx zrh%)Wu+a!1E4 z$MPm5+8p%hl(W>OQ`6J7TV8O_We=N@Wi)F0rw zxYU4$or;?0>xKy^wZ29f)6fQLx)IX2wia!XrMREDT`-0&d z8MTraPE6_)Vx2ucHFFTj03EHGwYu$Lh(*u?&8QLsVfPaQVLvs`6-ATi2bPWr$MGR zQ@>8zX#lr1-}N_p{pe)SQ#$RZNu6eyIzSUT9b^NC`LjR;i8i(#8@b;~YtYprRy zH)s|2==2eN%%4v%8zWnTyzfClN4B;yFZQk6V=p0sbA;O=)iNbgDADl$$J5MV!`GFw zg>G=%3uq3bQZXIO!f3Z~4OOr$QuJgSzA=8Q;^l34-ZOY_?jV^WTpiGN;sr`$y$hTz zH88iDw2kh@4uuQk39R?v|K1wi2LWmu2vWWv!h#_hK20N#q6Y$L=-5tTXqN5=-~m`X zf>pw*4gE;c_Z0aSbPw&qHx3EGwhHSHg3<*JziS@GZg(5!5$xFiC@_x_$r3$AInZO^ zMQ9xRJv0GY;+_mF=L5_7&=1rjtjjIyX=H};AtOf$@{_>Y@!MojRNa3Ysxh`* zR7W~hZ@CTCM`#L3<(`^`3GSWf(D3)9v}!7no%VHa5QrezTr)8Rt-gu|X@3Hm6#Ozk z;XXt1*gQ2dyafD)AS2Z}e!r-y)217%7V}s%b zSk>U@3WK=hMTFAls80gvzCJwk6)Ezy;onI8f|QlB(Tu!I@dhH1QvgZiq8WuT(cdY3m691H6Agj%oC=Vh(=sZ9v;d@Lv=Atn zivg6(#WOJm#RE_*6K{azYw%k3Z?JH3Dk7R@zg?%}G>2B|qc16s8!duc?h2g%uLn2i zWts;ihE6aBPb1g2}<2V zWh$b0_!Wp^z6dIU;=D+U2)75%+YFUJ$+*pTkp)UYaW~RgP|;8_SR20qT)3}E`xg)y zg_9%{izMk^sA}ya%;+Pf0cc?4c2)q3hF~pZCpQ4A?cf%^ivUMDZcO}$5*4FYu=2~d z_h;%o^#i5SYnLg_gGgt6U`h80T4(+SK_{8s2zr?|bv_)Txx`O}y+H+9EybM9 QmoyUmNU%{S{;}Zv2cGRxrvLx| literal 4402 zcmbVP>vI#=75}Zgt6fPetcVy8I1NeM#!r-xHf?1?0f!JLHV`amLLX!;ZS4hVC8U)T zn)KZ!>2s!^n#oMRmYED6TBdP2?M$crlFsyRYMTDe-j%eH{)ydl&r8NMsSo3i(oiSMN`j++*~ zFY^y%_@RX#S@^MqpIG>*Z2Zi`+a})8knpM+a;w*!ZKqgs{LSKO!{1!gP`K3b1F!C0 z@!H--%{}e=jlc=KhTqn(uv%%2}4bJr}WfG^2pmgsCCbX;z&;92#SyKsn(? zBqyU5U2L=EUKTjdjZM#7p&84KDi`Ccp6{OT)HmE#7#s0Ov|e#qo`{Y%^(qj+V)b~n*labn1GgO%84)kIRXpRg-LoM{iw_J6V-O>O&)k=!rE+=kB*i^4 zBCr>`o{_(A(+!mF<(ku`!TYCYVhIX22}`Yeo4yltS`5IU-H5I>k;drLpWu9$vxf(; zy>us+Jl_jWYB&E7%(H7XmBe_`XgTL~6tu4>R4gB=#J7`8^R<+j*}QkPTGL{_*H zl6JV+YtgLY^w#4cJKl3Sg@|t{km?~7!3Y%Jdiwr~cvea{yB;`|8*5H8Yy{q(y!2>& z#qrNdFi37W?Jd=u?9>(ddhycA+F1sJbh72PJGFpKtel?ed6k)po1dAA+i3+2l{5`+ zE|p97XLZZ)Y5S{6G zwW^fXzP@?WUX>?*fnUn-EB40x(J1aGn9%v7{m83zKlWT}Gd8Y+M6Rz&g;2xX|M#aC z!>+BndyCcJH(qCPIL)T(vlkXdwQDSc1D>)b2k_nY+Y_%p#%I02_vSEkBqTeeAK?p> z<@`DR9(8dPkCDZkMXU_xDgHj+#uvz7S|dg-WF&+!gW0Q?BbVuqxUpjk5a=-!33!Ui zUf`^8wr2kV?L#E~M0yNQb4-&1YBs6yI4N7<@C-j@fG-W~Jj<1so+ReWfUe;y_$uiV z_Yzp-dI={;Yf_Gp=5nOjp8W`8O1s|Io@Y=184tr?XfmApR@l3&kR7q&Yy627r#Nd; zw2`*cT#28??4M!$k%V$mpuj{-w6ROH?CciJE*K#?IV}3n1BhmCjS#I5i=KP{(d^g} zq7%cSAAJDP=U7W)VNI=4h15=RcJ4zM{hX>`=R?^C6e0??EhpJuoRQTjBh37{rj5Xw-MQI6z|il^{S)T^-b#f z7HxbM@)H0PjJA*HU77>PjE<)sXa(U{qXWo@^pEoqw;)-j!6R=k~N7({IZMp zU-z;jlu?j)^oyl??M3?5hxBRk@KeiEyl16YOsZ+-7MJuBVM$Ep7PnXsR&MS#%!M87 zdrkH;C0!T=J>pnWCW>X3jF80&2@hEXqsz*ck|8VEW3g^{YI1a{Ur@G0sUAZe6;$b( z!DPCm5=_o__)k*(1QWYSO6S9L99yIert}~@Qps2_no$ZRaUa0?ln|YX(=;Xvn)WG0 z_16j6n1Im*bTRtiRs>7NV14B9ZUi<5!F~J)29FHgnEZZH8N*wg<>fo|H;ljf5pwy5 zc956E?O=cYVMS*+QmuVl!1Op$(?PyMO diff --git a/target/classes/com/alihealth/d2d/provtest/service/XmlParserService.class b/target/classes/com/alihealth/d2d/provtest/service/XmlParserService.class index a991cdf995b6ee825db03a8d972db0f69b897da2..1d3e1c4441851707a99255ac6394ae2eaad5db5b 100644 GIT binary patch delta 3712 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 delta 3181 zcmai0d3;pW75>i5o4GS@-Yg8sBonp-36M-;K!bsaY(WA<0=2=~(AF9eA%G+$L7*U0 zK~U??bE(zVwiKb(Rv_&pAx6*^T5T=eTWVXn+Sho@L3acuutJ}h5aTD;B$Kagu>_b`lN|kd_jM{sPI$( z2TfQwWMT#m>ran~IKHIth}16U>i7 z_%TlD&rbq)$;40bGrjq_!fB1~7aHj=;}HBNl)`WEvcm5aey{LK0Dmx1k3TB>$;2$| zRrs^U%=J};zw~SrTkLt>$0FwZ%_~-RcDHw|?^1Zp9`c^{D*UzQRb#HFRuFFKZd|e`<@L!*!C1SkpwJ$S1OoK}SxdL< zN6am;CR}b|Ar@KqJN_X^*@ujYd%QloEi}@?KP~(V|F-ZS{MRnErbI}*W#MfMSyUnR z)z<8IlXxugVvi+;_(+N0e#*Ksq$~+Y&=ONZb~Ic!(~_{l>y|_$O5ZGr$p}m0GSZR) zTrL>7rtQYInssgKSJf@nZc+T2dmT>}SKxnb9)F zlCc<4GR~4xDHFsRIy$<$x;M0SHm~en-Em!4)Gy;>azWH56Jk$W-bW_NS$LL;Lzw7B0hlOD>X&sjW69)3lmPlmzQ6nJzN~CH5G9 ziT!w_Y>zd{J{~FaHc8rkC9$q zCRZ#z*D|xE+Pmi8(Am93;GJBt-0p~%^t>5=S?t^6qwJRoUJC}gJ6tdA=L?s5>*Z2= zR3fE(GE-1K+3pM$QMtcoP2vi%>tkg;wt>vDj}^TYn{CM)xy+LJ%qTvFhwT@Or^y1_ zn|#AqNLjlyS#FOjnUHBKKfJ zWb#5QHt88qi2_{cD6e!C_mvvLR^QH2#~uT*JBlel$nav zXlGe%XHl)eTJkMJW*63x$xp#k`4pbYrBI)(cPgs_2hl;*Ub^)JK7gY)dMJN)s@KUP~400y7Vq!=^07GExqB!jysKfJ#)Sq znFLc(L!&x%wXOjt`rKl=)7L`ANlx@VNMO7ZeVvCOb~CYt6MeS{HUDzraql+r?thyw zhw$vC&jfL69%3IQbR|qV2V&HPcm`eCs7?~y1P^pau_=e4B^(4@^msFU-NLHahHBj8 zpqu6D&ZC>6(J>ih9+!t#l7m-@m{XVr#l5W7_FS2{K((j_>fYVPyZ;L`h}&6x?l69u zt4?LwH<-x}n|v7pxY&EibBJp9l61 zUJqyWUIOLMiyT<3R*&+!%05&d;ah@!)Oh%rB8X4T^x>j@T&z=ByZA7srLwrB@(AiQ z*K{vWXAC2ClY18n?`}@2dr*jb`HORpgVJ@i4mQUgc$&Zi&f_%v5b3)Id3VP7wDT@x z_%PT!ZRDQ^55-LVUX#*~&{`t!aved>qX(M@P~RHAw5k^~k1_`OHS;l;?pqmg7$4xt zgG|Rmj!SwX`8k0;jz^pTjL11hg?N-xP4q;{kVWPzeB#WrXvboBGzN~&Pv&3#sg68Q zIDlC!hS@!sHh?*#=Jvp&$GDvJV2|d69ZTmP}iJC4+haoEA0_=p6=yve&0FVuP53Q?Y!)-sKF5>o>~%Ej8AhY%Sob+ zWR{SsJ)L?oSW33`TpGw@86#QYeepjDt`@yUbfd^7hO>?|TI6mf$Ob}e^xg&b`?l-t z9So#Zj-B4M)FiJXWs~oK)OM){@pH&4NNx3Qgd#rcN&@OW5-zeZaMVe#y zK?Ogl<`*;h%{>0-7=Lw$f7BT?n8g~?vn?`+UN)HiHiQ8-lz zJtf-1wv>o9sNV9JWhYoYk!@>*wJ_4wsoHvBEtFZa>TRIXHpZ$$ z@fO)4bgR&9LbnUuq10BT?o?`<@LfvXt<*N*dz89YsrzD^b9@#&M4TPgF^-UENAcS+ zVaJ(Z9n6)s$WD5va!;q7!&!`YJFjbB(Ah4^c}aaPQfgPc=Daul+d9J?o#C#U-V=MD zh4w(-)g5cfue6F$^l>Hl+-P!Km_k>|ELTRYD`%}6$0j$Pc2`A*o5)qSi0f`4U9N_k KF6zB4*!&+v9-Dmt delta 790 zcmWNOS!|6_6otQiiW+(qp>;cGZ`<2Z1?}x*Zq0KdofYL7Z51tjCN=YWkeGrJA)?#} ztwhZ6Vor&OAtd5SD2Z9Dr@gbXzOz>Lc~|kSqO;3iT#loXNU9h}H9pPZtRR*eMp8?H z_9T{)OdV<3Ggw9@%Nb3**X!>ItP$NHx=~~kF*K7%i`*Lsu#q6G-p9BDzIMI6jUjB8 zV~2M=A=c}NZ}lCLdRXca{2cYN6WV>}rF2TUAm2s#_V{i}xh3VcJa@dh#8bg1O6*bM zGY0cq>I+hMsZMXm;gx#5W(;q`nWLP|_)K5E5JfN1d?k)=r1D+XA7t~BT+Q+PqL|-I zVHP6R3P`p>(yfRwR!pIlP-GLl&w-w-X$-JZ2HA9m z+6+18DrhG0Hj5nw^Q1Hc?)6jI_`e zp<9Kv3*9bshf;Scb(c~-;k%W(N2#9hy-MAu)cxVMbe{!|5n;!5j1vsD4*Ygf*eNF3 zX%1^F{UR9rN^6k3UocZ2=UuSrrGdxt&M`9nd#GdH8 zo`xH;CRuSF{arpj7b4vilH-b)?@Fk26KHgkX?0UL=t}8uWn6RB+;ElLbXDASHQtBp Fw*OyKo7MmT