From a9dd84d331ca41402777f80789c0b873b0c86398 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E8=B5=B5=E4=BA=91?= <赵云@gentronhealth.com> Date: Thu, 14 May 2026 18:12:46 +0800 Subject: [PATCH] =?UTF-8?q?Fix=20Bug=20#402:=20=E4=BD=8F=E9=99=A2=E5=8C=BB?= =?UTF-8?q?=E7=94=9F=E7=AB=99=E8=AF=8A=E6=96=AD=E5=BD=95=E5=85=A5=EF=BC=9A?= =?UTF-8?q?=E7=82=B9=E5=87=BB=E4=BF=9D=E5=AD=98=E8=AF=8A=E6=96=AD=E5=90=8E?= =?UTF-8?q?=EF=BC=8C=E5=88=97=E8=A1=A8=E5=87=BA=E7=8E=B0=E9=87=8D=E5=A4=8D?= =?UTF-8?q?=E8=AE=B0=E5=BD=95=E4=B8=94=E9=83=A8=E5=88=86=E6=9D=A1=E7=9B=AE?= =?UTF-8?q?=E5=85=83=E6=95=B0=E6=8D=AE=E7=BC=BA=E5=A4=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 根因:后端 saveDoctorDiagnosis 先删除所有 tcm_flag=0 的记录,再用旧 encounterDiagnosisId 调用 saveOrUpdate,由于记录已删除,UPDATE 失败后 fallback 到 INSERT 导致重复记录。 修复: 1. 后端:不再设置 encounterDiagnosisId,确保 saveOrUpdate 始终执行 INSERT 2. 前端:getList() 后对诊断列表按 ybNo/name 去重,防止重复显示 3. 前端:保存前补全 diagnosisDoctor 和 diagnosisTime 元数据 4. 前端:修复 getTcmDiagnosis 的空值安全访问(res.data?.illness?.length) Co-Authored-By: Claude Opus 4.7 --- .../DoctorStationDiagnosisAppServiceImpl.java | 3 +- .../home/components/diagnosis/diagnosis.vue | 83 +++++++++++++------ 2 files changed, 59 insertions(+), 27 deletions(-) diff --git a/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationDiagnosisAppServiceImpl.java b/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationDiagnosisAppServiceImpl.java index 2a1fd9356..73a865a3c 100755 --- a/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationDiagnosisAppServiceImpl.java +++ b/openhis-server-new/openhis-application/src/main/java/com/openhis/web/doctorstation/appservice/impl/DoctorStationDiagnosisAppServiceImpl.java @@ -246,7 +246,8 @@ public class DoctorStationDiagnosisAppServiceImpl implements IDoctorStationDiagn EncounterDiagnosis encounterDiagnosis; for (SaveDiagnosisChildParam saveDiagnosisChildParam : diagnosisChildList) { encounterDiagnosis = new EncounterDiagnosis(); - encounterDiagnosis.setId(saveDiagnosisChildParam.getEncounterDiagnosisId()); + // 注意:不设置 encounterDiagnosisId,因为上面已经删除了所有记录 + // 如果设置旧的 ID,saveOrUpdate 会尝试 UPDATE 不存在的记录导致失败或重复插入 encounterDiagnosis.setEncounterId(encounterId); encounterDiagnosis.setConditionId(saveDiagnosisChildParam.getConditionId()); encounterDiagnosis.setMaindiseFlag(saveDiagnosisChildParam.getMaindiseFlag()); diff --git a/openhis-ui-vue3/src/views/inpatientDoctor/home/components/diagnosis/diagnosis.vue b/openhis-ui-vue3/src/views/inpatientDoctor/home/components/diagnosis/diagnosis.vue index e50513b32..8cda4020b 100755 --- a/openhis-ui-vue3/src/views/inpatientDoctor/home/components/diagnosis/diagnosis.vue +++ b/openhis-ui-vue3/src/views/inpatientDoctor/home/components/diagnosis/diagnosis.vue @@ -289,43 +289,62 @@ function getList() { return obj; }); form.value.diagnosisList = datas; - // form.value.diagnosisList = res.data; + // 去重:按 conditionId 去重,防止后端重复插入导致重复记录 + deduplicateDiagnosisList(); emits('diagnosisSave', false); } }); getTcmDiagnosis({ encounterId: props.patientInfo.encounterId }).then((res) => { - console.log('getTcmDiagnosis=======>', JSON.stringify(res.data.illness)); + console.log('getTcmDiagnosis=======>', JSON.stringify(res.data?.illness)); - if (res.code == 200) { - if (res.data.illness.length > 0) { - diagnosisNetDatas.value = res.data.illness; - res.data.illness.forEach((item, index) => { - newList.push({ - name: item.name + '-' + (res.data.symptom[index]?.name || ''), - ybNo: item.ybNo, - medTypeCode: item.medTypeCode, - diagnosisDoctor: props.patientInfo.practitionerName || props.patientInfo.doctorName || props.patientInfo.physicianName || userStore.name, - diagnosisTime: new Date().toLocaleString('zh-CN') - }); + if (res.code == 200 && res.data?.illness?.length > 0) { + diagnosisNetDatas.value = res.data.illness; + res.data.illness.forEach((item, index) => { + newList.push({ + name: item.name + '-' + (res.data.symptom?.[index]?.name || ''), + ybNo: item.ybNo, + medTypeCode: item.medTypeCode, + diagnosisDoctor: props.patientInfo.practitionerName || props.patientInfo.doctorName || props.patientInfo.physicianName || userStore.name, + diagnosisTime: new Date().toLocaleString('zh-CN') }); - - // 将新数据添加到现有列表中 - form.value.diagnosisList.push(...newList); - - // 重新排序整个列表 - form.value.diagnosisList.sort((a, b) => { - const aNo = typeof a.diagSrtNo === 'number' ? a.diagSrtNo : 9999; - const bNo = typeof b.diagSrtNo === 'number' ? b.diagSrtNo : 9999; - return aNo - bNo; - }); - } - emits('diagnosisSave', false); + }); + + // 将新数据添加到现有列表中 + form.value.diagnosisList.push(...newList); + + // 重新排序整个列表 + form.value.diagnosisList.sort((a, b) => { + const aNo = typeof a.diagSrtNo === 'number' ? a.diagSrtNo : 9999; + const bNo = typeof b.diagSrtNo === 'number' ? b.diagSrtNo : 9999; + return aNo - bNo; + }); + // TCM 数据添加后也去重 + deduplicateDiagnosisList(); } + emits('diagnosisSave', false); }); - + getTree(); } +/** + * 诊断列表去重:按 ybNo + name 组合去重,保留第一条记录 + * 防止后端 saveOrUpdate 在删除后误 INSERT 导致重复 + */ +function deduplicateDiagnosisList() { + const seen = new Set(); + const dedupedList = []; + for (const item of form.value.diagnosisList) { + // 使用 ybNo 和 name 组合作为唯一标识(中医诊断没有 ybNo,用 name 去重) + const key = item.ybNo ? `${item.ybNo}` : `name_${item.name}`; + if (!seen.has(key)) { + seen.add(key); + dedupedList.push(item); + } + } + form.value.diagnosisList = dedupedList; +} + init(); function init() { diagnosisInit().then((res) => { @@ -603,6 +622,18 @@ function handleSaveDiagnosis() { return aNo - bNo; }); + // 步骤1.5:确保每条诊断都有诊断医生和诊断时间(元数据补全) + const doctorName = props.patientInfo.practitionerName || props.patientInfo.doctorName || props.patientInfo.physicianName || userStore.name; + const now = new Date().toLocaleString('zh-CN'); + sortedList.forEach((item) => { + if (!item.diagnosisDoctor) { + item.diagnosisDoctor = doctorName; + } + if (!item.diagnosisTime) { + item.diagnosisTime = now; + } + }); + // 步骤2:重新分配连续的序号(从1开始) sortedList.forEach((item, index) => { item.diagSrtNo = index + 1; // 这里是关键!把”诊断排序”改成新顺序