feat(离线预约): 优化离线预约缓存逻辑和API
重构离线预约缓存处理逻辑,增强数据提取和格式化能力 更新API端点并完善文档注释 移除离线预约详情页中冗余的状态显示代码
Showing
4 changed files
with
99 additions
and
47 deletions
| 1 | /* | 1 | /* |
| 2 | * @Date: 2023-08-24 09:42:27 | 2 | * @Date: 2023-08-24 09:42:27 |
| 3 | * @LastEditors: hookehuyr hookehuyr@gmail.com | 3 | * @LastEditors: hookehuyr hookehuyr@gmail.com |
| 4 | - * @LastEditTime: 2026-01-13 14:52:29 | 4 | + * @LastEditTime: 2026-01-13 18:30:30 |
| 5 | * @FilePath: /xyxBooking-weapp/src/api/index.js | 5 | * @FilePath: /xyxBooking-weapp/src/api/index.js |
| 6 | * @Description: 文件描述 | 6 | * @Description: 文件描述 |
| 7 | */ | 7 | */ |
| ... | @@ -21,7 +21,7 @@ const Api = { | ... | @@ -21,7 +21,7 @@ const Api = { |
| 21 | QRCODE_LIST: '/srv/?a=api&t=qrcode_list', | 21 | QRCODE_LIST: '/srv/?a=api&t=qrcode_list', |
| 22 | QRCODE_STATUS: '/srv/?a=api&t=qrcode_status', | 22 | QRCODE_STATUS: '/srv/?a=api&t=qrcode_status', |
| 23 | BILL_LIST: '/srv/?a=api&t=bill_list', | 23 | BILL_LIST: '/srv/?a=api&t=bill_list', |
| 24 | - BILL_OFFLINE_ALL: '/srv/?a=api&t=bill_offline_all', | 24 | + BILL_OFFLINE_ALL: '/srv/?a=api&t=bill_all_info', |
| 25 | ICBC_REFUND: '/srv/?a=icbc_refund', | 25 | ICBC_REFUND: '/srv/?a=icbc_refund', |
| 26 | BILL_PREPARE: '/srv/?a=api&t=bill_person', | 26 | BILL_PREPARE: '/srv/?a=api&t=bill_person', |
| 27 | BILL_PAY_STATUS: '/srv/?a=api&t=bill_pay_status', | 27 | BILL_PAY_STATUS: '/srv/?a=api&t=bill_pay_status', |
| ... | @@ -183,8 +183,22 @@ export const qrcodeStatusAPI = (params) => fn(fetch.get(Api.QRCODE_STATUS, param | ... | @@ -183,8 +183,22 @@ export const qrcodeStatusAPI = (params) => fn(fetch.get(Api.QRCODE_STATUS, param |
| 183 | export const billListAPI = (params) => fn(fetch.get(Api.BILL_LIST, params)); | 183 | export const billListAPI = (params) => fn(fetch.get(Api.BILL_LIST, params)); |
| 184 | 184 | ||
| 185 | /** | 185 | /** |
| 186 | - * @description: 离线预约记录全量数据(列表+详情) | 186 | + * @description: 所有预约单的详情(用于离线缓存:列表+详情) |
| 187 | - * @returns {String} | 187 | + * @method: GET |
| 188 | + * @returns: {Object} | ||
| 189 | + * @returns: {Number} code | ||
| 190 | + * @returns: {String} msg | ||
| 191 | + * @returns: {Array} data | ||
| 192 | + * @returns: {Number} data[].bill_id 预约单id | ||
| 193 | + * @returns: {String} data[].begin_time 时段起始时间 | ||
| 194 | + * @returns: {String} data[].end_time 时段结束时间 | ||
| 195 | + * @returns: {Number} data[].total_qty 预约人数 | ||
| 196 | + * @returns: {String} data[].total_amt 金额 | ||
| 197 | + * @returns: {String} data[].status 状态(1/2/3/5/7/9/11) | ||
| 198 | + * @returns: {String} data[].created_time 下单时间 | ||
| 199 | + * @returns: {String} data[].pay_id 订单编号/支付凭证 | ||
| 200 | + * @returns: {Object} data[].list 列表字段集合 | ||
| 201 | + * @returns: {Number} data[].list.show_cancel_reserve 显示“取消预约”按钮(1=显示) | ||
| 188 | */ | 202 | */ |
| 189 | export const billOfflineAllAPI = (params) => fn(fetch.get(Api.BILL_OFFLINE_ALL, params)); | 203 | export const billOfflineAllAPI = (params) => fn(fetch.get(Api.BILL_OFFLINE_ALL, params)); |
| 190 | 204 | ... | ... |
| ... | @@ -16,18 +16,60 @@ export const OFFLINE_BOOKING_CACHE_KEY = 'OFFLINE_BOOKING_DATA' | ... | @@ -16,18 +16,60 @@ export const OFFLINE_BOOKING_CACHE_KEY = 'OFFLINE_BOOKING_DATA' |
| 16 | 16 | ||
| 17 | let refresh_promise = null | 17 | let refresh_promise = null |
| 18 | 18 | ||
| 19 | +const extract_bill_payload = (bill) => { | ||
| 20 | + if (!bill) return {} | ||
| 21 | + | ||
| 22 | + const data = { ...bill } | ||
| 23 | + const list = data.list | ||
| 24 | + | ||
| 25 | + if (list && typeof list === 'object' && !Array.isArray(list)) { | ||
| 26 | + return { ...list, ...data } | ||
| 27 | + } | ||
| 28 | + | ||
| 29 | + return data | ||
| 30 | +} | ||
| 31 | + | ||
| 32 | +const extract_person_list = (bill) => { | ||
| 33 | + if (!bill) return [] | ||
| 34 | + | ||
| 35 | + /** | ||
| 36 | + * 从预约记录中提取人员列表 | ||
| 37 | + * - 考虑不同字段名的情况(如 person_list, bill_person_list, persons, qrcode_list, qr_list, detail_list) | ||
| 38 | + * - 确保返回的是数组类型 | ||
| 39 | + */ | ||
| 40 | + const candidate = | ||
| 41 | + (Array.isArray(bill.list) ? bill.list : null) || | ||
| 42 | + (Array.isArray(bill?.list?.list) ? bill.list.list : null) || | ||
| 43 | + bill.person_list || | ||
| 44 | + bill.bill_person_list || | ||
| 45 | + bill.persons || | ||
| 46 | + bill.qrcode_list || | ||
| 47 | + bill.qr_list || | ||
| 48 | + bill.detail_list || | ||
| 49 | + [] | ||
| 50 | + | ||
| 51 | + return Array.isArray(candidate) ? candidate : [] | ||
| 52 | +} | ||
| 53 | + | ||
| 19 | /** | 54 | /** |
| 20 | * 格式化预约记录项 | 55 | * 格式化预约记录项 |
| 21 | * @param {Object} item - 原始预约记录项 | 56 | * @param {Object} item - 原始预约记录项 |
| 22 | * @returns {Object} 格式化后的预约记录项 | 57 | * @returns {Object} 格式化后的预约记录项 |
| 23 | */ | 58 | */ |
| 24 | const normalize_bill_item = (item) => { | 59 | const normalize_bill_item = (item) => { |
| 25 | - const data = item ? { ...item } : {} | 60 | + const data = extract_bill_payload(item) |
| 26 | 61 | ||
| 27 | data.datetime = data.datetime || formatDatetime(data) | 62 | data.datetime = data.datetime || formatDatetime(data) |
| 28 | data.booking_time = data.booking_time || data.datetime | 63 | data.booking_time = data.booking_time || data.datetime |
| 29 | data.order_time = data.order_time || (data.created_time ? data.created_time.slice(0, -3) : '') | 64 | data.order_time = data.order_time || (data.created_time ? data.created_time.slice(0, -3) : '') |
| 30 | 65 | ||
| 66 | + if (!data.person_name) { | ||
| 67 | + const person_list = extract_person_list(item) | ||
| 68 | + const first = person_list[0] | ||
| 69 | + const name = first?.name || first?.person_name | ||
| 70 | + if (name) data.person_name = name | ||
| 71 | + } | ||
| 72 | + | ||
| 31 | return data | 73 | return data |
| 32 | } | 74 | } |
| 33 | 75 | ||
| ... | @@ -70,17 +112,7 @@ export const get_offline_booking_by_pay_id = (pay_id) => { | ... | @@ -70,17 +112,7 @@ export const get_offline_booking_by_pay_id = (pay_id) => { |
| 70 | * @returns {Array} 人员列表(包含姓名、身份证号、二维码等信息) | 112 | * @returns {Array} 人员列表(包含姓名、身份证号、二维码等信息) |
| 71 | */ | 113 | */ |
| 72 | export const get_offline_bill_person_list = (bill) => { | 114 | export const get_offline_bill_person_list = (bill) => { |
| 73 | - if (!bill) return [] | 115 | + return extract_person_list(bill) |
| 74 | - const candidate = | ||
| 75 | - bill.person_list || | ||
| 76 | - bill.bill_person_list || | ||
| 77 | - bill.persons || | ||
| 78 | - bill.qrcode_list || | ||
| 79 | - bill.qr_list || | ||
| 80 | - bill.detail_list || | ||
| 81 | - [] | ||
| 82 | - | ||
| 83 | - return Array.isArray(candidate) ? candidate : [] | ||
| 84 | } | 116 | } |
| 85 | 117 | ||
| 86 | /** | 118 | /** |
| ... | @@ -93,14 +125,17 @@ export const build_offline_qr_list = (bill) => { | ... | @@ -93,14 +125,17 @@ export const build_offline_qr_list = (bill) => { |
| 93 | const datetime = bill?.datetime || formatDatetime(bill || {}) | 125 | const datetime = bill?.datetime || formatDatetime(bill || {}) |
| 94 | 126 | ||
| 95 | return list | 127 | return list |
| 96 | - .filter((item) => item && item.qr_code !== '') | 128 | + .filter((item) => item && (item.qr_code || item.qrcode || item.qrCode) && (item.qr_code || item.qrcode || item.qrCode) !== '') |
| 97 | .map((item) => { | 129 | .map((item) => { |
| 98 | const begin_time = item.begin_time || bill?.begin_time | 130 | const begin_time = item.begin_time || bill?.begin_time |
| 99 | const end_time = item.end_time || bill?.end_time | 131 | const end_time = item.end_time || bill?.end_time |
| 132 | + const qr_code = item.qr_code || item.qrcode || item.qrCode | ||
| 133 | + const name = item.name || item.person_name || item.real_name | ||
| 134 | + const id_number = item.id_number || item.idcard || item.idCard || item.id | ||
| 100 | return { | 135 | return { |
| 101 | - name: item.name, | 136 | + name, |
| 102 | - id_number: item.id_number, | 137 | + id_number, |
| 103 | - qr_code: item.qr_code, | 138 | + qr_code, |
| 104 | begin_time, | 139 | begin_time, |
| 105 | end_time, | 140 | end_time, |
| 106 | datetime: item.datetime || (begin_time && end_time ? formatDatetime({ begin_time, end_time }) : datetime), | 141 | datetime: item.datetime || (begin_time && end_time ? formatDatetime({ begin_time, end_time }) : datetime), | ... | ... |
| 1 | <!-- | 1 | <!-- |
| 2 | * @Date: 2024-01-16 13:19:23 | 2 | * @Date: 2024-01-16 13:19:23 |
| 3 | * @LastEditors: hookehuyr hookehuyr@gmail.com | 3 | * @LastEditors: hookehuyr hookehuyr@gmail.com |
| 4 | - * @LastEditTime: 2024-01-30 16:10:10 | 4 | + * @LastEditTime: 2026-01-13 18:36:58 |
| 5 | * @FilePath: /xyxBooking-weapp/src/pages/bookingDetail/index.vue | 5 | * @FilePath: /xyxBooking-weapp/src/pages/bookingDetail/index.vue |
| 6 | * @Description: 预约记录详情 | 6 | * @Description: 预约记录详情 |
| 7 | --> | 7 | --> |
| ... | @@ -48,6 +48,7 @@ import { useGo } from '@/hooks/useGo' | ... | @@ -48,6 +48,7 @@ import { useGo } from '@/hooks/useGo' |
| 48 | import qrCode from '@/components/qrCode'; | 48 | import qrCode from '@/components/qrCode'; |
| 49 | import { billInfoAPI, icbcRefundAPI } from '@/api/index' | 49 | import { billInfoAPI, icbcRefundAPI } from '@/api/index' |
| 50 | import { formatDatetime } from '@/utils/tools'; | 50 | import { formatDatetime } from '@/utils/tools'; |
| 51 | +import { refresh_offline_booking_cache } from '@/composables/useOfflineBookingCache' | ||
| 51 | 52 | ||
| 52 | const router = useTaroRouter(); | 53 | const router = useTaroRouter(); |
| 53 | const go = useGo(); | 54 | const go = useGo(); |
| ... | @@ -90,6 +91,9 @@ const cancelBooking = async () => { | ... | @@ -90,6 +91,9 @@ const cancelBooking = async () => { |
| 90 | Taro.hideLoading(); | 91 | Taro.hideLoading(); |
| 91 | if (code) { | 92 | if (code) { |
| 92 | Taro.showToast({ title: '取消成功' }); | 93 | Taro.showToast({ title: '取消成功' }); |
| 94 | + try { | ||
| 95 | + await refresh_offline_booking_cache({ force: true }) | ||
| 96 | + } catch (e) {} | ||
| 93 | Taro.navigateBack(); | 97 | Taro.navigateBack(); |
| 94 | } else { | 98 | } else { |
| 95 | Taro.showToast({ title: '取消失败', icon: 'none' }); | 99 | Taro.showToast({ title: '取消失败', icon: 'none' }); | ... | ... |
| ... | @@ -29,10 +29,10 @@ | ... | @@ -29,10 +29,10 @@ |
| 29 | <view>订单编号:</view> | 29 | <view>订单编号:</view> |
| 30 | <view>{{ bill_info.pay_id }}</view> | 30 | <view>{{ bill_info.pay_id }}</view> |
| 31 | </view> | 31 | </view> |
| 32 | - <view class="detail-item"> | 32 | + <!-- <view class="detail-item"> |
| 33 | <view>订单状态:</view> | 33 | <view>订单状态:</view> |
| 34 | <view>{{ status_text }}</view> | 34 | <view>{{ status_text }}</view> |
| 35 | - </view> | 35 | + </view> --> |
| 36 | </view> | 36 | </view> |
| 37 | </view> | 37 | </view> |
| 38 | 38 | ||
| ... | @@ -53,29 +53,29 @@ const router = useTaroRouter() | ... | @@ -53,29 +53,29 @@ const router = useTaroRouter() |
| 53 | const bill_info = ref(null) | 53 | const bill_info = ref(null) |
| 54 | const qr_list = ref([]) | 54 | const qr_list = ref([]) |
| 55 | 55 | ||
| 56 | -const CodeStatus = { | 56 | +// const CodeStatus = { |
| 57 | - APPLY: '1', | 57 | +// APPLY: '1', |
| 58 | - PAYING: '2', | 58 | +// PAYING: '2', |
| 59 | - SUCCESS: '3', | 59 | +// SUCCESS: '3', |
| 60 | - CANCEL: '5', | 60 | +// CANCEL: '5', |
| 61 | - CANCELED: '7', | 61 | +// CANCELED: '7', |
| 62 | - USED: '9', | 62 | +// USED: '9', |
| 63 | - REFUNDING: '11' | 63 | +// REFUNDING: '11' |
| 64 | -} | 64 | +// } |
| 65 | - | 65 | + |
| 66 | -const status_text = computed(() => { | 66 | +// const status_text = computed(() => { |
| 67 | - const status = bill_info.value?.status | 67 | +// const status = bill_info.value?.status |
| 68 | - switch (status) { | 68 | +// switch (status) { |
| 69 | - case CodeStatus.APPLY: return '待支付' | 69 | +// case CodeStatus.APPLY: return '待支付' |
| 70 | - case CodeStatus.PAYING: return '支付中' | 70 | +// case CodeStatus.PAYING: return '支付中' |
| 71 | - case CodeStatus.SUCCESS: return '预约成功' | 71 | +// case CodeStatus.SUCCESS: return '预约成功' |
| 72 | - case CodeStatus.CANCEL: return '已取消' | 72 | +// case CodeStatus.CANCEL: return '已取消' |
| 73 | - case CodeStatus.CANCELED: return '已取消' | 73 | +// case CodeStatus.CANCELED: return '已取消' |
| 74 | - case CodeStatus.USED: return '已使用' | 74 | +// case CodeStatus.USED: return '已使用' |
| 75 | - case CodeStatus.REFUNDING: return '退款中' | 75 | +// case CodeStatus.REFUNDING: return '退款中' |
| 76 | - default: return '未知状态' | 76 | +// default: return '未知状态' |
| 77 | - } | 77 | +// } |
| 78 | -}) | 78 | +// }) |
| 79 | 79 | ||
| 80 | const toList = () => { | 80 | const toList = () => { |
| 81 | Taro.navigateBack({ | 81 | Taro.navigateBack({ |
| ... | @@ -170,4 +170,3 @@ useDidShow(() => { | ... | @@ -170,4 +170,3 @@ useDidShow(() => { |
| 170 | } | 170 | } |
| 171 | } | 171 | } |
| 172 | </style> | 172 | </style> |
| 173 | - | ... | ... |
-
Please register or login to post a comment