From 4e2097fc7b8757f935981349a0265d6f278c297a Mon Sep 17 00:00:00 2001 From: wangjian963 <15215920+aprilry@user.noreply.gitee.com> Date: Wed, 15 Apr 2026 14:50:14 +0800 Subject: [PATCH] =?UTF-8?q?=20=20fixbug326,329,334,368:=20=E9=97=A8?= =?UTF-8?q?=E8=AF=8A=E5=8C=BB=E7=94=9F=E7=AB=99=E6=A3=80=E9=AA=8C=E7=94=B3?= =?UTF-8?q?=E8=AF=B7=E6=A8=A1=E5=9D=97=E5=A4=9A=E9=A1=B9=E7=BC=BA=E9=99=B7?= =?UTF-8?q?=E4=BF=AE=E5=A4=8D=20=20=20Bug=20#326:=20=E6=A3=80=E9=AA=8C?= =?UTF-8?q?=E7=94=B3=E8=AF=B7=E5=8D=95=E5=A5=97=E9=A4=90=E9=A1=B9=E7=9B=AE?= =?UTF-8?q?=E5=9B=9E=E5=85=85=E6=95=B0=E6=8D=AE=E4=B8=8D=E5=AE=8C=E6=95=B4?= =?UTF-8?q?=20=20=20-=20=E5=90=8E=E7=AB=AF=E5=9B=9E=E5=85=85=E6=97=B6?= =?UTF-8?q?=E6=9F=A5=E8=AF=A2=20LabActivityDefinition=20=E8=A1=A5=E5=85=A8?= =?UTF-8?q?=E5=A5=97=E9=A4=90=E4=BF=A1=20=20=20-=20DTO=20=E6=96=B0?= =?UTF-8?q?=E5=A2=9E=20activityId=E3=80=81feePackageId=E3=80=81isPackage?= =?UTF-8?q?=E3=80=81sampleType=E3=80=81unit=20=E5=AD=97=E6=AE=B5=20=20=20-?= =?UTF-8?q?=20=E5=89=8D=E7=AB=AF=E5=AE=9E=E7=8E=B0=E5=A5=97=E9=A4=90?= =?UTF-8?q?=E9=A1=B9=E7=9B=AE=E6=A0=91=E5=BD=A2=E5=B1=95=E5=BC=80=EF=BC=8C?= =?UTF-8?q?=E6=87=92=E5=8A=A0=E8=BD=BD=E5=A5=97=E9=A4=90=E6=98=8E=E7=BB=86?= =?UTF-8?q?=20=20=20Bug=20#329:=20=E6=A3=80=E9=AA=8C=E7=94=B3=E8=AF=B7?= =?UTF-8?q?=E6=89=A7=E8=A1=8C=E7=A7=91=E5=AE=A4=E9=BB=98=E8=AE=A4=E5=80=BC?= =?UTF-8?q?=E8=AE=BE=E7=BD=AE=E9=94=99=E8=AF=AF=20=20=20-=20=E5=90=8E?= =?UTF-8?q?=E7=AB=AF=E7=A7=BB=E9=99=A4=E9=BB=98=E8=AE=A4=E6=89=A7=E8=A1=8C?= =?UTF-8?q?=E7=A7=91=E5=AE=A4=E9=80=BB=E8=BE=91=EF=BC=8C=E6=B7=BB=E5=8A=A0?= =?UTF-8?q?=E6=9C=AA=E5=8C=B9=E9=85=8D=E7=A7=91=E5=AE=A4=E8=AD=A6=E5=91=8A?= =?UTF-8?q?=E6=97=A5=E5=BF=97=20=20=20-=20=E5=89=8D=E7=AB=AF=E4=BB=8E=20Or?= =?UTF-8?q?ganization=20=E8=A1=A8=E8=8E=B7=E5=8F=96=E6=89=A7=E8=A1=8C?= =?UTF-8?q?=E7=A7=91=E5=AE=A4=EF=BC=8C=E8=87=AA=E5=8A=A8=E6=A0=B9=E6=8D=AE?= =?UTF-8?q?=E6=A3=80=E9=AA=8C=E7=B1=BB=E5=9E=8B=E8=AE=BE=E7=BD=AE=E9=BB=98?= =?UTF-8?q?=E8=AE=A4=E5=80=BC=20=20=20Bug=20#334:=20=E6=A3=80=E9=AA=8C?= =?UTF-8?q?=E7=94=B3=E8=AF=B7=E7=95=8C=E9=9D=A2=E9=A1=B6=E9=83=A8=E6=93=8D?= =?UTF-8?q?=E4=BD=9C=E6=A0=8F=E5=8D=A0=E7=94=A8=E7=A9=BA=E9=97=B4=E8=BF=87?= =?UTF-8?q?=E5=A4=A7=20=20=20-=20=E9=9A=90=E8=97=8F=E9=A1=B6=E9=83=A8?= =?UTF-8?q?=E6=93=8D=E4=BD=9C=E6=A0=8F=EF=BC=8C=E4=BF=9D=E5=AD=98/?= =?UTF-8?q?=E6=96=B0=E5=A2=9E=E6=8C=89=E9=92=AE=E7=A7=BB=E8=87=B3=E5=8D=A1?= =?UTF-8?q?=E7=89=87=E5=A4=B4=E9=83=A8=20=20=20Bug=20#368:=20=E9=97=A8?= =?UTF-8?q?=E8=AF=8A=E5=8C=BB=E7=94=9F=E7=AB=99=E5=BE=85=E5=86=99=E7=97=85?= =?UTF-8?q?=E5=8E=86=E6=A0=87=E7=AD=BE=E9=A1=B5=E5=8A=9F=E8=83=BD=E5=86=97?= =?UTF-8?q?=E4=BD=99=20=20=20-=20=E5=B1=8F=E8=94=BD=E5=BE=85=E5=86=99?= =?UTF-8?q?=E7=97=85=E5=8E=86=E6=A0=87=E7=AD=BE=E9=A1=B5=EF=BC=88=E5=B7=A6?= =?UTF-8?q?=E4=BE=A7=E5=AF=BC=E8=88=AA=E6=A0=8F=E5=B7=B2=E6=9C=89=E7=8B=AC?= =?UTF-8?q?=E7=AB=8B=E8=8F=9C=E5=8D=95=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DoctorStationLabApplyServiceImpl.java | 112 ++++- .../dto/DoctorStationLabApplyItemDto.java | 40 ++ .../DoctorStationLabApplyMapper.xml | 35 -- .../lab/domain/InspectionLabApplyItem.java | 5 + .../inspection/inspectionApplication.vue | 394 +++++++++++++++--- .../src/views/doctorstation/index.vue | 5 +- 6 files changed, 489 insertions(+), 102 deletions(-) diff --git a/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationLabApplyServiceImpl.java b/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationLabApplyServiceImpl.java index 3dbb3792..dee8b486 100644 --- a/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationLabApplyServiceImpl.java +++ b/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationLabApplyServiceImpl.java @@ -11,10 +11,12 @@ import com.openhis.lab.domain.InspectionLabApply; import com.openhis.lab.domain.InspectionLabApplyItem; import com.openhis.lab.domain.BarCode; import com.openhis.lab.domain.InspectionPackage; +import com.openhis.lab.domain.LabActivityDefinition; import com.openhis.lab.service.IInspectionLabApplyItemService; import com.openhis.lab.service.IInspectionLabApplyService; import com.openhis.lab.service.IInspectionLabBarCodeService; import com.openhis.lab.service.IInspectionPackageService; +import com.openhis.lab.service.ILabActivityDefinitionService; import com.openhis.workflow.domain.ServiceRequest; import com.openhis.workflow.service.IServiceRequestService; import com.openhis.web.doctorstation.appservice.IDoctorStationAdviceAppService; @@ -45,6 +47,9 @@ import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.Set; +import java.util.stream.Collectors; +import java.util.function.Function; /** * 根据检验申请单开单信息系统自动插入门诊医嘱表(与检验申请主表申请单号进行关联), @@ -88,6 +93,10 @@ public class DoctorStationLabApplyServiceImpl implements IDoctorStationInspectio @Autowired private IInspectionPackageService inspectionPackageService; + // Bug #326: 检验项目定义服务(用于回充时获取套餐信息) + @Autowired + private ILabActivityDefinitionService labActivityDefinitionService; + /** * 保存检验申请单信息 * @param doctorStationLabApplyDto @@ -160,6 +169,28 @@ public class DoctorStationLabApplyServiceImpl implements IDoctorStationInspectio InspectionLabApplyItem inspectionLabApplyItem = new InspectionLabApplyItem(); BeanUtils.copyProperties(doctorStationLabApplyItemDto, inspectionLabApplyItem); + // 前端选择检验项目时已携带完整的关联信息(activityId、feePackageId、itemCode等) + // Bug #326修复: 只使用 activityId 直接查询,不使用名称反查 + Long activityId = doctorStationLabApplyItemDto.getActivityId(); + if (activityId != null) { + // 使用 activityId 直接查询检验项目定义 + LabActivityDefinition labActivityDefinition = labActivityDefinitionService.getById(activityId); + if (labActivityDefinition != null && DelFlag.NO.getCode().equals(labActivityDefinition.getDeleteFlag())) { + // 补充编码(如果前端未传或为空) + if (inspectionLabApplyItem.getItemCode() == null || inspectionLabApplyItem.getItemCode().isEmpty()) { + inspectionLabApplyItem.setItemCode(labActivityDefinition.getBusNo()); + } + // 补充套餐ID(如果前端未传) + if (inspectionLabApplyItem.getFeePackageId() == null) { + inspectionLabApplyItem.setFeePackageId(labActivityDefinition.getFeePackageId()); + } + } + } else { + // 没有 activityId 时记录警告,不使用名称反查 + log.warn("检验项目 [{}] 未传入 activityId,无法获取完整关联信息", + doctorStationLabApplyItemDto.getItemName()); + } + // 后端重新计算金额:金额 = 单价 × 数量 java.math.BigDecimal itemPrice = doctorStationLabApplyItemDto.getItemPrice(); java.math.BigDecimal itemQty = doctorStationLabApplyItemDto.getItemQty(); @@ -241,13 +272,16 @@ public class DoctorStationLabApplyServiceImpl implements IDoctorStationInspectio ); if (organization != null) { positionId = organization.getId(); + } else { + // Bug #329: 执行科室代码无法匹配到科室,记录警告日志 + log.warn("执行科室代码 [{}] 在科室表中未找到对应记录", performDeptCode); } + } else { + // Bug #329: 未指定执行科室,记录警告日志 + log.warn("检验项目 [{}] 未指定执行科室", itemName); } - // 如果没有指定执行科室,使用当前医生所在的科室作为默认执行科室 - if (positionId == null) { - positionId = SecurityUtils.getDeptId(); - } + // Bug #329: 移除默认执行科室逻辑,必须由前端明确指定执行科室 // 4. 创建医嘱保存对象 AdviceSaveDto adviceSaveDto = new AdviceSaveDto(); @@ -324,7 +358,6 @@ public class DoctorStationLabApplyServiceImpl implements IDoctorStationInspectio throw new RuntimeException("套餐项目 '" + itemName + "' 未设置有效价格,请先配置套餐金额"); } unitPrice = packageInfo.getPackageAmount(); - log.info("套餐项目 '{}' 使用套餐价格: {}", itemName, unitPrice); } else { // 普通项目:使用前端传入的价格 unitPrice = labApplyItemDto.getItemPrice(); @@ -367,30 +400,84 @@ public class DoctorStationLabApplyServiceImpl implements IDoctorStationInspectio */ @Override public Object getInspectionApplyByApplyNo(String applyNo) { - // 查询主表数据 - DoctorStationLabApplyDto applyDto = (DoctorStationLabApplyDto) doctorStationLabApplyMapper.getInspectionApplyByApplyNo(applyNo); - if (applyDto == null) { + // 使用MyBatis-Plus查询主表数据 + InspectionLabApply mainEntity = inspectionLabApplyService.getOne( + new QueryWrapper() + .eq("apply_no", applyNo) + .eq("delete_flag", DelFlag.NO.getCode()) + ); + + if (mainEntity == null) { return null; } + // 使用BeanUtils进行基础字段映射 + DoctorStationLabApplyDto applyDto = new DoctorStationLabApplyDto(); + BeanUtils.copyProperties(mainEntity, applyDto); + // 由于字段名称映射关系(如 id -> applicationId),需要单独设置 + applyDto.setApplicationId(mainEntity.getId()); + // 查询检验项目明细 List itemList = inspectionLabApplyItemService.list( new QueryWrapper() .eq("apply_no", applyNo) - .eq("delete_flag", "0") + .eq("delete_flag", DelFlag.NO.getCode()) .orderByAsc("item_seq") ); // 转换为 DTO 列表 List itemDtoList = new ArrayList<>(); if (itemList != null && !itemList.isEmpty()) { + // 提取所有不同的 itemCode,用于批量查询 + Set itemCodes = itemList.stream() + .filter(item -> item.getItemCode() != null && !item.getItemCode().isEmpty()) + .map(InspectionLabApplyItem::getItemCode) + .collect(Collectors.toSet()); + + // 批量查询所有关联的检验项目定义(使用MyBatis-Plus) + Map definitionMap = new HashMap<>(); + if (!itemCodes.isEmpty()) { + List labActivityDefinitions = labActivityDefinitionService.list( + new QueryWrapper() + .in("bus_no", itemCodes) + .eq("delete_flag", DelFlag.NO.getCode()) + ); + // 构建 itemCode 到定义的映射 + definitionMap = labActivityDefinitions.stream() + .collect(Collectors.toMap(LabActivityDefinition::getBusNo, Function.identity())); + } + + // 处理每个明细项 for (InspectionLabApplyItem item : itemList) { DoctorStationLabApplyItemDto itemDto = new DoctorStationLabApplyItemDto(); + // 使用BeanUtils进行基础字段映射 BeanUtils.copyProperties(item, itemDto); + + // feePackageId 在保存时已存储,直接使用 + itemDto.setFeePackageId(item.getFeePackageId()); + // 判断是否是套餐项目(根据 feePackageId 是否存在) + itemDto.setIsPackage(item.getFeePackageId() != null); + + // 从批量查询结果中获取关联信息 + if (item.getItemCode() != null && !item.getItemCode().isEmpty()) { + LabActivityDefinition labActivityDefinition = definitionMap.get(item.getItemCode()); + if (labActivityDefinition != null) { + itemDto.setActivityId(labActivityDefinition.getId()); + itemDto.setSampleType(labActivityDefinition.getSpecimenCode()); + itemDto.setUnit(labActivityDefinition.getPermittedUnitCode()); + // 补充检验类型ID,用于前端自动设置执行科室 + itemDto.setInspectionTypeId(labActivityDefinition.getInspectionTypeId()); + } + } else { + log.warn("检验项目 [{}] 未存储 itemCode,无法获取完整关联信息", item.getItemName()); + } + itemDtoList.add(itemDto); } // 从第一个明细项获取执行科室代码 - applyDto.setExecuteDepartment(itemList.get(0).getPerformDeptCode()); + if (!itemList.isEmpty() && itemList.get(0).getPerformDeptCode() != null) { + applyDto.setExecuteDepartment(itemList.get(0).getPerformDeptCode()); + } } applyDto.setLabApplyItemList(itemDtoList); @@ -409,8 +496,9 @@ public class DoctorStationLabApplyServiceImpl implements IDoctorStationInspectio // 使用 PageHelper 进行分页查询 PageHelper.startPage(pageNo, pageSize); - // 查询检验申请单列表 - log.debug("查询申请单数据前"); + // 使用MyBatis-Plus查询检验申请单列表 + // 需要关联adm_encounter表,仍使用原Mapper方法或重构为MyBatis-Plus方式 + // 为保持一致性和考虑到复杂的关联查询,暂时保留原有实现方式 List list = doctorStationLabApplyMapper.getInspectionApplyListPage(encounterId); log.debug("查询申请单数据后"); diff --git a/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/dto/DoctorStationLabApplyItemDto.java b/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/dto/DoctorStationLabApplyItemDto.java index 42189f28..e0e9401a 100644 --- a/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/dto/DoctorStationLabApplyItemDto.java +++ b/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/dto/DoctorStationLabApplyItemDto.java @@ -1,5 +1,7 @@ package com.openhis.web.doctorstation.dto; +import com.fasterxml.jackson.databind.annotation.JsonSerialize; +import com.fasterxml.jackson.databind.ser.std.ToStringSerializer; import lombok.Data; import lombok.experimental.Accessors; @@ -67,4 +69,42 @@ public class DoctorStationLabApplyItemDto { */ @NotNull(message = "行状态不能为空") private Long itemStatus; + + // ========== Bug #326: 套餐相关字段(回充时需要) ========== + + /** + * 活动定义ID(检验项目定义ID) + * 用于回充时关联到原始检验项目定义 + */ + @JsonSerialize(using = ToStringSerializer.class) + private Long activityId; + + /** + * 套餐ID(如果该项目是套餐,则关联套餐表) + * 对应 InspectionPackage.basicInformationId + */ + @JsonSerialize(using = ToStringSerializer.class) + private Long feePackageId; + + /** + * 是否是套餐项目 + */ + private Boolean isPackage; + + /** + * 样本类型 + */ + private String sampleType; + + /** + * 单位 + */ + private String unit; + + /** + * 检验类型ID(关联 inspection_type 大类) + * 用于前端自动设置执行科室 + */ + @JsonSerialize(using = ToStringSerializer.class) + private Long inspectionTypeId; } diff --git a/openhis-server-new/openhis-application/src/main/resources/mapper/doctorstation/DoctorStationLabApplyMapper.xml b/openhis-server-new/openhis-application/src/main/resources/mapper/doctorstation/DoctorStationLabApplyMapper.xml index cef460a4..d3a8168f 100644 --- a/openhis-server-new/openhis-application/src/main/resources/mapper/doctorstation/DoctorStationLabApplyMapper.xml +++ b/openhis-server-new/openhis-application/src/main/resources/mapper/doctorstation/DoctorStationLabApplyMapper.xml @@ -4,41 +4,6 @@ "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> - - diff --git a/openhis-server-new/openhis-domain/src/main/java/com/openhis/lab/domain/InspectionLabApplyItem.java b/openhis-server-new/openhis-domain/src/main/java/com/openhis/lab/domain/InspectionLabApplyItem.java index 8b0a257a..9dc83106 100644 --- a/openhis-server-new/openhis-domain/src/main/java/com/openhis/lab/domain/InspectionLabApplyItem.java +++ b/openhis-server-new/openhis-domain/src/main/java/com/openhis/lab/domain/InspectionLabApplyItem.java @@ -74,4 +74,9 @@ public class InspectionLabApplyItem extends HisBaseEntity { */ @JsonSerialize(using = ToStringSerializer.class) private Long itemStatus; + /** + * 套餐ID + */ + @JsonSerialize(using = ToStringSerializer.class) + private Long feePackageId; } diff --git a/openhis-ui-vue3/src/views/doctorstation/components/inspection/inspectionApplication.vue b/openhis-ui-vue3/src/views/doctorstation/components/inspection/inspectionApplication.vue index 132e7f24..0a5b4a4c 100644 --- a/openhis-ui-vue3/src/views/doctorstation/components/inspection/inspectionApplication.vue +++ b/openhis-ui-vue3/src/views/doctorstation/components/inspection/inspectionApplication.vue @@ -1,7 +1,5 @@