Explorar el Código

完成ca签名

xiaochan hace 1 mes
padre
commit
5f989699fc

+ 1 - 1
pom.xml

@@ -10,7 +10,7 @@
     </parent>
     <groupId>thyyxxk</groupId>
     <artifactId>web-server</artifactId>
-    <version>14.1.4</version>
+    <version>14.1.6</version>
     <name>web-server</name>
     <description>server for yibao-web</description>
     <properties>

+ 6 - 1
src/main/java/thyyxxk/webserver/config/envionment/SystemConfig.java

@@ -34,6 +34,11 @@ public class SystemConfig {
 
     /**
      * 医保科科室编码
-     * */
+     */
     private String medinsurDept;
+
+    /**
+     * magic-api地址
+     */
+    private String magicApi = "http://172.16.32.167:9205/thyy/api";
 }

+ 8 - 13
src/main/java/thyyxxk/webserver/controller/ca/CaController.java

@@ -4,6 +4,7 @@ import cn.hutool.core.util.StrUtil;
 import cn.hutool.json.JSONObject;
 import lombok.RequiredArgsConstructor;
 import lombok.extern.slf4j.Slf4j;
+import org.springframework.validation.annotation.Validated;
 import org.springframework.web.bind.annotation.*;
 import thyyxxk.webserver.config.auth.PassToken;
 import thyyxxk.webserver.config.exception.ExceptionEnum;
@@ -36,28 +37,16 @@ public class CaController {
         return ResultVoUtil.success(server.sendByCode(send));
     }
 
-    @GetMapping("/getSignInfoByBizSn")
-    public ResultVo<CaSingBizSnReturnData> getSignInfoByBizSn(@RequestParam("bizSn") String bizSn) {
-        return server.getSignInfoByBizSn(bizSn);
-    }
-
     @PostMapping("/sendMoreEventSign")
     public ResultVo<JSONObject> sendMoreEventSign(@RequestBody CaSignClass.MoreEventSign moreEventSign) {
         return server.sendMoreEventSign(moreEventSign);
     }
 
     @PostMapping("/h5EventSign")
-    public ResultVo<CaSignClass.H5Return> h5EventSign(@RequestBody CaSignClass.H5EventSign value) {
+    public ResultVo<CaSignClass.H5Return> h5EventSign(@Validated @RequestBody CaSignClass.H5EventSign value) {
         return server.h5EventSign(value);
     }
 
-
-    @GetMapping("/downloadSealV2")
-    public ResultVo<JSONObject> downloadSealV2(@RequestParam("id") String id,
-                                               @RequestParam("documentId") String documentId) {
-        return server.downloadSealV2(id, documentId);
-    }
-
     @RequestMapping("/hBoardSignReturnUrl/{document}")
     @PassToken
     public JSONObject hBoardSignReturnUrl(@PathVariable("document") String document,
@@ -92,4 +81,10 @@ public class CaController {
         return server.getUserSeal(code);
     }
 
+    @PostMapping("/retrySMS")
+    public ResultVo<String> retrySMS(@RequestBody CaServer.RetrySMSParams info) {
+        return server.retrySMS(info);
+    }
+
+
 }

+ 12 - 6
src/main/java/thyyxxk/webserver/controller/zhuyuanyizheng/ClinicalPathwayPatientController.java

@@ -56,12 +56,6 @@ public class ClinicalPathwayPatientController {
         return service.getClinicalPathway(patNo, times);
     }
 
-    @GetMapping("/generatePath")
-    public ResultVo<String> generatePath(@RequestParam("patNo") String patNo,
-                                         @RequestParam("times") Integer times) {
-        return service.generatePath(patNo, times);
-    }
-
     @PostMapping("/updatePatientDay")
     public ResultVo<String> updatePatientDay(@RequestBody UpdatePatientDayReq params) {
         return service.updatePatientDay(params);
@@ -79,4 +73,16 @@ public class ClinicalPathwayPatientController {
         return service.exitClinicalPathway(req);
     }
 
+    @GetMapping("/continueExecution")
+    public ResultVo<String> continueExecution(@RequestParam("patNo") String patNo,
+                                              @RequestParam("times") Integer times) {
+        return service.continueExecution(patNo, times, false);
+    }
+
+    @GetMapping("/nextPhase")
+    public ResultVo<String> nextPhase(@RequestParam("patNo") String patNo,
+                                      @RequestParam("times") Integer times) {
+        return service.continueExecution(patNo, times, true);
+    }
+
 }

+ 5 - 1
src/main/java/thyyxxk/webserver/dao/his/zhuyuanyisheng/patientClinicalPathway/ClinicalPathwayPatientDao.java

@@ -4,6 +4,7 @@ import com.baomidou.mybatisplus.core.mapper.BaseMapper;
 import org.apache.ibatis.annotations.Mapper;
 import org.apache.ibatis.annotations.Select;
 import thyyxxk.webserver.entity.dictionary.pathwayTemplates.dto.ClinicalPathwayTemplates;
+import thyyxxk.webserver.entity.dictionary.pathwayTemplates.dto.ClinicalPathwayWork;
 import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.dto.ClinicalPathwayPatient;
 import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.dto.ClinicalPathwayPatientDayLog;
 import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.vo.ClinicalPathwayPatientWorkLogVo;
@@ -42,7 +43,7 @@ public interface ClinicalPathwayPatientDao extends BaseMapper<ClinicalPathwayPat
             "where pat_no = #{patNo}\n" +
             "  and times = #{times}\n" +
             "  and template_id = #{id} and exec_date >= #{createDate}")
-    List<ClinicalPathwayPatientDayLog> selectExecDay(String patNo, Integer times, String id,String createDate);
+    List<ClinicalPathwayPatientDayLog> selectExecDay(String patNo, Integer times, String id, String createDate);
 
 
     @Select("select sum(execution_day)\n" +
@@ -92,4 +93,7 @@ public interface ClinicalPathwayPatientDao extends BaseMapper<ClinicalPathwayPat
             "where pat_no = #{patNo}\n" +
             "  and times = #{times} order by create_time")
     List<ClinicalPathwayPatient> selectPatientCount(String patNo, Integer times);
+
+    @Select("select * from clinical_pathway_work where day_id = '${dayId}'")
+    List<ClinicalPathwayWork> selectWorkByDayId(String dayId);
 }

+ 17 - 0
src/main/java/thyyxxk/webserver/dao/his/zhuyuanyisheng/patientClinicalPathway/ClinicalPathwayPatientDayLogDao.java

@@ -1,11 +1,28 @@
 package thyyxxk.webserver.dao.his.zhuyuanyisheng.patientClinicalPathway;
 
+import com.baomidou.mybatisplus.core.conditions.Wrapper;
 import com.baomidou.mybatisplus.core.mapper.BaseMapper;
 import org.apache.ibatis.annotations.Mapper;
+import org.apache.ibatis.annotations.Param;
+import org.apache.ibatis.annotations.Select;
 import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.dto.ClinicalPathwayPatientDayLog;
 
 @Mapper
 public interface ClinicalPathwayPatientDayLogDao extends BaseMapper<ClinicalPathwayPatientDayLog> {
 
 
+    @Select("select top 1 * from clinical_pathway_patient_day_log " +
+            "${ew.customSqlSegment}")
+    ClinicalPathwayPatientDayLog getCurrentPatientWorkLog(
+            @Param("ew") Wrapper<ClinicalPathwayPatientDayLog> ew
+    );
+
+
+    @Select("select top 1 id\n" +
+            "from clinical_pathway_day\n" +
+            "where template_id = '${templateId}'\n" +
+            "order by sort;")
+    String getTheFirstDay(@Param("templateId") String templateId);
+
+
 }

+ 0 - 1
src/main/java/thyyxxk/webserver/dao/his/zhuyuanyisheng/patientClinicalPathway/ClinicalPathwayPatientWorkLogDao.java

@@ -7,5 +7,4 @@ import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.dto.Clinic
 @Mapper
 public interface ClinicalPathwayPatientWorkLogDao extends BaseMapper<ClinicalPathwayPatientWorkLog> {
 
-
 }

+ 30 - 5
src/main/java/thyyxxk/webserver/entity/ca/CaSignClass.java

@@ -4,6 +4,10 @@ import cn.hutool.json.JSONObject;
 import lombok.*;
 import thyyxxk.webserver.entity.ca.dto.CaSignData;
 
+import javax.validation.constraints.Min;
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.NotNull;
+import javax.validation.constraints.Null;
 import java.util.List;
 
 public class CaSignClass {
@@ -25,6 +29,9 @@ public class CaSignClass {
     }
 
     @Data
+    @AllArgsConstructor
+    @Builder
+    @NoArgsConstructor
     public static class MoreEventSignData {
         private String content;
 
@@ -77,16 +84,33 @@ public class CaSignClass {
      */
     @Data
     public static class H5EventSign {
-        private String uuid;
+
+        @NotBlank(message = "文档id不能为空")
         private String documentId;
+
+        @NotBlank(message = "签名位置不能为空")
         private String content;
+
+        @NotBlank(message = "身份证不能为空")
         private String idCard;
-        private Integer signType;
+
+        @NotBlank(message = "与患者关系不能为空")
+        private String signType;
+
+        @NotBlank(message = "名字不能为空")
         private String name;
         private String signOpinion;
+
+        @NotNull(message = "来源不能为空")
         private SignSourceEnum source;
+
+        @NotBlank(message = "患者id不能为空")
         private String patNo;
+
+        @Min(value = 0, message = "次数需要大于0 ")
         private Integer times;
+
+        @NotBlank(message = "请输入手机号")
         private String phone;
     }
 
@@ -95,9 +119,10 @@ public class CaSignClass {
     @AllArgsConstructor
     @NoArgsConstructor
     public static class H5Return {
-        private String caDocumentId;
-        private String result;
-        private String uuid;
+        // 签名页面地址(公网地址)
+        private String signUrl;
+        // 签名页面地址(内网地址),后台未配置内网地址则不显示
+        private String extSignUrl;
     }
 
     @Data

+ 2 - 1
src/main/java/thyyxxk/webserver/entity/ca/dto/CaSignData.java

@@ -101,7 +101,8 @@ public class CaSignData implements Serializable {
     public static enum SignType {
         qrCode(1, "扫码"),
         MOVE_PAD(2, "平板签名"),
-        IPAD_EDITOR(3, "移动平板编辑");
+        IPAD_EDITOR(3, "移动平板编辑"),
+        H5_HTTP(4, "H5签名");
 
         @Getter
         @EnumValue

+ 20 - 4
src/main/java/thyyxxk/webserver/entity/dictionary/pathwayTemplates/dto/ClinicalPathwayWork.java

@@ -3,10 +3,7 @@ package thyyxxk.webserver.entity.dictionary.pathwayTemplates.dto;
 import java.io.Serializable;
 
 import com.baomidou.mybatisplus.annotation.*;
-import lombok.Data;
-import lombok.AllArgsConstructor;
-import lombok.Builder;
-import lombok.NoArgsConstructor;
+import lombok.*;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 
@@ -55,6 +52,25 @@ public class ClinicalPathwayWork implements Serializable {
     @TableField(value = "sort")
     private Integer sort;
 
+    @AllArgsConstructor
+    @Getter
+    public enum WorkType {
+        zhenliao(0, "主要诊疗工作", 1),
+        yzchangqi(1, "长期医嘱", 0),
+        yzlinshi(2, "临时医嘱", 0),
+        huli(3, "主要护理", 1);
+
+        private final Integer code;
+        private final String desc;
+        private final Integer complete;
+
+        public static WorkType getByCode(Integer code) {
+            for (WorkType type : WorkType.values())
+                if (type.code.equals(code))
+                    return type;
+            return null;
+        }
+    }
 
 
     public static LambdaQueryWrapper<ClinicalPathwayWork> lambdaQueryWrapper() {

+ 1 - 1
src/main/java/thyyxxk/webserver/entity/zhuyuanyisheng/patientClinicalPathway/dto/ClinicalPathwayPatientDayLog.java

@@ -31,7 +31,7 @@ public class ClinicalPathwayPatientDayLog implements Serializable {
     private String id;
 
     /**
-     * 天数id
+     * 天数id这个是 clinical_pathway_day 里面的id
      */
     @TableField(value = "day_id")
     private String dayId;

+ 213 - 53
src/main/java/thyyxxk/webserver/service/ca/CaServer.java

@@ -1,7 +1,8 @@
 package thyyxxk.webserver.service.ca;
 
 import cn.hutool.core.codec.Base64;
-import cn.hutool.core.convert.Convert;
+import cn.hutool.core.date.DateUnit;
+import cn.hutool.core.date.DateUtil;
 import cn.hutool.core.io.FileUtil;
 import cn.hutool.core.util.IdUtil;
 import cn.hutool.core.util.IdcardUtil;
@@ -12,11 +13,11 @@ import cn.hutool.crypto.asymmetric.RSA;
 import cn.hutool.json.JSONArray;
 import cn.hutool.json.JSONObject;
 import cn.hutool.json.JSONUtil;
-import com.alibaba.fastjson.JSON;
 import com.dtflys.forest.Forest;
 import com.dtflys.forest.http.ForestRequest;
 import com.dtflys.forest.logging.LogConfiguration;
 import com.dtflys.forest.utils.ForestDataType;
+import com.dtflys.forest.utils.RequestNameValue;
 import lombok.*;
 import lombok.extern.slf4j.Slf4j;
 import org.jetbrains.annotations.NotNull;
@@ -24,6 +25,7 @@ import org.springframework.stereotype.Service;
 import thyyxxk.webserver.config.Assertion;
 import thyyxxk.webserver.config.envionment.ArchiveConfig;
 import thyyxxk.webserver.config.envionment.CaData;
+import thyyxxk.webserver.config.envionment.SystemConfig;
 import thyyxxk.webserver.config.exception.BizException;
 import thyyxxk.webserver.config.exception.ExceptionEnum;
 import thyyxxk.webserver.constants.YesOrNo;
@@ -33,7 +35,6 @@ import thyyxxk.webserver.entity.ResultVo;
 import thyyxxk.webserver.entity.ca.*;
 import thyyxxk.webserver.entity.ca.dto.CaSignData;
 import thyyxxk.webserver.entity.login.UserInfo;
-import thyyxxk.webserver.service.hutoolcache.CaCache;
 import thyyxxk.webserver.service.hutoolcache.UserCache;
 import thyyxxk.webserver.service.zhuyuanyisheng.emr.EmrServer;
 import thyyxxk.webserver.utils.R;
@@ -44,7 +45,9 @@ import java.io.UnsupportedEncodingException;
 import java.net.URLDecoder;
 import java.nio.charset.StandardCharsets;
 import java.util.ArrayList;
+import java.util.Date;
 import java.util.List;
+import java.util.Set;
 
 @Slf4j
 @Service
@@ -54,10 +57,10 @@ public class CaServer implements Assertion {
     private final String archivePath;
     private final static String privateKey = "MIICdgIBADANBgkqhkiG9w0BAQEFAASCAmAwggJcAgEAAoGBAKAc+jzqVKHsjNdyuDGL7u6zZR55j87l+0GGT4/yEV+K8ZtL1GoIgOD6vv6eEg2iOwl6Wh6hq8XR4cIyzVyvMZ35dIw3oGN89ObtuCha7gLOmWYUIGVnkUBkLFeIdwe4F8bq1q15o7azsTVekSyNJf/wnxWMp8ibtvO41T8DIzZPAgMBAAECgYAeeLVVD4Gw2VyKij4sy8Var1CQxrDMPu+c7ktJCVguFzrZA8r2rQyeBIqB2aJ07smOibcJ+lm/Ca0N8O4tc/gcm4g/JsjBALFUmqyCkLQpRyIbz8V9uAmrLcchT74GS727Uv4KVTmQNDZTPIDdSZWSJ8S+WKmj8q3wUF1HLF1eXQJBAOC7D6xIB2XNS6Voa7C7m8aeg53lfcDUVJ6m0YFdvMbsU2cnlxnCSX1OsghFuVQLKcGeN+aXiTEileb3pAl2RC0CQQC2ZDtDb+1OmLmRNugp29Pmm8MM8KpktfqiBFi92Q747XwEeMgLi3qetq1wDT4dgvyURs2McsbF7diVtFv7DMXrAkAoYzXj3mYF86k+ps+DyZOrVF2PCOlauE4k3RIVz8TXcy1iAolzRalzbastNWqjIgZ1F3wwYtdzDyYlhifi03BZAkEArkgidPMbwDGhiAf+WhkrZz1JaTECsM9PGcergGVLsENFcQR0qstxtPz7x4lv5EVI0urA+Man93OptIsuJTr0VwJAd86EbHyOn5Lah7ptPGsmsqkrdMZcJ3chRj6pDtvb0A2lhaJfDRxmAiWCnviPhTApH6/1WRzBqc1ZTymyRTF9kA==";
     private final static String publicKey = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCgHPo86lSh7IzXcrgxi+7us2UeeY/O5ftBhk+P8hFfivGbS9RqCIDg+r7+nhINojsJeloeoavF0eHCMs1crzGd+XSMN6BjfPTm7bgoWu4CzplmFCBlZ5FAZCxXiHcHuBfG6tateaO2s7E1XpEsjSX/8J8VjKfIm7bzuNU/AyM2TwIDAQAB";
-    private final CaCache cache;
     private final UserCache userCache;
     private final ArchiveConfig archiveConfig;
     private final CaSignDataDao caSignDataDao;
+    private final SystemConfig systemConfig;
 
     private final PatientIdCardTypeDao patientIdCardTypeDao;
 
@@ -65,18 +68,14 @@ public class CaServer implements Assertion {
 
     RSA idCardRsa = new RSA(privateKey, publicKey);
 
-    public CaServer(CaData caData, CaCache cache, UserCache userCache, ArchiveConfig archiveConfig, CaSignDataDao caSignDataDao, PatientIdCardTypeDao patientIdCardTypeDao) {
+    public CaServer(CaData caData, UserCache userCache, ArchiveConfig archiveConfig, CaSignDataDao caSignDataDao, PatientIdCardTypeDao patientIdCardTypeDao, SystemConfig systemConfig) {
         this.caData = caData;
         this.archivePath = archiveConfig.getPath() + "/archive/emr";
-        this.cache = cache;
         this.userCache = userCache;
         this.caSignDataDao = caSignDataDao;
         this.patientIdCardTypeDao = patientIdCardTypeDao;
         this.archiveConfig = archiveConfig;
-    }
-
-    private String getRedisKey(String documentId) {
-        return "ca-emr-" + documentId;
+        this.systemConfig = systemConfig;
     }
 
     public List<CaReturn.CaData> sendBatchByCode(CaSignClass.Send send) {
@@ -428,8 +427,18 @@ public class CaServer implements Assertion {
      * @return 数据
      */
     public ResultVo<CaSignClass.H5Return> h5EventSign(CaSignClass.H5EventSign value) {
-        JSONObject ret = new JSONObject();
+        String id = CaSignData.getId(value.getDocumentId(), value.getSource());
+        CaSignData caSignData = caSignDataDao.selectById(id);
         String uuid = IdUtil.simpleUUID();
+        if (caSignData != null) {
+            if (caSignData.getSignComplete()) {
+                return R.fail(ExceptionEnum.LOGICAL_ERROR, "病历已经完成,签名了。");
+            }
+            return R.fail(ExceptionEnum.LOGICAL_ERROR, "病历已经在签名");
+        }
+        String returnUrl = StrUtil.join("/",
+                caData.getHBoardSign().getReturnUrl(), id);
+        JSONObject ret = new JSONObject();
         CaData.HBoardSign app = caData.getHBoardSign();
         ret.set("api_key", app.getApiKey());
         ret.set("api_secret", app.getApiSecret());
@@ -441,6 +450,7 @@ public class CaServer implements Assertion {
                 set("page", "0");
                 set("content", URLUtil.encode(value.getContent()));
             }});
+            set("return_url", returnUrl);
         }});
         String execute = Forest
                 .post(caData.getHBoardSign().getUrl() + "/seal/h5EventSign")
@@ -448,47 +458,154 @@ public class CaServer implements Assertion {
                 .bodyType(ForestDataType.JSON)
                 .execute(String.class);
 
-        return getStringResultVo(execute, uuid);
-    }
+        // 组装签名人的信息
+        JSONArray jsonArray = new JSONArray();
+        jsonArray.put(CaSignClass.MoreEventSignData.builder()
+                .content(value.getContent())
+                .signType(value.getSignType())
+                .signTypeName(getSignTypeName(value.getSignType()))
+                .idCard(idCardRsa.decryptStr(value.getIdCard(), KeyType.PrivateKey))
+                .signName(value.getName())
+                .signOpinion(value.getSignOpinion())
+                .build());
+
+        CaSignClass.H5Return h5Return = getStringResultVo(execute);
+
+        H5ssmInfo ssmInfo = H5ssmInfo.builder()
+                .name(value.getName())
+                .signUrl(h5Return.getSignUrl())
+                .extSignUrl(h5Return.getExtSignUrl())
+                .sendTime(DateUtil.date())
+                .build();
 
+        // 组装短信发送的信息,让医生能重试
+        ret.set("ssmInfo", ssmInfo);
 
-    @NotNull
-    private ResultVo<CaSignClass.H5Return> getStringResultVo(String execute,
-                                                             String caDocumentId) {
-        JSONObject rst = JSONUtil.parseObj(execute);
-        String msg = URLUtil.decode(rst.getByPath("ret_msg", String.class));
-        if (0 == rst.getByPath("ret_code", Integer.class)) {
-            CaSignClass.H5Return build = CaSignClass.H5Return.builder()
-                    .result(rst.getByPath("sign_url", String.class))
-                    .caDocumentId(caDocumentId)
-                    .uuid("")
-                    .build();
-            return ResultVoUtil.success(build);
+        CaSignData logData = CaSignData.builder()
+                .documentId(id)
+                .patNo(value.getPatNo())
+                .times(value.getTimes())
+                .caId(uuid)
+                .value(ret.toJSONString(0))
+                .createStaff(TokenUtil.getInstance().getTokenUserId())
+                .signType(CaSignData.SignType.H5_HTTP)
+                .signComplete(false)
+                .source(value.getSource().getCode())
+                .relationship(jsonArray.toJSONString(0))
+                .build();
+        caSignDataDao.insert(logData);
+
+        JSONObject ssmRst = ssmData(ssmInfo, value.getPhone());
+
+        if (ssmRst.getInt("code") != 0) {
+            return R.fail(ExceptionEnum.LOGICAL_ERROR,
+                    "发送短信失败但是病历已生成,带签名文书" +
+                    ssmRst.getStr("message"),
+                    h5Return);
         }
-        return ResultVoUtil.fail(ExceptionEnum.NO_DATA_EXIST, "签名失败" + msg);
+
+        return R.ok(ExceptionEnum.SUCCESS_AND_EL_MESSAGE, h5Return);
     }
 
-    public ResultVo<JSONObject> downloadSealV2(String id, String documentId) {
-        JSONObject ret = new JSONObject();
-        ret.set("api_key", caData.getHBoardSign().getApiKey());
-        ret.set("api_secret", caData.getHBoardSign().getApiSecret());
-        ret.set("data", new JSONObject() {{
-            set("document_no", id);
-        }});
-        String execute = Forest
-                .post(caData.getHBoardSign().getUrl() + "/v2/seal/download")
-                .addBody(ret)
+    // 这里不保存 手机号因为医生可能会选错
+    @Data
+    @Builder
+    @AllArgsConstructor
+    @NoArgsConstructor
+    public static class H5ssmInfo {
+        private String name;
+        private String signUrl;
+        private String extSignUrl;
+        private Date sendTime;
+    }
+
+
+    private JSONObject ssmData(H5ssmInfo info, String phone) {
+        return Forest.post(systemConfig.getMagicApi() + "/public/sms/sendMessageOne")
+                .addHeader("content-type", "application/json")
+                .addBody(new JSONObject() {{
+                    set("templateId", "mb465551e87fdf4146aa745492c99a2812");
+                    set("key", "zyb5beed2597b243608841cb719b5d4135");
+                    set("data", new JSONArray() {{
+                        add(new JSONObject() {{
+                            set("phone", phone);
+                            set("content", new JSONObject() {{
+                                set("name", info.getName());
+                                set("url", info.getSignUrl());
+                            }});
+                        }});
+                    }});
+                }})
                 .bodyType(ForestDataType.JSON)
-                .execute(String.class);
+                .execute(JSONObject.class);
+    }
+
+    @Data
+    public static class RetrySMSParams {
+        private String phone;
+        private String documentId;
+        private CaSignClass.SignSourceEnum source;
+    }
+
+    public ResultVo<String> retrySMS(RetrySMSParams info) {
+        CaSignData caSignData = caSignDataDao.selectById(CaSignData.getId(info.getDocumentId(), info.getSource()));
+        if (caSignData == null) {
+            return R.fail(ExceptionEnum.NO_DATA_EXIST, "还没有发起签名请求。");
+        } else {
+            if (caSignData.getSignComplete()) {
+                return R.fail(ExceptionEnum.NO_DATA_EXIST, "病历签名完成无法发送。");
+            }
+        }
+
+        JSONObject caParamsValue = JSONUtil.parseObj(caSignData.getValue());
+        H5ssmInfo ssmInfo = caParamsValue.getBean("ssmInfo", H5ssmInfo.class);
+
+        long between = DateUtil.between(DateUtil.date(), ssmInfo.getSendTime(), DateUnit.SECOND);
+
+        int maxSecond = 30;
+
+        if (between <= maxSecond) {
+            return R.fail(ExceptionEnum.ERROR_EL_MESSAGE, StrUtil.format("发送的太频繁了,请【{}】秒后,重试", maxSecond - between));
+        }
+
+        JSONObject ssmRst = ssmData(ssmInfo, info.getPhone());
+        ssmInfo.setSendTime(DateUtil.date());
+
+        caParamsValue.set("ssmInfo", ssmInfo);
+        // 重新更新时间
+        caSignDataDao.updateById(CaSignData.builder()
+                .documentId(caSignData.getDocumentId())
+                .value(caParamsValue.toJSONString(0))
+                .build());
+
+        if (ssmRst.getInt("code") != 0) {
+            return R.fail(ExceptionEnum.LOGICAL_ERROR,
+                    "发送短信失败但是病历已生成,带签名文书" +
+                    ssmRst.getStr("message")
+            );
+        }
+
+        return R.ok(ExceptionEnum.SUCCESS_AND_EL_MESSAGE, "发送成功");
+    }
+
+    @NotNull
+    private CaSignClass.H5Return getStringResultVo(String execute) {
         JSONObject rst = JSONUtil.parseObj(execute);
         String msg = URLUtil.decode(rst.getByPath("ret_msg", String.class));
         if (0 == rst.getByPath("ret_code", Integer.class)) {
-            return ResultVoUtil.success(rst);
+            return CaSignClass.H5Return.builder()
+                    .signUrl(rst.getByPath("sign_url", String.class))
+                    .extSignUrl(rst.getByPath("ext_sign_url", String.class))
+                    .build();
         }
-        return ResultVoUtil.fail(ExceptionEnum.NO_DATA_EXIST, msg);
+        throw new BizException(ExceptionEnum.NO_DATA_EXIST, "签名失败" + msg);
     }
 
-
+    /**
+     * 取消平板的签名
+     *
+     * @param id ca 的唯一id
+     */
     public void cancelSignature(String id) {
         JSONObject ret = new JSONObject();
         CaData.HBoardSign app = caData.getHBoardSign();
@@ -520,16 +637,13 @@ public class CaServer implements Assertion {
         if (caSignData == null) {
             return R(-1, "病历不存在");
         }
-
-        JSONObject appDownload = appDownload(caSignData.getCaId());
-
         CaSignClass.Upload build = CaSignClass.Upload
                 .builder()
                 .patNo(caSignData.getPatNo())
                 .times(caSignData.getTimes())
-                .file(appDownload.getStr("pdf"))
+                .file(data.getStr("pdf"))
                 .fileName(document.replace(caSignData.getSource(), ""))
-                .caData(appDownload.getStr("signed"))
+                .caData(data.getStr("signed", ""))
                 .build();
 
         CaSignData updateData = CaSignData.builder().signComplete(true).documentId(document).build();
@@ -545,6 +659,35 @@ public class CaServer implements Assertion {
         }};
     }
 
+    /**
+     * 这个是下载
+     *
+     * @param bizSn
+     * @return
+     */
+    public JSONObject sealDownload(String bizSn) {
+        JSONObject data = new JSONObject() {{
+            set("api_key", caData.getHBoardSign().getApiKey());
+            set("api_secret", caData.getHBoardSign().getApiSecret());
+            set("data", new JSONObject() {{
+                set("document_no", bizSn);
+            }});
+        }};
+        JSONObject execute = Forest
+                .post(caData.getHBoardSign().getUrl() + "/v2/seal/download")
+                .bodyType(ForestDataType.JSON)
+                .addBody(data.toJSONString(0))
+                .execute(JSONObject.class);
+
+        execute.set("ret_msg", URLUtil.decode(execute.getStr("ret_msg")));
+        log.info("返回:{}", execute);
+
+        if (execute.getInt("ret_code") != 0) {
+            throw new BizException(ExceptionEnum.LOGICAL_ERROR, execute.getStr("ret_msg"));
+        }
+        return execute;
+    }
+
     public JSONObject appDownload(String bizSn) {
         JSONObject data = new JSONObject() {{
             set("api_key", caData.getHBoardSign().getApiKey());
@@ -569,23 +712,22 @@ public class CaServer implements Assertion {
         return execute;
     }
 
-    public String uploadBase64(CaSignClass.Upload upload) {
+    public void uploadBase64(CaSignClass.Upload upload) {
         byte[] file = Base64.decode(upload.getFile());
         String tmpPath = "/" + upload.getPatNo()
                          + "/" + upload.getTimes()
                          + "/emr"
                          + "/" + upload.getFileName();
         String pdfPath = tmpPath + ".pdf";
-        String caPath = "/" + upload.getPatNo()
-                        + "/" + upload.getTimes()
-                        + "/ca/"
-                        + upload.getFileName()
-                        + ".txt";
+//        String caPath = "/" + upload.getPatNo()
+//                        + "/" + upload.getTimes()
+//                        + "/ca/"
+//                        + upload.getFileName()
+//                        + ".txt";
 
         // 写入CA数据
-        FileUtil.writeString(upload.getCaData(), archivePath + caPath, StandardCharsets.UTF_8);
+//        FileUtil.writeString(upload.getCaData(), archivePath + caPath, StandardCharsets.UTF_8);
         FileUtil.writeBytes(file, archivePath + pdfPath);
-        return "/archive" + pdfPath;
     }
 
     public ResultVo<List<PatientIdCardType>> getIdCardTypeList(String patNo) {
@@ -736,4 +878,22 @@ public class CaServer implements Assertion {
     }
 
 
+    private String getSignTypeName(String type) {
+        if (StrUtil.isBlank(type)) {
+            return "朋友";
+        }
+        switch (type) {
+            case "1":
+                return "亲属";
+            case "2":
+                return "患者签名";
+            case "4":
+                return "伴侣";
+            case "3":
+            default:
+                return "朋友";
+        }
+    }
+
+
 }

+ 140 - 179
src/main/java/thyyxxk/webserver/service/zhuyuanyiji/ClinicalPathwayPatientService.java

@@ -1,20 +1,22 @@
 package thyyxxk.webserver.service.zhuyuanyiji;
 
+import cn.hutool.core.date.DateTime;
 import cn.hutool.core.util.StrUtil;
 import cn.hutool.json.JSONArray;
 import cn.hutool.json.JSONObject;
 import cn.hutool.json.JSONUtil;
-import com.baomidou.mybatisplus.core.mapper.BaseMapper;
-import lombok.Data;
-import lombok.RequiredArgsConstructor;
+import com.baomidou.mybatisplus.core.conditions.Wrapper;
+import lombok.*;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.stereotype.Service;
 import thyyxxk.webserver.config.exception.ExceptionEnum;
+import thyyxxk.webserver.dao.his.dictionary.clinicalPathway.ClinicalPathwayDayDao;
 import thyyxxk.webserver.dao.his.zhuyuanyisheng.emr.EmrPatientDao;
 import thyyxxk.webserver.dao.his.zhuyuanyisheng.patientClinicalPathway.ClinicalPathwayPatientDao;
 import thyyxxk.webserver.dao.his.zhuyuanyisheng.patientClinicalPathway.ClinicalPathwayPatientDayLogDao;
 import thyyxxk.webserver.dao.his.zhuyuanyisheng.patientClinicalPathway.ClinicalPathwayPatientWorkLogDao;
 import thyyxxk.webserver.entity.ResultVo;
+import thyyxxk.webserver.entity.dictionary.pathwayTemplates.dto.ClinicalPathwayDay;
 import thyyxxk.webserver.entity.dictionary.pathwayTemplates.dto.ClinicalPathwayTemplates;
 import thyyxxk.webserver.entity.dictionary.pathwayTemplates.dto.ClinicalPathwayWork;
 import thyyxxk.webserver.entity.dictionary.pathwayTemplates.vo.TemplateDayVo;
@@ -29,14 +31,11 @@ import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.vo.Patient
 import thyyxxk.webserver.entity.zhuyuanyisheng.patientClinicalPathway.vo.PatientOrderDayVo;
 import thyyxxk.webserver.enums.ClinicalPathwayPatientState;
 import thyyxxk.webserver.service.dictionary.clinicalPathway.ClinicalPathwayService;
-import thyyxxk.webserver.service.hutoolcache.ClinicalPathwayCache;
-import thyyxxk.webserver.utils.DateUtil;
-import thyyxxk.webserver.utils.ListUtil;
-import thyyxxk.webserver.utils.ResultVoUtil;
-import thyyxxk.webserver.utils.SnowFlakeId;
+import thyyxxk.webserver.utils.*;
 
 import java.util.*;
 import java.util.stream.Collectors;
+import java.util.stream.IntStream;
 
 
 @Service
@@ -46,8 +45,10 @@ public class ClinicalPathwayPatientService {
     private final ClinicalPathwayPatientDao dao;
     private final EmrPatientDao emrPatientDao;
     private final ClinicalPathwayService clinicalPathwayService;
-    private final ClinicalPathwayCache cache;
     private final ClinicalPathwayPatientDayLogDao dayDao;
+    private final ClinicalPathwayDayDao templateDayDao;
+    private final ClinicalPathwayPatientWorkLogDao workLogDao;
+
 
     /**
      * 获取患者的入院诊断来推荐可以进入的临床路径
@@ -175,184 +176,23 @@ public class ClinicalPathwayPatientService {
         return dayLogByPatientNo;
     }
 
-    private Map<String, List<ClinicalPathwayPatientWorkLogVo>> getEmptyMap() {
+    /**
+     * 获取一个包含特定键的空列表的Map
+     *
+     * @return 包含四个键(" zhenliao ", " yzchangqi ", " yzlinshi ", " huli ")且每个键对应的值都是空List的Map
+     */
+    public static Map<String, List<ClinicalPathwayPatientWorkLogVo>> getEmptyMap() {
         Map<String, List<ClinicalPathwayPatientWorkLogVo>> tmpMap = new HashMap<>();
         tmpMap.put("zhenliao", new ArrayList<>());
+        // 向Map中添加四个键值对,键分别为"zhenliao"(治疗)、"yzchangqi"(长期医嘱)、
+        // "yzlinshi"(临时医嘱)和"huli"(护理),每个键对应的值都是一个新的ArrayList实例
         tmpMap.put("yzchangqi", new ArrayList<>());
         tmpMap.put("yzlinshi", new ArrayList<>());
         tmpMap.put("huli", new ArrayList<>());
+        // 返回填充好的Map
         return tmpMap;
     }
 
-    @Data
-    public static class GenerateParams {
-        private List<TemplateDayVo> dayValue;
-        private List<ClinicalPathwayPatientDayLog> execDays;
-        private long betweenDay;
-        private String patNo;
-        private int times;
-        private Date createTime;
-    }
-
-    /**
-     * 判断是否需要生成今天的临床路径
-     * generatePath
-     *
-     * @param patNo 住院号
-     * @param times 住院次数
-     * @return ok
-     */
-    public ResultVo<String> generatePath(String patNo, Integer times) {
-        // 根据住院号和住院次数查询患者临床路径信息
-        ClinicalPathwayPatient patient = dao.selectPatientClinicalPathway(patNo, times);
-        // 如果患者临床路径信息为空,则返回失败信息
-        if (patient == null) {
-            return ResultVoUtil.fail(ExceptionEnum.NO_DATA_EXIST, "患者未入经无法进入下一个日期。");
-        }
-
-        // 如果患者临床路径状态为完成,则返回成功信息
-        if (ClinicalPathwayPatientState.完成.getCode().equals(patient.getState())) {
-            return ResultVoUtil.success(ExceptionEnum.SUCCESS_AND_EL_NOTIFICATION, "患者完成了全部的路径");
-        }
-
-        // 如果不是入径的话就不执行
-        if (!ClinicalPathwayPatientState.入径.getCode().equals(patient.getState())) {
-            return ResultVoUtil.success();
-        }
-
-        Date createTime = patient.getCreateTime();
-        Date now = new Date();
-        // 判断当前时间和入径的时间相差几天
-        long betweenDay = DateUtil.betweenDay(now, createTime, true);
-        List<ClinicalPathwayPatientDayLog> execDays = dao.selectExecDay(patNo, times, patient.getTemplateId(), DateUtil.formatDate(patient.getCreateTime(), DateUtil.DATE));
-        int execDay = execDays.size();
-
-        // 如果一次都没执行的话就判断一下有无上一次入径
-        if (execDay == 0) {
-            checkPatientPathway(patNo, times);
-        }
-        // 判断已经执行了几天和这个模板需要执行几天,如果时间一样的话就说明完成了临床路径,如果是第三天的话就需要多点一次了
-        if (execDay == dao.execDayByTemplateId(patient.getTemplateId())) {
-            ClinicalPathwayPatient updateParams = new ClinicalPathwayPatient();
-            updateParams.setId(patient.getId());
-            updateParams.setState(ClinicalPathwayPatientState.完成.getCode());
-            dao.updateById(updateParams);
-            // 完成了临床路径
-            return ResultVoUtil.success(ExceptionEnum.SUCCESS_AND_EL_NOTIFICATION, "患者完成了全部的路径");
-        }
-
-        List<TemplateDayVo> templateDay = cache.getTemplateDayNotContent(patient.getTemplateId(), () -> clinicalPathwayService.getTemplateDay(patient.getTemplateId()));
-
-        GenerateParams params = new GenerateParams();
-        params.setBetweenDay(betweenDay + 1);
-        params.setDayValue(templateDay);
-        params.setExecDays(execDays);
-        params.setPatNo(patNo);
-        params.setTimes(times);
-        params.setCreateTime(patient.getCreateTime());
-        whatDayDoesItNeedToGenerate(params);
-        return ResultVoUtil.success();
-    }
-
-    public void checkPatientPathway(String patNo, Integer times) {
-        // 根据patNo和times查询患者信息
-        List<ClinicalPathwayPatient> patients = dao.selectPatientCount(patNo, times);
-        // 如果患者信息只有一个,则直接返回
-        if (patients.size() == 1) {
-            return;
-        }
-        // 获取患者信息
-        ClinicalPathwayPatient patient = patients.get(0);
-        // 获取患者创建时间
-        Date createTime = patient.getCreateTime();
-        // 获取当前时间
-        Date now = new Date();
-        // 执行几天了
-        long betweenDay = DateUtil.betweenDay(createTime, now, true);
-        log.info("判断是否需要删除一天:{}", betweenDay);
-    }
-
-    public void whatDayDoesItNeedToGenerate(GenerateParams params) {
-        List<TemplateDayVo> tmpDay = new ArrayList<>();
-        for (TemplateDayVo item : params.getDayValue()) {
-            for (int i = 0; i < item.getExecutionDay(); i++) {
-                tmpDay.add(item);
-            }
-        }
-        int size = params.getExecDays().size();
-        // 应该需要生成几天的
-        for (int i = 0; i < params.getBetweenDay(); i++) {
-            Date createTime = DateUtil.addNaturalDays(params.getCreateTime(), i + 1);
-            // 当前的天数,小于患者指定生成的天数的话就需要生成
-            if (i > size - 1) {
-                TemplateDayVo templateDayVo = tmpDay.get(i);
-                String id = generateDays(templateDayVo, params, createTime);
-                generateWorks(templateDayVo, params, id);
-            }
-        }
-    }
-
-    /**
-     * 生成这一天的
-     *
-     * @param value
-     * @param params
-     */
-    public String generateDays(TemplateDayVo value, GenerateParams params, Date createTime) {
-        ClinicalPathwayPatientDayLog day = new ClinicalPathwayPatientDayLog();
-        day.setId(SnowFlakeId.instance().nextId());
-        day.setDayId(value.getId());
-        day.setPatNo(params.getPatNo());
-        day.setTimes(params.getTimes());
-        day.setState(ClinicalPathwayPatientState.入径.getCode());
-        day.setTemplateId(value.getTemplateId());
-        day.setExecDate(DateUtil.beginOfDay(createTime));
-        dayDao.insert(day);
-        return day.getId();
-    }
-
-    /**
-     * 生成工作内容
-     *
-     * @param value
-     * @param params
-     */
-    public void generateWorks(TemplateDayVo value, GenerateParams params, String id) {
-        // 创建一个ClinicalPathwayPatientWorkLog的列表
-        List<ClinicalPathwayPatientWorkLog> insertData = new ArrayList<>();
-        // 遍历value的execute属性
-        for (Map.Entry<String, List<ClinicalPathwayWork>> item : value.getExecute().entrySet()) {
-            // 获取execute属性的值
-            List<ClinicalPathwayWork> value1 = item.getValue();
-            // 遍历execute属性的值
-            for (ClinicalPathwayWork clinicalPathwayWork : value1) {
-                // 创建一个ClinicalPathwayPatientWorkLog对象
-                ClinicalPathwayPatientWorkLog work = new ClinicalPathwayPatientWorkLog();
-                // 设置id
-                work.setId(SnowFlakeId.instance().nextId());
-                // 设置dayId
-                work.setDayId(id);
-                // 判断key是否为huli或zhenliao
-                if (item.getKey().equals("huli") || item.getKey().equals("zhenliao")) {
-                    // 设置complete为1
-                    work.setComplete(1);
-                } else {
-                    // 设置complete为0
-                    work.setComplete(0);
-                }
-                // 设置patNo
-                work.setPatNo(params.getPatNo());
-                // 设置times
-                work.setTimes(params.getTimes());
-                // 设置contentId
-                work.setContentId(clinicalPathwayWork.getId());
-                // 将work对象添加到insertData列表中
-                insertData.add(work);
-            }
-        }
-        // 批量插入insertData列表中的数据
-        ListUtil.batchList(insertData, ClinicalPathwayPatientWorkLogDao.class, BaseMapper::insert);
-    }
 
     public ResultVo<String> updatePatientDay(UpdatePatientDayReq params) {
         ClinicalPathwayPatientDayLog dayLog = new ClinicalPathwayPatientDayLog();
@@ -393,4 +233,125 @@ public class ClinicalPathwayPatientService {
     }
 
 
+    /**
+     * 患者继续执行当前的路径
+     *
+     * @param patNo 住院号
+     * @param times 住院次数
+     * @param next  是否是下一天
+     * @return 提示
+     */
+    public ResultVo<String> continueExecution(String patNo, Integer times, boolean next) {
+        // 患者的当前路径
+        ClinicalPathwayPatient currentPath = dao.selectPatientClinicalPathway(patNo, times);
+        if (currentPath == null) {
+            return R.ok(ExceptionEnum.LOGICAL_ERROR, "患者还没有入径无法点击。");
+        }
+        // 获取当前患者的
+        ClinicalPathwayPatientDayLog currentDay = dayDao.getCurrentPatientWorkLog(whereCurrentDay(currentPath));
+        // 如果是空的话就说明是第一天,就需要用模板的第一天的数据
+        String dayId = currentDay == null ? dayDao.getTheFirstDay(currentPath.getTemplateId()) : currentDay.getDayId();
+        // 如果是进入到下一个阶段,且不是第一次点击的话就能进入到下一个阶段,因为必须执行第一天的东西
+        if (next && currentDay != null) {
+            List<ClinicalPathwayDay> clinicalPathwayDays = templateDayDao.selectList(ClinicalPathwayDay
+                    .lambdaQueryWrapper()
+                    .eq(ClinicalPathwayDay::getTemplateId, currentPath.getTemplateId())
+                    .orderByDesc(ClinicalPathwayDay::getSort)
+            );
+            if (ListUtil.isBlank(clinicalPathwayDays)) {
+                return R.ok(ExceptionEnum.LOGICAL_ERROR, "没有下一个阶段了。");
+            }
+
+            String finalDayId = dayId;
+            int currentDayIndex = IntStream.range(0, clinicalPathwayDays.size())
+                    .filter(i -> clinicalPathwayDays.get(i).getId().equals(finalDayId))
+                    .findFirst()
+                    .orElse(-1);
+
+            if (currentDayIndex == -1) {
+                return R.ok(ExceptionEnum.LOGICAL_ERROR, "找不到下一个阶段。");
+            }
+            try {
+                ClinicalPathwayDay clinicalPathwayDay = clinicalPathwayDays.get(currentDayIndex - 1);
+                dayId = clinicalPathwayDay.getId();
+            } catch (Exception e) {
+                return R.ok(ExceptionEnum.LOGICAL_ERROR, "找不到下一个阶段。");
+            }
+        }
+        generateDayByDayId(new GenerateDayByDayIdParams(dayId, patNo, times));
+        return R.ok();
+    }
+
+
+    private Wrapper<ClinicalPathwayPatientDayLog> whereCurrentDay(ClinicalPathwayPatient currentPath) {
+        return ClinicalPathwayPatientDayLog.lambdaQueryWrapper()
+                .eq(ClinicalPathwayPatientDayLog::getPatNo, currentPath.getPatNo())
+                .eq(ClinicalPathwayPatientDayLog::getTimes, currentPath.getTimes())
+                .eq(ClinicalPathwayPatientDayLog::getTemplateId, currentPath.getTemplateId())
+                .orderByDesc(ClinicalPathwayPatientDayLog::getCreateTime);
+    }
+
+    @Data
+    @Builder
+    @AllArgsConstructor
+    @NoArgsConstructor
+    public static class GenerateDayByDayIdParams {
+        private String dayId;
+        private String patNo;
+        private Integer times;
+    }
+
+    public void generateDayByDayId(GenerateDayByDayIdParams params) {
+        ClinicalPathwayDay clinicalPathwayDay = templateDayDao.selectById(params.getDayId());
+        if (clinicalPathwayDay == null) {
+            throw new RuntimeException("当前天数已经被删除了,请重新入径。");
+        }
+        DateTime now = DateUtil.date();
+
+        String tokenUserId = TokenUtil.getInstance().getTokenUserId();
+
+        ClinicalPathwayPatientDayLog dayData = ClinicalPathwayPatientDayLog
+                .builder()
+                .id(SnowFlakeId.instance().nextId())
+                .dayId(clinicalPathwayDay.getId())
+                .createCode(tokenUserId)
+                .createTime(now)
+                .patNo(params.getPatNo())
+                .times(params.getTimes())
+                .state(0)
+                .templateId(clinicalPathwayDay.getTemplateId())
+                .execDate(now)
+                .build();
+
+        List<ClinicalPathwayWork> clinicalPathwayWorks = dao.selectWorkByDayId(clinicalPathwayDay.getId());
+
+        List<ClinicalPathwayPatientWorkLog> patWorkLog = new ArrayList<>();
+
+        clinicalPathwayWorks.forEach(item -> {
+            patWorkLog.add(new ClinicalPathwayPatientWorkLog(
+                    SnowFlakeId.instance().nextId(),
+                    dayData.getId(),
+                    completeValue(item.getExecType()),
+                    tokenUserId,
+                    DateUtil.date(),
+                    item.getId(),
+                    null,
+                    params.getPatNo(),
+                    params.getTimes()
+            ));
+        });
+
+        dayDao.insert(dayData);
+        workLogDao.insert(patWorkLog);
+    }
+
+    private Integer completeValue(Integer type) {
+        if (type == null) {
+            return 0;
+        }
+
+        ClinicalPathwayWork.WorkType byCode = ClinicalPathwayWork.WorkType.getByCode(type);
+        return byCode == null ? 0 : byCode.getComplete();
+    }
+
 }

+ 1 - 1
src/main/java/thyyxxk/webserver/service/zhuyuanyisheng/emr/EmrServer.java

@@ -990,7 +990,7 @@ public class EmrServer {
             String[] split = text.substring(text.lastIndexOf("<br/>buffer:,") + 13).split(",");
             return Base64.encode(Convert.toPrimitiveByteArray(split));
         }
-        throw new RuntimeException(text);
+        throw new RuntimeException("生成pdf错误" + text);
     }
 
     public static String getPdfBase(String documentId) {