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 4d9f32c..54e2335 100644 Binary files a/target/classes/com/alihealth/d2d/provtest/ProvTestClient.class and b/target/classes/com/alihealth/d2d/provtest/ProvTestClient.class differ diff --git a/target/classes/com/alihealth/d2d/provtest/controller/ProvTestServerController.class b/target/classes/com/alihealth/d2d/provtest/controller/ProvTestServerController.class index dc6420f..b6465f7 100644 Binary files a/target/classes/com/alihealth/d2d/provtest/controller/ProvTestServerController.class and b/target/classes/com/alihealth/d2d/provtest/controller/ProvTestServerController.class differ diff --git a/target/classes/com/alihealth/d2d/provtest/entity/BaseEntity.class b/target/classes/com/alihealth/d2d/provtest/entity/BaseEntity.class index 1d98fbc..1f62ee1 100644 Binary files a/target/classes/com/alihealth/d2d/provtest/entity/BaseEntity.class and b/target/classes/com/alihealth/d2d/provtest/entity/BaseEntity.class differ diff --git a/target/classes/com/alihealth/d2d/provtest/service/XmlParserService.class b/target/classes/com/alihealth/d2d/provtest/service/XmlParserService.class index a991cdf..1d3e1c4 100644 Binary files a/target/classes/com/alihealth/d2d/provtest/service/XmlParserService.class and b/target/classes/com/alihealth/d2d/provtest/service/XmlParserService.class differ diff --git a/target/classes/com/alihealth/d2d/provtest/utils/KeyStoreUtil.class b/target/classes/com/alihealth/d2d/provtest/utils/KeyStoreUtil.class index 486cae8..8ce6eaf 100644 Binary files a/target/classes/com/alihealth/d2d/provtest/utils/KeyStoreUtil.class and b/target/classes/com/alihealth/d2d/provtest/utils/KeyStoreUtil.class differ