fix(预约提交): 添加提交状态检查防止重复提交并优化支付流程
添加 is_submitting 状态防止重复提交订单 优化支付流程的错误处理和状态重置 提取刷新参观者列表为独立函数复用逻辑
Showing
1 changed file
with
50 additions
and
22 deletions
| 1 | <!-- | 1 | <!-- |
| 2 | * @Date: 2024-01-15 16:25:51 | 2 | * @Date: 2024-01-15 16:25:51 |
| 3 | * @LastEditors: hookehuyr hookehuyr@gmail.com | 3 | * @LastEditors: hookehuyr hookehuyr@gmail.com |
| 4 | - * @LastEditTime: 2026-01-16 17:38:55 | 4 | + * @LastEditTime: 2026-01-16 18:01:23 |
| 5 | * @FilePath: /xyxBooking-weapp/src/pages/submit/index.vue | 5 | * @FilePath: /xyxBooking-weapp/src/pages/submit/index.vue |
| 6 | * @Description: 预约人员信息 | 6 | * @Description: 预约人员信息 |
| 7 | --> | 7 | --> |
| ... | @@ -100,6 +100,7 @@ const RESERVE_STATUS = { | ... | @@ -100,6 +100,7 @@ const RESERVE_STATUS = { |
| 100 | } | 100 | } |
| 101 | 101 | ||
| 102 | const checked_visitors = ref([]); | 102 | const checked_visitors = ref([]); |
| 103 | +const is_submitting = ref(false); // 是否正在提交订单 | ||
| 103 | const addVisitor = (item) => { | 104 | const addVisitor = (item) => { |
| 104 | if (item.is_reserve === RESERVE_STATUS.ENABLE) { // 今天已经预约 | 105 | if (item.is_reserve === RESERVE_STATUS.ENABLE) { // 今天已经预约 |
| 105 | Taro.showToast({ title: '已预约过参观,请不要重复预约', icon: 'none' }) | 106 | Taro.showToast({ title: '已预约过参观,请不要重复预约', icon: 'none' }) |
| ... | @@ -128,43 +129,74 @@ const pending_pay_id = ref(null); | ... | @@ -128,43 +129,74 @@ const pending_pay_id = ref(null); |
| 128 | // 待支付订单是否需要支付 | 129 | // 待支付订单是否需要支付 |
| 129 | const pending_need_pay = ref(null); | 130 | const pending_need_pay = ref(null); |
| 130 | 131 | ||
| 132 | +/** | ||
| 133 | + * 刷新参观者列表 | ||
| 134 | + */ | ||
| 135 | + | ||
| 136 | +const refreshVisitorList = async (options) => { | ||
| 137 | + if (!date.value || !time.value) return; | ||
| 138 | + const res = await personListAPI({ | ||
| 139 | + reserve_date: date.value, | ||
| 140 | + begin_time: time.value.split('-')[0], | ||
| 141 | + end_time: time.value.split('-')[1], | ||
| 142 | + period_type: period_type.value | ||
| 143 | + }); | ||
| 144 | + if (res && res.code) { | ||
| 145 | + visitorList.value = res.data || []; | ||
| 146 | + if (options?.reset_checked) { | ||
| 147 | + checked_visitors.value = []; | ||
| 148 | + } | ||
| 149 | + } | ||
| 150 | +} | ||
| 151 | + | ||
| 131 | const submitBtn = async () => { | 152 | const submitBtn = async () => { |
| 153 | + if (is_submitting.value) return; | ||
| 132 | if (!checked_visitors.value.length) { | 154 | if (!checked_visitors.value.length) { |
| 133 | Taro.showToast({ title: '请先添加参观者', icon: 'none' }) | 155 | Taro.showToast({ title: '请先添加参观者', icon: 'none' }) |
| 134 | return; | 156 | return; |
| 135 | } | 157 | } |
| 136 | 158 | ||
| 159 | + is_submitting.value = true; | ||
| 160 | + try { | ||
| 137 | let pay_id = pending_pay_id.value; | 161 | let pay_id = pending_pay_id.value; |
| 138 | let need_pay = pending_need_pay.value; | 162 | let need_pay = pending_need_pay.value; |
| 139 | 163 | ||
| 140 | if (!pay_id) { // TAG: 提交订单, 如果没有待支付订单ID, 则创建一个新的订单 | 164 | if (!pay_id) { // TAG: 提交订单, 如果没有待支付订单ID, 则创建一个新的订单 |
| 141 | Taro.showLoading({ title: '提交中...' }); | 165 | Taro.showLoading({ title: '提交中...' }); |
| 142 | - const { code, data, msg } = await addReserveAPI({ | 166 | + let reserve_res = null; |
| 167 | + try { | ||
| 168 | + reserve_res = await addReserveAPI({ | ||
| 143 | reserve_date: date.value, | 169 | reserve_date: date.value, |
| 144 | begin_time: time.value.split('-')[0], | 170 | begin_time: time.value.split('-')[0], |
| 145 | end_time: time.value.split('-')[1], | 171 | end_time: time.value.split('-')[1], |
| 146 | person_id_list: JSON.stringify(checked_visitors.value), | 172 | person_id_list: JSON.stringify(checked_visitors.value), |
| 147 | period_type: period_type.value | 173 | period_type: period_type.value |
| 148 | }); | 174 | }); |
| 149 | - | 175 | + } finally { |
| 150 | Taro.hideLoading(); | 176 | Taro.hideLoading(); |
| 177 | + } | ||
| 151 | 178 | ||
| 152 | - if (code != 1) { | 179 | + if (!reserve_res || reserve_res.code != 1) { |
| 153 | return; | 180 | return; |
| 154 | } | 181 | } |
| 155 | - pay_id = data.pay_id; | 182 | + pay_id = reserve_res.data.pay_id; |
| 156 | pending_pay_id.value = pay_id; | 183 | pending_pay_id.value = pay_id; |
| 157 | - need_pay = data?.need_pay; | 184 | + need_pay = reserve_res.data?.need_pay; |
| 158 | pending_need_pay.value = need_pay; | 185 | pending_need_pay.value = need_pay; |
| 186 | + await refreshVisitorList({ reset_checked: true }); | ||
| 159 | } | 187 | } |
| 160 | 188 | ||
| 161 | // 以接口返回的 need_pay 为准:1=需要支付,0=不需要支付 | 189 | // 以接口返回的 need_pay 为准:1=需要支付,0=不需要支付 |
| 162 | if (Number(need_pay) === 1 || need_pay === true) { | 190 | if (Number(need_pay) === 1 || need_pay === true) { |
| 163 | Taro.showLoading({ title: '支付准备中...' }); | 191 | Taro.showLoading({ title: '支付准备中...' }); |
| 164 | - const payParams = await wxPayAPI({ pay_id }); // 参数接口 | 192 | + let payParams = null; |
| 193 | + try { | ||
| 194 | + payParams = await wxPayAPI({ pay_id }); // 参数接口 | ||
| 195 | + } finally { | ||
| 165 | Taro.hideLoading(); | 196 | Taro.hideLoading(); |
| 197 | + } | ||
| 166 | 198 | ||
| 167 | - if (payParams.code) { | 199 | + if (payParams && payParams.code == 1) { |
| 168 | let pay_params = payParams.data; | 200 | let pay_params = payParams.data; |
| 169 | Taro.requestPayment({ | 201 | Taro.requestPayment({ |
| 170 | timeStamp: pay_params.timeStamp, | 202 | timeStamp: pay_params.timeStamp, |
| ... | @@ -178,21 +210,22 @@ const submitBtn = async () => { | ... | @@ -178,21 +210,22 @@ const submitBtn = async () => { |
| 178 | go('/success', { pay_id }); | 210 | go('/success', { pay_id }); |
| 179 | }, | 211 | }, |
| 180 | fail(res) { | 212 | fail(res) { |
| 181 | - // 支付取消或失败,保留 pending_pay_id,允许用户再次点击按钮尝试支付同一订单 | 213 | + refreshVisitorList({ reset_checked: true }).catch(() => {}); |
| 182 | - // 只有当 wxPayAPI 获取支付参数失败时(如下面的 else 分支),才重置 ID 以便重新创建订单 | 214 | + Taro.showToast({ title: '支付未完成,可再次点击提交订单继续支付', icon: 'none' }); |
| 183 | - Taro.showToast({ title: '支付失败,请重试', icon: 'none' }); | ||
| 184 | } | 215 | } |
| 185 | }) | 216 | }) |
| 186 | } else { | 217 | } else { |
| 187 | - pending_pay_id.value = null; // 支付参数获取失败,重置订单ID | 218 | + refreshVisitorList({ reset_checked: true }).catch(() => {}); |
| 188 | - pending_need_pay.value = null; // 支付参数获取失败,重置是否需要支付标志 | 219 | + Taro.showToast({ title: payParams?.msg || '获取支付信息失败', icon: 'none' }); |
| 189 | - Taro.showToast({ title: payParams.msg || '获取支付信息失败', icon: 'none' }); | ||
| 190 | } | 220 | } |
| 191 | } else { | 221 | } else { |
| 192 | - pending_pay_id.value = null; // 不需要支付,重置订单ID | 222 | + pending_pay_id.value = null; |
| 193 | - pending_need_pay.value = null; // 不需要支付,重置是否需要支付标志 | 223 | + pending_need_pay.value = null; |
| 194 | go('/success', { pay_id }); | 224 | go('/success', { pay_id }); |
| 195 | } | 225 | } |
| 226 | + } finally { | ||
| 227 | + is_submitting.value = false; | ||
| 228 | + } | ||
| 196 | } | 229 | } |
| 197 | 230 | ||
| 198 | useDidShow(async () => { | 231 | useDidShow(async () => { |
| ... | @@ -202,12 +235,7 @@ useDidShow(async () => { | ... | @@ -202,12 +235,7 @@ useDidShow(async () => { |
| 202 | price.value = params.price || 0; | 235 | price.value = params.price || 0; |
| 203 | period_type.value = params.period_type || ''; | 236 | period_type.value = params.period_type || ''; |
| 204 | 237 | ||
| 205 | - if (date.value && time.value) { | 238 | + await refreshVisitorList(); |
| 206 | - const { code, data } = await personListAPI({ reserve_date: date.value, begin_time: time.value.split('-')[0], end_time: time.value.split('-')[1], period_type: period_type.value }); | ||
| 207 | - if (code) { | ||
| 208 | - visitorList.value = data || []; | ||
| 209 | - } | ||
| 210 | - } | ||
| 211 | }); | 239 | }); |
| 212 | </script> | 240 | </script> |
| 213 | 241 | ... | ... |
-
Please register or login to post a comment