Fix Bug #548: isInitializing 同步赋值但 Vue watcher 异步执行导致拦截失效 — transferValue 赋值后加 await nextTick() 确保 watcher 在标志为 true 时执行
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
@@ -33,3 +33,30 @@
|
||||
2. `transferValue` 的 watch 增加 `if (isInitializing.value) return;` 拦截
|
||||
3. `applyEditTransferSelection()` 中设置 `transferValue` 前后加 `isInitializing` 标志
|
||||
4. `applicationListAll` 的 watch 中设置 `transferValue` 前后也加 `isInitializing` 标志
|
||||
|
||||
## 二次修复(isInitializing 时序问题)
|
||||
|
||||
### 二次根因
|
||||
|
||||
Vue 的 `watch()` 回调默认是**异步刷新**的(在下一个 microtask 执行)。前一轮修复使用了同步模式:
|
||||
|
||||
```js
|
||||
isInitializing.value = true
|
||||
transferValue.value = uniq // watcher 被排队,尚未执行
|
||||
isInitializing.value = false // 在 watcher 回调执行前已重置
|
||||
// → watcher 触发时 isInitializing 已为 false → 拦截失效
|
||||
```
|
||||
|
||||
导致 `projectWithDepartment(newValue, 1)` 仍然被调用,`form.targetDepartment = ''` 仍然清空了 descJson 中的科室值。
|
||||
|
||||
### 修复方案
|
||||
|
||||
在 `applyEditTransferSelection` 和 `applicationListAll` watch 中,设置 `transferValue` 后使用 `await nextTick()` 确保 Vue 的 watcher 在 `isInitializing` 为 `true` 的状态下执行完毕,然后再重置为 `false`。
|
||||
|
||||
### 修复结果:✅ 成功,5行改动
|
||||
|
||||
**改动文件**: `openhis-ui-vue3/src/views/inpatientDoctor/home/components/order/applicationForm/laboratoryTests.vue`
|
||||
|
||||
1. import 增加 `nextTick`
|
||||
2. `applyEditTransferSelection` 改为 `async` 函数,`transferValue` 赋值后加 `await nextTick()`
|
||||
3. `applicationListAll` 的 watch 回调改为 `async`,`transferValue` 赋值后加 `await nextTick()`
|
||||
|
||||
@@ -134,7 +134,7 @@
|
||||
</div>
|
||||
</template>
|
||||
<script setup name="LaboratoryTests">
|
||||
import {getCurrentInstance, onMounted, reactive, ref, watch, computed} from 'vue';
|
||||
import {getCurrentInstance, nextTick, onMounted, reactive, ref, watch, computed} from 'vue';
|
||||
import {patientInfo} from '../../../store/patient.js';
|
||||
import {getApplicationList, saveInspection} from './api';
|
||||
import {getOrgList} from '@/views/doctorstation/components/api.js';
|
||||
@@ -349,7 +349,7 @@ watch(
|
||||
);
|
||||
|
||||
/** 编辑弹窗:根据申请单明细把右侧「已选择」与 transferValue 对齐(依赖 applicationListAll 已加载) */
|
||||
const applyEditTransferSelection = () => {
|
||||
const applyEditTransferSelection = async () => {
|
||||
const newData = props.editData
|
||||
if (!newData?.requestFormId || !newData.requestFormDetailList?.length) {
|
||||
return
|
||||
@@ -383,6 +383,8 @@ const applyEditTransferSelection = () => {
|
||||
// 设置初始化标志,防止 transferValue 变化触发 projectWithDepartment 覆盖 descJson 中的科室值
|
||||
isInitializing.value = true
|
||||
transferValue.value = uniq
|
||||
// Vue watcher 默认异步刷新,必须 await nextTick 确保 watcher 在 isInitializing 为 true 时执行
|
||||
await nextTick()
|
||||
isInitializing.value = false
|
||||
if (newData.requestFormDetailList.length && uniq.length === 0) {
|
||||
console.warn(
|
||||
@@ -419,7 +421,7 @@ watch(
|
||||
// 编辑模式下,applicationListAll 加载完成后重新回显已选项目
|
||||
watch(
|
||||
() => applicationListAll.value,
|
||||
() => {
|
||||
async () => {
|
||||
if (!props.editData?.requestFormId) return;
|
||||
if (!props.editData.requestFormDetailList?.length) return;
|
||||
if (!applicationListAll.value.length) return;
|
||||
@@ -435,6 +437,7 @@ watch(
|
||||
});
|
||||
isInitializing.value = true;
|
||||
transferValue.value = selectedIds;
|
||||
await nextTick();
|
||||
isInitializing.value = false;
|
||||
}
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user