فهرست منبع

处方PDF生成

yjwang 1 هفته پیش
والد
کامیت
435b6e673b

+ 57 - 4
fs-admin/src/main/java/com/fs/hisStore/controller/FsStoreHospital580PrescriptionScrmController.java

@@ -4,14 +4,24 @@ import com.fs.common.core.controller.BaseController;
 import com.fs.common.core.domain.R;
 import com.fs.common.core.page.TableDataInfo;
 import com.fs.hisStore.facade.FsStore580FacadeService;
+import com.fs.hospital580.param.PrescriptionPdfParam;
 import com.fs.hospital580.vo.PrescriptionAdminQueryVo;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.http.HttpHeaders;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.MediaType;
+import org.springframework.http.ResponseEntity;
 import org.springframework.security.access.prepost.PreAuthorize;
-import org.springframework.web.bind.annotation.GetMapping;
-import org.springframework.web.bind.annotation.PathVariable;
-import org.springframework.web.bind.annotation.RequestMapping;
-import org.springframework.web.bind.annotation.RestController;
+import org.springframework.web.bind.annotation.*;
+
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.net.URLEncoder;
+import java.nio.charset.StandardCharsets;
+import java.util.List;
 
 /**
  * 处方相关接口
@@ -23,6 +33,7 @@ public class FsStoreHospital580PrescriptionScrmController extends BaseController
     @Autowired
     private FsStore580FacadeService facadeService;
 
+
     /**
      * 处方订单列表
      */
@@ -50,4 +61,46 @@ public class FsStoreHospital580PrescriptionScrmController extends BaseController
     public R chatDetail(@PathVariable("preId") Long preId) {
         return R.ok(facadeService.chatDetail(preId));
     }
+
+
+    /**
+     * 批量导出PDF接口
+     * @param param 包含需要导出的ID列表等参数
+     * @return 二进制文件流响应
+     */
+    @PostMapping("/downloadMedicalPdf")
+    public ResponseEntity<byte[]> downloadMedicalPdf(@RequestBody PrescriptionPdfParam param) {
+        if (param == null || param.getIds() == null || param.getIds().isEmpty()) {
+            return new ResponseEntity<>(HttpStatus.BAD_REQUEST);
+        }
+        try {
+            ByteArrayOutputStream pdfStream = facadeService.generatePdf(param);
+            if (pdfStream == null) {
+                return new ResponseEntity<>(HttpStatus.NO_CONTENT);
+            }
+            byte[] pdfBytes = pdfStream.toByteArray();
+            if (pdfBytes.length < 1024) {
+                return new ResponseEntity<>(HttpStatus.NO_CONTENT);
+            }
+
+            HttpHeaders headers = new HttpHeaders();
+            String downloadFileName = "医疗记录_" + System.currentTimeMillis() + ".pdf";
+            String encodedFileName = URLEncoder.encode(downloadFileName, StandardCharsets.UTF_8.name());
+
+            headers.setContentDispositionFormData("attachment", encodedFileName);
+            headers.setContentType(MediaType.APPLICATION_PDF);
+            headers.setContentLength(pdfBytes.length);
+            headers.setCacheControl("no-cache, no-store, must-revalidate");
+            headers.setPragma("no-cache");
+            headers.setExpires(0);
+
+            return new ResponseEntity<>(pdfBytes, headers, HttpStatus.OK);
+        } catch (IOException e) {
+            log.error("PDF下载IO异常", e);
+            return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
+        } catch (Exception e) {
+            log.error("PDF下载异常", e);
+            return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
+        }
+    }
 }

+ 9 - 0
fs-admin/src/main/java/com/fs/hisStore/facade/FsStore580FacadeService.java

@@ -1,10 +1,12 @@
 package com.fs.hisStore.facade;
 
 import com.fs.hospital580.entity.Hospital580PrescriptionScrmEntity;
+import com.fs.hospital580.param.PrescriptionPdfParam;
 import com.fs.hospital580.vo.OrderChatScrmVo;
 import com.fs.hospital580.vo.PrescriptionAdminQueryVo;
 import com.fs.hospital580.vo.PrescriptionAdminScrmVo;
 
+import java.io.ByteArrayOutputStream;
 import java.util.List;
 
 public interface FsStore580FacadeService {
@@ -13,4 +15,11 @@ public interface FsStore580FacadeService {
     PrescriptionAdminScrmVo prescriptionDetail(Long preId);
 
     List<OrderChatScrmVo> chatDetail(Long preId);
+
+    /**
+     * 批量导出PDF接口
+     * @param param 包含需要导出的ID列表等参数
+     * @return ByteArrayOutputStream
+     */
+    ByteArrayOutputStream generatePdf(PrescriptionPdfParam param);
 }

+ 337 - 3
fs-admin/src/main/java/com/fs/hisStore/facade/impl/FsStore580FacadeServiceImpl.java

@@ -1,28 +1,42 @@
 package com.fs.hisStore.facade.impl;
 
 import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.io.resource.ClassPathResource;
 import cn.hutool.core.util.ObjectUtil;
 import cn.hutool.json.JSONArray;
 import cn.hutool.json.JSONObject;
 import cn.hutool.json.JSONUtil;
+import com.alibaba.fastjson.JSON;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.fs.hisStore.facade.FsStore580FacadeService;
 import com.fs.hospital580.entity.Hospital580PrescriptionAnswerScrmEntity;
 import com.fs.hospital580.entity.Hospital580PrescriptionChatScrmEntity;
 import com.fs.hospital580.entity.Hospital580PrescriptionMedicineScrmEntity;
 import com.fs.hospital580.entity.Hospital580PrescriptionScrmEntity;
+import com.fs.hospital580.param.PrescriptionPdfParam;
 import com.fs.hospital580.service.Hospital580PrescriptionAnswerScrmService;
 import com.fs.hospital580.service.Hospital580PrescriptionChatScrmService;
 import com.fs.hospital580.service.Hospital580PrescriptionMedicineScrmService;
 import com.fs.hospital580.service.Hospital580PrescriptionScrmService;
 import com.fs.hospital580.vo.*;
+import com.itextpdf.text.*;
+import com.itextpdf.text.pdf.BaseFont;
+import com.itextpdf.text.pdf.PdfPCell;
+import com.itextpdf.text.pdf.PdfPTable;
+import com.itextpdf.text.pdf.PdfWriter;
+import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
-import java.util.Collections;
+import javax.net.ssl.HttpsURLConnection;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.*;
+import java.text.SimpleDateFormat;
+import java.time.format.DateTimeFormatter;
+import java.util.*;
 import java.util.List;
-import java.util.Objects;
-import java.util.Optional;
 import java.util.stream.Collectors;
 
 @Service("fsStore580FacadeService")
@@ -37,6 +51,8 @@ public class FsStore580FacadeServiceImpl implements FsStore580FacadeService {
     @Autowired
     private Hospital580PrescriptionMedicineScrmService medicineScrmService;
 
+    private static final DateTimeFormatter DATE_FORMAT = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm");
+    private static final ClassPathResource FONT_RESOURCE = new ClassPathResource("fonts/SimHei.ttf");
 
     @Override
     public List<Hospital580PrescriptionScrmEntity> list(PrescriptionAdminQueryVo vo) {
@@ -88,4 +104,322 @@ public class FsStore580FacadeServiceImpl implements FsStore580FacadeService {
                         .collect(Collectors.toList()))
                 .orElse(Collections.emptyList());
     }
+
+    @Override
+    public ByteArrayOutputStream generatePdf(PrescriptionPdfParam param) {
+        //获取需要下载咨询的列表信息
+        List<Hospital580PrescriptionScrmEntity> hospital580PrescriptionScrmEntityList=prescriptionScrmService.list(new LambdaQueryWrapper<Hospital580PrescriptionScrmEntity>().in(Hospital580PrescriptionScrmEntity::getPreId,param.getIds()));
+        if(!hospital580PrescriptionScrmEntityList.isEmpty()){
+            //获取对应聊天记录信息
+           List<Hospital580PrescriptionChatScrmEntity> chatScrmEntityList = chatScrmService.list(new LambdaQueryWrapper<Hospital580PrescriptionChatScrmEntity>().select(Hospital580PrescriptionChatScrmEntity::getContent,Hospital580PrescriptionChatScrmEntity::getPreId).in(Hospital580PrescriptionChatScrmEntity::getPreId,param.getIds()));
+            Map<Long,List<ChatMessageVo>> messageMap = null;
+           if(!chatScrmEntityList.isEmpty()){
+               //转换消息
+               List<ChatMessageVo> chatMessageVoList = chatScrmEntityList.stream()
+                       .flatMap(c -> {
+                           Long preId = c.getPreId();
+                           return JSON.parseArray(c.getContent(), ChatMessageVo.class)
+                                   .stream()
+                                   .peek(vo -> vo.setPreId(preId));
+                       })
+                       .collect(Collectors.toList());
+               messageMap = chatMessageVoList.stream()
+                       .collect(Collectors.groupingBy(ChatMessageVo::getPreId));
+           }
+            return combinedPdf(hospital580PrescriptionScrmEntityList,messageMap);
+        }
+        return null;
+    }
+
+    //组合pdf格式
+    public ByteArrayOutputStream combinedPdf(List<Hospital580PrescriptionScrmEntity> entityList, Map<Long, List<ChatMessageVo>> messageMap) {
+        ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
+        Document document = new Document(PageSize.A4, 40, 40, 50, 50);
+        try {
+          PdfWriter.getInstance(document, outputStream);
+            document.open();
+            int pageNum=0;
+            for (Hospital580PrescriptionScrmEntity h : entityList) {
+                List<ChatMessageVo> messages = messageMap.getOrDefault(h.getPreId(), Collections.emptyList());
+                generateToDocument(h, document, messages,pageNum);
+                pageNum++;
+            }
+        } catch (Exception e) {
+            e.printStackTrace();
+            throw new RuntimeException("PDF合并失败", e);
+        } finally {
+            if (document.isOpen()) {
+                document.close();
+            }
+        }
+        return outputStream;
+    }
+
+    /**
+     * 重构:仅向现有文档添加内容,不返回document,不关闭任何资源
+     */
+    private void generateToDocument(Hospital580PrescriptionScrmEntity entity, Document document, List<ChatMessageVo> messageList,Integer pageNum) throws DocumentException, IOException {
+        if(pageNum > 0){
+            document.newPage();
+        }
+        BaseFont baseFont = BaseFont.createFont(FONT_RESOURCE.getPath(), BaseFont.IDENTITY_H, BaseFont.EMBEDDED);
+        Font titleFont = new Font(baseFont, 18, Font.BOLD, BaseColor.BLACK);
+        Font tableKeyFont = new Font(baseFont, 11, Font.BOLD, BaseColor.DARK_GRAY);
+        Font tableValueFont = new Font(baseFont, 11, Font.NORMAL, BaseColor.BLACK);
+        Font subTitleFont = new Font(baseFont, 14, Font.BOLD, BaseColor.DARK_GRAY);
+        Font msgFont = new Font(baseFont, 10, Font.NORMAL, BaseColor.BLACK);
+
+        //------------每条处方首页-----
+        Paragraph title = new Paragraph("问诊处方信息表", titleFont);
+        title.setAlignment(Element.ALIGN_CENTER);
+        title.setSpacingAfter(30);
+        document.add(title);
+
+        Map<String, String> dataMap = convertEntityData(entity);
+        PdfPTable table = new PdfPTable(2);
+        table.setWidthPercentage(90);
+        table.setHorizontalAlignment(Element.ALIGN_CENTER);
+        table.setSpacingBefore(10);
+        table.setSpacingAfter(20);
+        table.setWidths(new float[]{1f, 2f});
+
+        for (Map.Entry<String, String> entry : dataMap.entrySet()) {
+            PdfPCell keyCell = new PdfPCell(new Phrase(entry.getKey(), tableKeyFont));
+            keyCell.setPadding(8);
+            keyCell.setBackgroundColor(new BaseColor(240, 240, 240));
+            keyCell.setBorder(Rectangle.BOX);
+
+            PdfPCell valueCell = new PdfPCell(new Phrase(entry.getValue(), tableValueFont));
+            valueCell.setPadding(8);
+            valueCell.setBorder(Rectangle.BOX);
+
+            table.addCell(keyCell);
+            table.addCell(valueCell);
+        }
+        document.add(table);
+
+
+        //-----------生成图片------------------
+        if (entity.getDstFilePath() != null) {
+            try {
+                document.newPage();
+                Paragraph pageBreakPlaceholder = new Paragraph(" ", tableValueFont);
+                pageBreakPlaceholder.setSpacingAfter(10);
+                document.add(pageBreakPlaceholder);
+                Image image = loadImageFromUrl(entity.getDstFilePath());
+                if (image != null) {
+                    scaleImageToFitPage(image, document);
+                    image.setAlignment(Element.ALIGN_CENTER);
+                    document.add(image);
+                } else {
+                    Paragraph errorMsg = new Paragraph("无法加载处方图片", msgFont);
+                    errorMsg.setAlignment(Element.ALIGN_CENTER);
+                    document.add(errorMsg);
+                }
+            } catch (Exception e) {
+                Paragraph errorMsg = new Paragraph("图片处理失败: " + e.getMessage(), msgFont);
+                errorMsg.setAlignment(Element.ALIGN_CENTER);
+                document.add(errorMsg);
+            }
+        }
+
+        //------------聊天页-----------------
+        document.newPage();
+
+        Paragraph msgTitle = new Paragraph("沟通记录", subTitleFont);
+        msgTitle.setAlignment(Element.ALIGN_CENTER);
+        msgTitle.setSpacingAfter(20);
+        document.add(msgTitle);
+
+        // 对话框表格
+        PdfPTable chatTable = new PdfPTable(1);
+        chatTable.setWidthPercentage(90);
+        chatTable.setHorizontalAlignment(Element.ALIGN_CENTER);
+        chatTable.setSpacingAfter(20);
+
+        if (messageList.isEmpty()) {
+            PdfPCell emptyCell = new PdfPCell(new Phrase("无沟通记录", msgFont));
+            emptyCell.setBorder(Rectangle.NO_BORDER);
+            emptyCell.setHorizontalAlignment(Element.ALIGN_CENTER);
+            emptyCell.setPadding(10);
+            chatTable.addCell(emptyCell);
+        } else {
+            for (ChatMessageVo msg : messageList) {
+                PdfPCell msgCell = new PdfPCell();
+                msgCell.setBorder(Rectangle.NO_BORDER);
+                msgCell.setPadding(5);
+
+                Paragraph content = new Paragraph();
+                String sender = msg.getTarget() == 2 ? "医生" : "患者";
+                Chunk senderChunk = new Chunk("【" + sender + "】", new Font(baseFont, 10, Font.BOLD, BaseColor.DARK_GRAY));
+                content.add(senderChunk);
+
+                Chunk timeChunk = new Chunk(":" + timestampToDate(msg.getCreatedTime()) + "\n\n", new Font(baseFont, 10, Font.NORMAL, new BaseColor(100, 100, 100)));
+                content.add(timeChunk);
+
+                //type=3的药品信息
+                String msgContent;
+                if (msg.getType() == 3) {
+                    msgContent = parseMedicineContent(msg.getContent());
+                } else {
+                    msgContent = msg.getContent().replaceAll("<br />", "\n").replaceAll("<br>", "\n");
+                }
+
+                Chunk contentChunk = new Chunk(msgContent, msgFont);
+                content.add(contentChunk);
+
+                if (msg.getTarget() == 2) {
+                    msgCell.setHorizontalAlignment(Element.ALIGN_LEFT);
+                    msgCell.setBackgroundColor(new BaseColor(245, 245, 245));
+                } else {
+                    msgCell.setHorizontalAlignment(Element.ALIGN_RIGHT);
+                    msgCell.setBackgroundColor(new BaseColor(220, 235, 255));
+                }
+
+                msgCell.setPadding(10);
+                msgCell.setBorderWidth(1);
+                msgCell.setBorderColor(BaseColor.LIGHT_GRAY);
+                msgCell.setPhrase(content);
+                chatTable.addCell(msgCell);
+            }
+        }
+        document.add(chatTable);
+    }
+
+    private Map<String, String> convertEntityData(Hospital580PrescriptionScrmEntity entity) {
+        Map<String, String> dataMap = new HashMap<>(20);
+        dataMap.put("处方编号", StringUtils.defaultString(entity.getSerialNo(), "无"));
+        dataMap.put("用户ID", entity.getUserId() == null ? "无" : entity.getUserId().toString());
+        dataMap.put("创建时间", entity.getCreateTime() == null ? "无" : entity.getCreateTime().format(DATE_FORMAT));
+        dataMap.put("就诊人姓名", StringUtils.defaultString(entity.getUserFamilyName(), "无"));
+        dataMap.put("性别", convertGender(entity.getUserFamilyGender()));
+        dataMap.put("年龄", entity.getUserFamilyAge() == null ? "无" : entity.getUserFamilyAge().toString());
+        dataMap.put("身份证号", StringUtils.defaultString(entity.getUserFamilyIdCard(), "无"));
+        dataMap.put("联系电话", StringUtils.defaultString(entity.getUserFamilyPhone(), "无"));
+        dataMap.put("家庭住址", StringUtils.defaultString(entity.getUserFamilyAddr(), "无"));
+        dataMap.put("医生姓名", StringUtils.defaultString(entity.getDoctorName(), "无"));
+        dataMap.put("所属科室", StringUtils.defaultString(entity.getDoctorOffice(), "无"));
+        dataMap.put("开方时间", entity.getCreatedTime() == null ? "无" : entity.getCreatedTime().format(DATE_FORMAT));
+        dataMap.put("服务类型", convertServiceType(entity.getServiceType()));
+        dataMap.put("处方状态", convertStatus(entity.getStatus()));
+        dataMap.put("审核状态", convertAuditStatus(entity.getAuditStatus()));
+        dataMap.put("审方药师", StringUtils.defaultString(entity.getAuditApothecaryName(), "无"));
+        dataMap.put("医院名称", StringUtils.defaultString(entity.getHospitalName(), "无"));
+        dataMap.put("药店名称", StringUtils.defaultString(entity.getStoreName(), "无"));
+        dataMap.put("诊断标签", StringUtils.defaultString(entity.getTags(), "无"));
+        return dataMap;
+    }
+
+    private String convertGender(Byte gender) {
+        return gender == null ? "无" : (gender == 1 ? "男" : "女");
+    }
+
+    private String convertServiceType(Byte type) {
+        return type == null ? "无" : (type == 0 ? "图文" : "视频");
+    }
+
+    private String convertStatus(Byte status) {
+        return status == null ? "无" : (status == 1 ? "正常" : "已作废");
+    }
+
+    private String convertAuditStatus(Integer status) {
+        if (status == null) return "无";
+        switch (status) {
+            case 1: return "待审核";
+            case 2: return "审核通过";
+            case 3: return "审核不通过";
+            default: return "未知";
+        }
+    }
+
+    private String timestampToDate(Long timestamp) {
+        Date date = new Date(timestamp);
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm");
+        sdf.setTimeZone(TimeZone.getTimeZone("Asia/Shanghai"));
+        return sdf.format(date);
+    }
+
+    /**
+     * 解析type=3的药品信息JSON字符串,返回格式化文本
+     */
+    private String parseMedicineContent(String content) {
+        try {
+            cn.hutool.json.JSONObject jsonObj = JSONUtil.parseObj(content);
+            cn.hutool.json.JSONArray medicineList = jsonObj.getJSONArray("list");
+
+            if (medicineList.isEmpty()) {
+                return "无具体药品信息";
+            }
+
+            StringBuilder sb = new StringBuilder("处方药品清单:\n");
+            for (int i = 0; i < medicineList.size(); i++) {
+                cn.hutool.json.JSONObject medicine = medicineList.getJSONObject(i);
+                String productName = medicine.getStr("productName", "未知药品");
+                String spec = medicine.getStr("spec", "无");
+                int number = medicine.getInt("number", 0);
+                String usageHowto = medicine.getStr("usageHowto", "无");
+                String frequency = medicine.getStr("frequency", "无");
+                String packingSpec= medicine.getStr("packingSpec", "无");
+                String perDosageNumber =  medicine.getStr("perDosageNumber", "无");
+                String perDosageUnit =  medicine.getStr("perDosageUnit", "无");
+
+                sb.append(String.format("%d. %s\n", i + 1, productName + "(" +packingSpec+")"));
+                sb.append(String.format("   规格用法:%s\n", spec));
+                sb.append(String.format("   服用方式:%s,%s\n", usageHowto, frequency));
+                sb.append(String.format("   数量:%d盒\n", number));
+                sb.append(String.format("   每次:%s%s\n", perDosageNumber, perDosageUnit));
+                sb.append("\n");
+            }
+            return sb.toString();
+        } catch (Exception e) {
+            e.printStackTrace();
+            return "药品信息解析失败";
+        }
+    }
+
+    //图片调整
+    private void scaleImageToFitPage(Image image, Document document) {
+        float pageWidth = document.getPageSize().getWidth() - document.leftMargin() - document.rightMargin();
+        float pageHeight = document.getPageSize().getHeight() - document.topMargin() - document.bottomMargin() - 50; // 预留50pt空白,避免贴边
+        float imageWidth = image.getWidth();
+        float imageHeight = image.getHeight();
+
+        float widthRatio = pageWidth / imageWidth;
+        float heightRatio = pageHeight / imageHeight;
+        float scaleRatio = Math.min(widthRatio, heightRatio);
+
+        if (scaleRatio < 1.0) {
+            image.scalePercent(scaleRatio * 100);
+        }
+        image.setAlignment(Image.ALIGN_CENTER);
+    }
+
+    /**
+     *URL加载图片
+     */
+    private Image loadImageFromUrl(String imageUrl) throws IOException, BadElementException {
+        try {
+            URL url = new URL(imageUrl);
+            URLConnection connection = url.openConnection();
+            connection.setConnectTimeout(10000);
+            connection.setReadTimeout(30000);
+
+            try (InputStream inputStream = connection.getInputStream()) {
+                ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
+                byte[] buffer = new byte[4096];
+                int bytesRead;
+                while ((bytesRead = inputStream.read(buffer)) != -1) {
+                    outputStream.write(buffer, 0, bytesRead);
+                }
+                byte[] imageBytes = outputStream.toByteArray();
+                return Image.getInstance(imageBytes);
+            }
+        } catch (MalformedURLException e) {
+            throw new IOException("图片URL格式错误: " + imageUrl, e);
+        } catch (SocketTimeoutException e) {
+            throw new IOException("图片下载超时: " + imageUrl, e);
+        } catch (Exception e) {
+            throw new IOException("无法加载图片: " + imageUrl, e);
+        }
+    }
 }

+ 1 - 1
fs-admin/src/main/resources/application.yml

@@ -4,7 +4,7 @@ server:
 # Spring配置
 spring:
   profiles:
-    active: druid-jnmy-test
+    active: dev-yjb
 #    active: druid-hdt
 #    active: druid-yzt
 #    active: druid-sxjz

+ 6 - 0
fs-service/pom.xml

@@ -291,6 +291,12 @@
             <version>1.1.26</version>
         </dependency>
 
+        <!-- pdf -->
+        <dependency>
+            <groupId>com.itextpdf</groupId>
+            <artifactId>itextpdf</artifactId>
+            <version>5.5.13.3</version>
+        </dependency>
     </dependencies>
 
 </project>

+ 17 - 0
fs-service/src/main/java/com/fs/hospital580/param/PrescriptionPdfParam.java

@@ -0,0 +1,17 @@
+package com.fs.hospital580.param;
+
+import lombok.Data;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * pdf批量下载接收
+ * **/
+@Data
+public class PrescriptionPdfParam implements Serializable {
+    /***
+     * 批量下载pdfId
+     * **/
+    private List<Long> ids;
+}

+ 19 - 0
fs-service/src/main/java/com/fs/hospital580/vo/ChatMessageVo.java

@@ -0,0 +1,19 @@
+package com.fs.hospital580.vo;
+
+import lombok.Data;
+
+import java.io.Serializable;
+
+@Data
+public class ChatMessageVo implements Serializable {
+    //聊天信息
+    private String content;
+    //角色1:患者 2医生
+    private Integer target;
+    //消息日期
+    private Long createdTime;
+    //处方id
+    private Long preId;
+    //消息类型
+    private Integer type;
+}

BIN
fs-service/src/main/resources/fonts/SimHei.ttf