hookehuyr

fix(booking): 修复二维码已核销时取消预约按钮仍显示的问题

- qrCode 组件添加状态变化事件通知机制
- 预约详情页监听状态变化并刷新订单信息
- 订单已核销时显示禁用提示而非取消按钮
- 移除未使用的导入和变量,修复 ESLint 警告

问题详情:
- 二维码轮询更新状态时只更新组件内部状态
- 父组件订单信息未同步更新导致取消按钮不消失

解决方案:
- qrCode 组件状态改变时触发 status-change 事件
- 父组件接收到事件后调用 billInfoAPI 刷新订单
- 订单状态更新为 USED 后自动隐藏取消按钮

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
......@@ -62,7 +62,6 @@
<script setup>
import { ref, computed, watch, onMounted, onUnmounted } from 'vue'
import Taro from '@tarojs/taro'
import { formatDatetime, mask_id_number, get_qrcode_status_text } from '@/utils/tools'
import { qrcodeListAPI, qrcodeStatusAPI, billPersonAPI } from '@/api/index'
import { useGo } from '@/hooks/useGo'
......@@ -86,6 +85,8 @@ const props = defineProps({
}
})
const emit = defineEmits(['status-change'])
const select_index = ref(0)
const userList = ref([])
......@@ -158,6 +159,7 @@ const STATUS_CODE = {
/**
* @description 刷新当前选中二维码状态
* - 仅在当前选中用户存在时请求
* - 状态改变时通知父组件刷新订单信息
* @returns {Promise<void>} 无返回值
*/
const refreshBtn = async () => {
......@@ -168,7 +170,13 @@ const refreshBtn = async () => {
qr_code: userList.value[select_index.value].qr_code
})
if (code) {
const oldStatus = useStatus.value
useStatus.value = data.status
// 当状态发生改变时,通知父组件刷新订单信息
if (oldStatus !== data.status) {
emit('status-change', data.status)
}
}
}
......
......@@ -7,7 +7,13 @@
-->
<template>
<view class="booking-detail-page">
<qrCode ref="qr_code_ref" :status="qrCodeStatus" type="detail" :payId="pay_id"></qrCode>
<qrCode
ref="qr_code_ref"
:status="qrCodeStatus"
type="detail"
:payId="pay_id"
@status-change="handleQrCodeStatusChange"
></qrCode>
<view v-if="billInfo.pay_id" class="detail-wrapper">
<view class="detail-item">
<view>参访时间:</view>
......@@ -41,6 +47,9 @@
>
<view @tap="cancelBooking" class="cancel-btn">取消预约</view>
</view>
<view v-else-if="billInfo.status === CodeStatus.USED" class="cancel-wrapper">
<view class="cancel-btn disabled">订单已核销,无法取消</view>
</view>
</view>
</template>
......@@ -82,6 +91,24 @@ const qrCodeStatusText = computed(() => {
})
/**
* @description 处理二维码状态变化
* - 当二维码被核销时,刷新订单信息以更新页面状态
* @param {string} newStatus 新的二维码状态
* @returns {Promise<void>} 无返回值
*/
const handleQrCodeStatusChange = async newStatus => {
// 当二维码状态变为已使用时,刷新订单信息
if (newStatus === CodeStatus.USED && pay_id.value) {
const { code, data } = await billInfoAPI({ pay_id: pay_id.value })
if (code) {
data.datetime = data && formatDatetime(data)
data.order_time = data.created_time ? data.created_time.slice(0, -3) : ''
billInfo.value = data
}
}
}
/**
* @description 取消预约
* - 成功后刷新离线缓存(保证弱网/离线模式数据一致)
* @returns {Promise<void>} 无返回值
......@@ -95,12 +122,13 @@ const cancelBooking = async () => {
if (confirm) {
Taro.showLoading({ title: '取消中...' })
const { code, data } = await icbcRefundAPI({ pay_id: pay_id.value })
const { code } = await icbcRefundAPI({ pay_id: pay_id.value })
Taro.hideLoading()
if (code) {
Taro.showToast({ title: '取消成功' })
try {
await refresh_offline_booking_cache({ force: true })
// eslint-disable-next-line no-empty
} catch (e) {}
Taro.navigateBack()
} else {
......@@ -179,6 +207,12 @@ useDidHide(() => {
padding: 26rpx 0;
border-radius: 16rpx;
font-size: 35rpx;
&.disabled {
color: #999;
border-color: #999;
background-color: #f5f5f5;
}
}
}
}
......