组套应用时数据预处理缺失部分关键字段(doseUnitCode_dictText/positionName/ injectFlag/skinTestFlag),导致父组件构建行数据时无法获取完整信息。 在orderGroupDrawer的processed item中显式补充这些字段。 Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
753 lines
26 KiB
Vue
Executable File
753 lines
26 KiB
Vue
Executable File
<template>
|
||
<el-drawer v-model="drawer" title="医嘱组套" direction="ltr" size="700px">
|
||
<!-- 列表视图 -->
|
||
<div v-if="!editMode">
|
||
<div style="margin: 10px 0px">
|
||
<el-input
|
||
v-model="queryParams.searchKey"
|
||
placeholder="请输入组套名称搜索"
|
||
clearable
|
||
style="width: 45%; margin-bottom: -6px; margin-right: 20px"
|
||
@keyup.enter="handleSearch"
|
||
>
|
||
<template #append>
|
||
<el-button icon="Search" @click="handleSearch" />
|
||
</template>
|
||
</el-input>
|
||
<el-radio-group v-model="queryParams.rangeCode" @change="handelRadioChange">
|
||
<el-radio-button :label="1">个人</el-radio-button>
|
||
<el-radio-button :label="2">科室</el-radio-button>
|
||
<el-radio-button :label="3">全院</el-radio-button>
|
||
</el-radio-group>
|
||
<el-button
|
||
type="primary"
|
||
style="float: right"
|
||
@click="handleManageGroup"
|
||
v-if="checkPermi(['personalization:ordersGroupPackage:manage'])"
|
||
>
|
||
管理组套
|
||
</el-button>
|
||
</div>
|
||
|
||
<el-table
|
||
:data="filteredOrderList"
|
||
highlight-current-row
|
||
v-loading="loading"
|
||
border
|
||
stripe
|
||
style="margin-top: 10px"
|
||
>
|
||
<el-table-column type="index" label="序号" width="60" align="center" />
|
||
<el-table-column label="组套名称" align="left" prop="name" min-width="180" show-overflow-tooltip>
|
||
<template #default="scope">
|
||
<el-tooltip content="点击进入编辑" placement="top">
|
||
<span
|
||
style="cursor: pointer; color: #409eff; font-weight: 500; text-decoration: underline;"
|
||
@click="handleEditGroup(scope.row)"
|
||
>
|
||
{{ scope.row.name }}
|
||
</span>
|
||
</el-tooltip>
|
||
</template>
|
||
</el-table-column>
|
||
<el-table-column label="使用范围" align="center" prop="rangeCode_dictText" width="90" />
|
||
<el-table-column label="明细数量" align="center" width="80">
|
||
<template #default="scope">
|
||
<el-tag size="small" type="info">{{ scope.row.detailList?.length || 0 }} 项</el-tag>
|
||
</template>
|
||
</el-table-column>
|
||
<el-table-column label="操作" align="center" width="150" fixed="right">
|
||
<template #default="scope">
|
||
<el-button type="primary" link @click="handlePreviewGroup(scope.row)">
|
||
预览
|
||
</el-button>
|
||
<el-button type="success" link @click="handleUseOrderGroup(scope.row)">
|
||
<el-icon><Select /></el-icon>
|
||
应用
|
||
</el-button>
|
||
</template>
|
||
</el-table-column>
|
||
</el-table>
|
||
|
||
<div v-if="filteredOrderList.length === 0 && !loading" style="text-align: center; padding: 40px; color: #909399;">
|
||
<el-icon :size="48" style="margin-bottom: 10px"><Box /></el-icon>
|
||
<p>暂无组套数据</p>
|
||
<p style="font-size: 12px; margin-top: 5px;">您可以在"个性化设置 > 医嘱组套"中创建组套</p>
|
||
</div>
|
||
</div>
|
||
|
||
<!-- 编辑视图 -->
|
||
<div v-else>
|
||
<!-- 返回按钮 -->
|
||
<div style="margin-bottom: 15px; border-bottom: 1px solid #ebeef5; padding-bottom: 10px;">
|
||
<el-button @click="handleCancelEdit">
|
||
<el-icon><ArrowLeft /></el-icon>
|
||
返回列表
|
||
</el-button>
|
||
<span style="margin-left: 15px; font-weight: 600; font-size: 16px;">编辑组套</span>
|
||
<el-button type="primary" style="float: right" @click="handleSaveGroup" :loading="saving">
|
||
<el-icon><Check /></el-icon>
|
||
保存组套
|
||
</el-button>
|
||
</div>
|
||
|
||
<!-- 基本信息 -->
|
||
<div style="margin-bottom: 20px;">
|
||
<h4 style="margin: 0 0 15px 0; color: #606266;">基本信息</h4>
|
||
<el-form :model="editingGroup" label-width="100px" :inline="true">
|
||
<el-form-item label="组套名称" required>
|
||
<el-input
|
||
v-model="editingGroup.name"
|
||
placeholder="请输入组套名称"
|
||
style="width: 220px"
|
||
clearable
|
||
/>
|
||
</el-form-item>
|
||
<el-form-item label="组套类型">
|
||
<el-select v-model="editingGroup.typeEnum" placeholder="请选择" style="width: 150px">
|
||
<el-option label="医嘱组套" :value="1" />
|
||
<el-option label="诊疗组套" :value="2" />
|
||
</el-select>
|
||
</el-form-item>
|
||
<el-form-item label="使用范围">
|
||
<el-select v-model="editingGroup.rangeCode" placeholder="请选择" style="width: 150px">
|
||
<el-option label="个人" :value="1" />
|
||
<el-option label="科室" :value="2" />
|
||
<el-option label="全院" :value="3" />
|
||
</el-select>
|
||
</el-form-item>
|
||
</el-form>
|
||
</div>
|
||
|
||
<!-- 项目列表 -->
|
||
<div>
|
||
<div style="display: flex; justify-content: space-between; align-items: center; margin-bottom: 10px;">
|
||
<h4 style="margin: 0; color: #606266;">
|
||
项目列表
|
||
<el-tag size="small" type="info">{{ editingGroup.detailList?.length || 0 }} 项</el-tag>
|
||
</h4>
|
||
<el-button type="primary" link @click="handleAddItem">
|
||
<el-icon><Plus /></el-icon>
|
||
添加项目
|
||
</el-button>
|
||
</div>
|
||
|
||
<el-table :data="editingGroup.detailList" border size="small" v-loading="detailLoading">
|
||
<el-table-column type="index" label="#" width="40" align="center" />
|
||
<el-table-column label="医嘱名称" prop="orderDefinitionName" min-width="150" show-overflow-tooltip />
|
||
<el-table-column label="数量" width="80" align="center">
|
||
<template #default="scope">
|
||
<el-input-number
|
||
v-model="scope.row.quantity"
|
||
:min="1"
|
||
:controls="false"
|
||
size="small"
|
||
style="width: 60px"
|
||
/>
|
||
</template>
|
||
</el-table-column>
|
||
<el-table-column label="单位" prop="unitCodeName" width="60" align="center" />
|
||
<el-table-column label="用法" width="100" align="center">
|
||
<template #default="scope">
|
||
<el-select
|
||
v-model="scope.row.methodCode"
|
||
placeholder="用法"
|
||
size="small"
|
||
filterable
|
||
clearable
|
||
>
|
||
<el-option
|
||
v-for="dict in method_code"
|
||
:key="dict.value"
|
||
:label="dict.label"
|
||
:value="dict.value"
|
||
/>
|
||
</el-select>
|
||
</template>
|
||
</el-table-column>
|
||
<el-table-column label="频次" width="100" align="center">
|
||
<template #default="scope">
|
||
<el-select
|
||
v-model="scope.row.rateCode"
|
||
placeholder="频次"
|
||
size="small"
|
||
filterable
|
||
clearable
|
||
>
|
||
<el-option
|
||
v-for="dict in rate_code"
|
||
:key="dict.value"
|
||
:label="dict.label"
|
||
:value="dict.value"
|
||
/>
|
||
</el-select>
|
||
</template>
|
||
</el-table-column>
|
||
<el-table-column label="操作" width="60" align="center" fixed="right">
|
||
<template #default="scope">
|
||
<el-button type="danger" link size="small" @click="handleRemoveItem(scope.$index)">
|
||
<el-icon><Delete /></el-icon>
|
||
</el-button>
|
||
</template>
|
||
</el-table-column>
|
||
</el-table>
|
||
|
||
<div v-if="!editingGroup.detailList || editingGroup.detailList.length === 0"
|
||
style="text-align: center; padding: 30px; color: #909399; border: 1px dashed #dcdfe6; margin-top: 10px;">
|
||
<p>暂无项目,点击"添加项目"按钮添加</p>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
<!-- 组套预览对话框 -->
|
||
<el-dialog v-model="previewVisible" title="组套预览" width="600px" append-to-body>
|
||
<div v-if="currentGroup">
|
||
<h4>{{ currentGroup.name }}</h4>
|
||
<p style="color: #909399; font-size: 14px;">
|
||
使用范围:{{ currentGroup.rangeCode_dictText }} |
|
||
包含 {{ currentGroup.detailList?.length || 0 }} 个医嘱项
|
||
</p>
|
||
<el-table :data="currentGroup.detailList" border size="small" style="margin-top: 15px;">
|
||
<el-table-column type="index" label="#" width="40" align="center" />
|
||
<el-table-column label="医嘱名称" prop="orderDefinitionName" min-width="180" show-overflow-tooltip />
|
||
<el-table-column label="数量" prop="quantity" width="80" align="center" />
|
||
<el-table-column label="单位" prop="unitCodeName" width="80" align="center" />
|
||
<el-table-column label="用法" prop="methodCode_dictText" width="100" align="center" />
|
||
<el-table-column label="频次" prop="rateCode_dictText" width="100" align="center" />
|
||
</el-table>
|
||
</div>
|
||
<template #footer>
|
||
<span class="dialog-footer">
|
||
<el-button @click="previewVisible = false">取消</el-button>
|
||
<el-button type="primary" @click="confirmUseGroup">应用到当前患者</el-button>
|
||
</span>
|
||
</template>
|
||
</el-dialog>
|
||
|
||
<!-- 添加项目对话框 -->
|
||
<el-dialog v-model="addItemVisible" title="添加医嘱项目" width="800px" append-to-body>
|
||
<div style="margin-bottom: 15px;">
|
||
<el-input
|
||
v-model="itemSearchKey"
|
||
placeholder="输入医嘱名称或拼音码搜索"
|
||
clearable
|
||
@keyup.enter="searchAdviceItems"
|
||
style="width: 300px"
|
||
>
|
||
<template #append>
|
||
<el-button icon="Search" @click="searchAdviceItems" />
|
||
</template>
|
||
</el-input>
|
||
</div>
|
||
|
||
<el-table
|
||
:data="adviceItemList"
|
||
border
|
||
highlight-current-row
|
||
@current-change="handleItemSelect"
|
||
v-loading="itemLoading"
|
||
max-height="400"
|
||
>
|
||
<el-table-column type="index" label="#" width="40" align="center" />
|
||
<el-table-column label="医嘱名称" prop="adviceName" min-width="150" show-overflow-tooltip />
|
||
<el-table-column label="类型" prop="adviceType_dictText" width="80" align="center" />
|
||
<el-table-column label="规格" prop="volume" width="100" show-overflow-tooltip />
|
||
<el-table-column label="单价" width="80" align="right">
|
||
<template #default="scope">
|
||
{{ scope.row.unitPrice?.toFixed(2) || '-' }}
|
||
</template>
|
||
</el-table-column>
|
||
<el-table-column label="单位" prop="unitCode_dictText" width="60" align="center" />
|
||
</el-table>
|
||
|
||
<div v-if="adviceItemList.length === 0 && !itemLoading"
|
||
style="text-align: center; padding: 30px; color: #909399;">
|
||
<p>请输入关键词搜索医嘱项目</p>
|
||
</div>
|
||
|
||
<!-- 选中项目的配置 -->
|
||
<div v-if="selectedItem" style="margin-top: 15px; padding: 15px; background: #f5f7fa; border-radius: 4px;">
|
||
<h4 style="margin: 0 0 10px 0;">配置项目:{{ selectedItem.adviceName }}</h4>
|
||
<el-form :inline="true" label-width="80px">
|
||
<el-form-item label="数量">
|
||
<el-input-number v-model="newItemConfig.quantity" :min="1" :controls="false" />
|
||
</el-form-item>
|
||
<el-form-item label="用法">
|
||
<el-select v-model="newItemConfig.methodCode" placeholder="用法" filterable clearable style="width: 120px">
|
||
<el-option v-for="dict in method_code" :key="dict.value" :label="dict.label" :value="dict.value" />
|
||
</el-select>
|
||
</el-form-item>
|
||
<el-form-item label="频次">
|
||
<el-select v-model="newItemConfig.rateCode" placeholder="频次" filterable clearable style="width: 120px">
|
||
<el-option v-for="dict in rate_code" :key="dict.value" :label="dict.label" :value="dict.value" />
|
||
</el-select>
|
||
</el-form-item>
|
||
</el-form>
|
||
</div>
|
||
|
||
<template #footer>
|
||
<span class="dialog-footer">
|
||
<el-button @click="addItemVisible = false">取消</el-button>
|
||
<el-button type="primary" @click="confirmAddItem" :disabled="!selectedItem">
|
||
添加到组套
|
||
</el-button>
|
||
</span>
|
||
</template>
|
||
</el-dialog>
|
||
</el-drawer>
|
||
</template>
|
||
|
||
<script setup>
|
||
import { getOrderGroup, getAdviceBaseInfo, saveOrderGroup } from '../api';
|
||
import { Select, Box, ArrowLeft, Check, Plus, Delete } from '@element-plus/icons-vue';
|
||
import { checkPermi } from '@/utils/permission';
|
||
import { ElMessage } from 'element-plus';
|
||
|
||
const { proxy } = getCurrentInstance();
|
||
const { method_code, rate_code } = proxy.useDict('method_code', 'rate_code');
|
||
|
||
const props = defineProps({
|
||
diagnosis: {
|
||
type: Object,
|
||
required: true,
|
||
},
|
||
organizationId: {
|
||
type: [String, Number],
|
||
required: true,
|
||
},
|
||
patientInfo: {
|
||
type: Object,
|
||
default: () => ({})
|
||
}
|
||
});
|
||
|
||
const drawer = ref(false);
|
||
const orderList = ref([]);
|
||
const result = ref([]);
|
||
const loading = ref(false);
|
||
const previewVisible = ref(false);
|
||
const currentGroup = ref(null);
|
||
|
||
// 编辑模式相关
|
||
const editMode = ref(false);
|
||
const editingGroup = ref({});
|
||
const saving = ref(false);
|
||
const detailLoading = ref(false);
|
||
|
||
// 添加项目相关
|
||
const addItemVisible = ref(false);
|
||
const itemSearchKey = ref('');
|
||
const adviceItemList = ref([]);
|
||
const itemLoading = ref(false);
|
||
const selectedItem = ref(null);
|
||
const newItemConfig = ref({
|
||
quantity: 1,
|
||
methodCode: '',
|
||
rateCode: ''
|
||
});
|
||
|
||
const emit = defineEmits(['useOrderGroup']);
|
||
|
||
const queryParams = ref({
|
||
searchKey: '',
|
||
rangeCode: 2,
|
||
});
|
||
|
||
// 根据搜索关键字过滤组套列表
|
||
const filteredOrderList = computed(() => {
|
||
if (!queryParams.value.searchKey) {
|
||
return orderList.value;
|
||
}
|
||
const keyword = queryParams.value.searchKey.toLowerCase();
|
||
return orderList.value.filter(item =>
|
||
item.name && item.name.toLowerCase().includes(keyword)
|
||
);
|
||
});
|
||
|
||
function handleOpen(group = null, scope = 'personal') {
|
||
drawer.value = true;
|
||
// 设置范围
|
||
if (scope === 'personal') {
|
||
queryParams.value.rangeCode = 1;
|
||
} else if (scope === 'department') {
|
||
queryParams.value.rangeCode = 2;
|
||
} else if (scope === 'hospital') {
|
||
queryParams.value.rangeCode = 3;
|
||
}
|
||
|
||
// 如果有传入组套数据,进入编辑模式
|
||
if (group && group.groupPackageId) {
|
||
editMode.value = true;
|
||
editingGroup.value = JSON.parse(JSON.stringify(group));
|
||
if (!editingGroup.value.detailList) {
|
||
editingGroup.value.detailList = [];
|
||
}
|
||
} else {
|
||
editMode.value = false;
|
||
}
|
||
getList();
|
||
}
|
||
|
||
function handleSearch() {
|
||
console.log('搜索组套:', queryParams.value.searchKey);
|
||
}
|
||
|
||
function handelRadioChange(value) {
|
||
queryParams.value.rangeCode = value;
|
||
switch (value) {
|
||
case 1:
|
||
orderList.value = result.value.personalList || [];
|
||
break;
|
||
case 2:
|
||
orderList.value = result.value.organizationList || [];
|
||
break;
|
||
case 3:
|
||
orderList.value = result.value.hospitalList || [];
|
||
break;
|
||
}
|
||
}
|
||
|
||
// 进入编辑模式
|
||
function handleEditGroup(row) {
|
||
editMode.value = true;
|
||
// 深拷贝组套数据,避免直接修改原数据
|
||
editingGroup.value = JSON.parse(JSON.stringify(row));
|
||
// 确保 detailList 存在
|
||
if (!editingGroup.value.detailList) {
|
||
editingGroup.value.detailList = [];
|
||
}
|
||
}
|
||
|
||
// 取消编辑
|
||
function handleCancelEdit() {
|
||
editMode.value = false;
|
||
editingGroup.value = {};
|
||
}
|
||
|
||
// 保存组套
|
||
async function handleSaveGroup() {
|
||
if (!editingGroup.value.name?.trim()) {
|
||
ElMessage.warning('请输入组套名称');
|
||
return;
|
||
}
|
||
|
||
saving.value = true;
|
||
try {
|
||
// 构建保存数据
|
||
const saveData = {
|
||
groupPackageId: editingGroup.value.groupPackageId || editingGroup.value.id,
|
||
name: editingGroup.value.name,
|
||
packageTypeEnum: editingGroup.value.typeEnum || 1,
|
||
rangeCode: editingGroup.value.rangeCode,
|
||
detailList: editingGroup.value.detailList?.map((item, index) => ({
|
||
id: item.id,
|
||
orderDefinitionId: item.orderDefinitionId,
|
||
orderDefinitionName: item.orderDefinitionName,
|
||
quantity: item.quantity,
|
||
unitCode: item.unitCode,
|
||
unitCodeName: item.unitCodeName,
|
||
methodCode: item.methodCode,
|
||
rateCode: item.rateCode,
|
||
dose: item.dose,
|
||
doseQuantity: item.doseQuantity,
|
||
dispensePerDuration: item.dispensePerDuration,
|
||
sortOrder: index
|
||
})) || []
|
||
};
|
||
|
||
const res = await saveOrderGroup(saveData);
|
||
if (res.code === 200) {
|
||
ElMessage.success('保存成功');
|
||
editMode.value = false;
|
||
editingGroup.value = {};
|
||
// 刷新列表
|
||
getList();
|
||
} else {
|
||
ElMessage.error(res.message || '保存失败');
|
||
}
|
||
} catch (error) {
|
||
console.error('保存组套失败:', error);
|
||
ElMessage.error('保存失败:' + (error.message || '未知错误'));
|
||
} finally {
|
||
saving.value = false;
|
||
}
|
||
}
|
||
|
||
// 打开添加项目对话框
|
||
function handleAddItem() {
|
||
addItemVisible.value = true;
|
||
itemSearchKey.value = '';
|
||
adviceItemList.value = [];
|
||
selectedItem.value = null;
|
||
newItemConfig.value = {
|
||
quantity: 1,
|
||
methodCode: '',
|
||
rateCode: ''
|
||
};
|
||
}
|
||
|
||
// 搜索医嘱项目
|
||
async function searchAdviceItems() {
|
||
console.log('点击搜索按钮, itemSearchKey:', itemSearchKey.value, 'organizationId:', props.organizationId);
|
||
|
||
if (!itemSearchKey.value.trim()) {
|
||
ElMessage.warning('请输入搜索关键词');
|
||
return;
|
||
}
|
||
|
||
// 确保 organizationId 是数字类型
|
||
const orgId = Number(props.organizationId) || null;
|
||
|
||
itemLoading.value = true;
|
||
try {
|
||
const params = {
|
||
searchKey: itemSearchKey.value,
|
||
organizationId: orgId,
|
||
pageNo: 1,
|
||
pageSize: 50,
|
||
adviceTypes: '1,2,3'
|
||
};
|
||
console.log('搜索参数:', params);
|
||
|
||
const res = await getAdviceBaseInfo(params);
|
||
console.log('搜索返回结果:', res);
|
||
adviceItemList.value = res.data?.records || res.rows || [];
|
||
} catch (error) {
|
||
console.error('搜索医嘱项目失败:', error);
|
||
ElMessage.error('搜索失败: ' + (error.message || '未知错误'));
|
||
} finally {
|
||
itemLoading.value = false;
|
||
}
|
||
}
|
||
|
||
// 选择医嘱项目
|
||
function handleItemSelect(row) {
|
||
selectedItem.value = row;
|
||
// 设置默认值
|
||
newItemConfig.value = {
|
||
quantity: 1,
|
||
methodCode: row?.methodCode || '',
|
||
rateCode: row?.rateCode || ''
|
||
};
|
||
}
|
||
|
||
// 确认添加项目到组套
|
||
function confirmAddItem() {
|
||
if (!selectedItem.value) return;
|
||
|
||
const newItem = {
|
||
orderDefinitionId: selectedItem.value.adviceDefinitionId,
|
||
orderDefinitionName: selectedItem.value.adviceName,
|
||
quantity: newItemConfig.value.quantity,
|
||
unitCode: selectedItem.value.unitCode,
|
||
unitCodeName: selectedItem.value.unitCode_dictText,
|
||
methodCode: newItemConfig.value.methodCode,
|
||
rateCode: newItemConfig.value.rateCode,
|
||
dose: selectedItem.value.dose,
|
||
doseQuantity: selectedItem.value.doseQuantity,
|
||
dispensePerDuration: selectedItem.value.dispensePerDuration,
|
||
// 保留医嘱库完整信息用于后续应用
|
||
orderDetailInfos: selectedItem.value
|
||
};
|
||
|
||
if (!editingGroup.value.detailList) {
|
||
editingGroup.value.detailList = [];
|
||
}
|
||
editingGroup.value.detailList.push(newItem);
|
||
|
||
addItemVisible.value = false;
|
||
ElMessage.success('添加成功');
|
||
}
|
||
|
||
// 移除项目
|
||
function handleRemoveItem(index) {
|
||
editingGroup.value.detailList.splice(index, 1);
|
||
}
|
||
|
||
// 单击应用按钮(应用组套)
|
||
async function handleUseOrderGroup(row) {
|
||
if (!row.detailList || row.detailList.length === 0) {
|
||
ElMessage.warning('该组套没有明细项');
|
||
return;
|
||
}
|
||
|
||
// 🔧 Bug 修复:组套保存时未持久化 orderDetailInfos,导致应用时缺失医嘱库信息。
|
||
// 通过 API 批量查询补全,确保 setValue 能获取到 adviceType、inventoryList、priceList 等关键字段。
|
||
const itemsMissingDetail = row.detailList.filter(
|
||
item => !item.orderDetailInfos || Object.keys(item.orderDetailInfos).length === 0
|
||
);
|
||
const detailMap = {};
|
||
if (itemsMissingDetail.length > 0) {
|
||
const ids = itemsMissingDetail
|
||
.map(item => item.orderDefinitionId)
|
||
.filter(Boolean)
|
||
.join(',');
|
||
if (ids) {
|
||
try {
|
||
const res = await getAdviceBaseInfo({
|
||
adviceDefinitionIdParamList: ids,
|
||
organizationId: props.organizationId,
|
||
});
|
||
const records = res.data?.records || res.rows || [];
|
||
records.forEach(rec => {
|
||
if (rec.adviceDefinitionId) {
|
||
detailMap[rec.adviceDefinitionId] = rec;
|
||
}
|
||
});
|
||
} catch (e) {
|
||
// 批量查询失败,使用原始 orderDetailInfos
|
||
}
|
||
}
|
||
}
|
||
|
||
// 🔧 辅助函数:根据字典 code 查找对应的 dictText
|
||
const findDictText = (dictList, code) => {
|
||
if (!code || !dictList?.value?.length) return '';
|
||
const found = dictList.value.find(d => d.value === code);
|
||
return found?.label || '';
|
||
};
|
||
|
||
// 🔧 数据预处理:确保每个明细项都有完整的医嘱信息
|
||
const processedDetailList = row.detailList.map(item => {
|
||
// 优先使用组套中已带的 orderDetailInfos,否则使用 API 查询结果
|
||
const orderDetail = (item.orderDetailInfos && Object.keys(item.orderDetailInfos).length > 0)
|
||
? item.orderDetailInfos
|
||
: (detailMap[item.orderDefinitionId] || {});
|
||
|
||
// 🔧 修复:组套明细只存了 methodCode/rateCode,没有 dictText。
|
||
// 用字典查找补充 dictText,确保界面显示正确的用法/频次名称。
|
||
const resolvedMethodCode = item.methodCode ?? orderDetail.methodCode;
|
||
const resolvedRateCode = item.rateCode ?? orderDetail.rateCode;
|
||
const methodCodeDictText = item.methodCode_dictText
|
||
|| findDictText(method_code, resolvedMethodCode)
|
||
|| orderDetail.methodCode_dictText
|
||
|| '';
|
||
const rateCodeDictText = item.rateCode_dictText
|
||
|| findDictText(rate_code, resolvedRateCode)
|
||
|| orderDetail.rateCode_dictText
|
||
|| '';
|
||
|
||
return {
|
||
// 组套明细字段
|
||
...item,
|
||
|
||
// 医嘱库字段
|
||
adviceName: orderDetail.adviceName || item.orderDefinitionName || '未知项目',
|
||
adviceType: orderDetail.adviceType,
|
||
adviceDefinitionId: item.orderDefinitionId || orderDetail.adviceDefinitionId,
|
||
|
||
// 价格和库存
|
||
unitPrice: orderDetail.unitPrice,
|
||
minUnitPrice: orderDetail.minUnitPrice,
|
||
inventoryList: orderDetail.inventoryList || [],
|
||
priceList: orderDetail.priceList || [],
|
||
partPercent: orderDetail.partPercent ?? 1,
|
||
partAttributeEnum: orderDetail.partAttributeEnum,
|
||
unitConversionRatio: orderDetail.unitConversionRatio,
|
||
positionId: item.positionId ?? orderDetail.positionId,
|
||
defaultLotNumber: orderDetail.defaultLotNumber,
|
||
|
||
// 单位信息
|
||
unitCode: item.unitCode ?? orderDetail.unitCode,
|
||
categoryCode: item.categoryCode ?? orderDetail.categoryCode,
|
||
unitCodeName: item.unitCodeName || orderDetail.unitCode_dictText,
|
||
minUnitCode: orderDetail.minUnitCode,
|
||
doseUnitCode: orderDetail.doseUnitCode,
|
||
doseUnitCode_dictText: orderDetail.doseUnitCode_dictText || '',
|
||
|
||
// 药房/科室名称(setValue 通过库存查找设置,但需确保 orderDetail 中有)
|
||
positionName: orderDetail.positionName || '',
|
||
|
||
// 注射/皮试标识(表格列显示依赖这些字段)
|
||
injectFlag: orderDetail.injectFlag,
|
||
injectFlag_enumText: orderDetail.injectFlag_enumText || '',
|
||
skinTestFlag: orderDetail.skinTestFlag,
|
||
skinTestFlag_enumText: orderDetail.skinTestFlag_enumText || '',
|
||
|
||
// 字典文本(传递到 item 层级,避免后续代码依赖 mergedDetail 再查一次)
|
||
methodCode_dictText: methodCodeDictText,
|
||
rateCode_dictText: rateCodeDictText,
|
||
|
||
// 合并后的完整对象(用于 setValue)
|
||
// 先展开 orderDetail 获取所有药品基础字段(categoryCode、minUnitCode、doseUnitCode、
|
||
// partPercent、partAttributeEnum、unitConversionRatio、defaultLotNumber 等),
|
||
// 再用组套用户覆盖值覆盖,确保单次剂量/频次/用法/用药天数/总量等不被丢失
|
||
mergedDetail: {
|
||
...orderDetail,
|
||
adviceName: orderDetail.adviceName || item.orderDefinitionName || '未知项目',
|
||
adviceType: orderDetail.adviceType,
|
||
quantity: item.quantity,
|
||
unitCode: item.unitCode ?? orderDetail.unitCode,
|
||
categoryCode: item.categoryCode ?? orderDetail.categoryCode,
|
||
unitCodeName: item.unitCodeName,
|
||
dose: item.dose ?? orderDetail.dose,
|
||
rateCode: resolvedRateCode,
|
||
rateCode_dictText: rateCodeDictText,
|
||
methodCode: resolvedMethodCode,
|
||
methodCode_dictText: methodCodeDictText,
|
||
dispensePerDuration: item.dispensePerDuration ?? orderDetail.dispensePerDuration,
|
||
doseQuantity: item.doseQuantity ?? orderDetail.doseQuantity,
|
||
positionId: item.positionId ?? orderDetail.positionId,
|
||
orgId: item.orgId ?? orderDetail.orgId,
|
||
orgName: item.orgName ?? orderDetail.orgName,
|
||
groupId: item.groupId,
|
||
groupOrder: item.groupOrder,
|
||
// 🔧 类型默认为临时医嘱(2=临时,1=长期)
|
||
therapyEnum: item.therapyEnum ?? orderDetail.therapyEnum ?? '2',
|
||
}
|
||
};
|
||
});
|
||
|
||
emit('useOrderGroup', processedDetailList);
|
||
drawer.value = false;
|
||
editMode.value = false;
|
||
}
|
||
|
||
// 预览组套
|
||
function handlePreviewGroup(row) {
|
||
currentGroup.value = row;
|
||
previewVisible.value = true;
|
||
}
|
||
|
||
// 确认应用组套(从预览对话框)
|
||
async function confirmUseGroup() {
|
||
if (currentGroup.value) {
|
||
await handleUseOrderGroup(currentGroup.value);
|
||
previewVisible.value = false;
|
||
}
|
||
}
|
||
|
||
// 跳转到组套管理页面
|
||
function handleManageGroup() {
|
||
window.open('/basicmanage/ordersCombination', '_blank');
|
||
}
|
||
|
||
function getList() {
|
||
loading.value = true;
|
||
getOrderGroup({ organizationId: props.organizationId })
|
||
.then((res) => {
|
||
result.value = res.data || {};
|
||
handelRadioChange(queryParams.value.rangeCode);
|
||
})
|
||
.catch((err) => {
|
||
console.error('获取组套列表失败:', err);
|
||
ElMessage.error('获取组套列表失败');
|
||
})
|
||
.finally(() => {
|
||
loading.value = false;
|
||
});
|
||
}
|
||
|
||
defineExpose({
|
||
handleOpen,
|
||
});
|
||
</script>
|
||
|
||
<style scoped>
|
||
.dialog-footer {
|
||
display: flex;
|
||
justify-content: flex-end;
|
||
gap: 10px;
|
||
}
|
||
</style>
|