feat: 后台延期订单详情可作废待支付订单
Some checks failed
构建并部署前端到测试环境 / deploy (push) Failing after 7m32s

作废前后端先查单,已支付则按支付成功办理延期并拒绝作废;作废后同一套餐可重新下单
This commit is contained in:
邹进
2026-11-07 20:33:46 +09:00
parent 8fe65ca66d
commit 227dd63bb8
2 changed files with 64 additions and 0 deletions

View File

@@ -24,6 +24,10 @@
>支付截止:{{ data.expire_at ? formatDateTime(data.expire_at) : '-' }}</p
></div
>
<div v-if="canCloseOrder" class="silence-order-actions">
<ElButton type="danger" plain :loading="handling" @click="closeOrder">作废订单</ElButton>
<span class="silence-order-tip">作废后同一套餐可以重新下单;已支付的订单不能作废。</span>
</div>
<ElAlert
v-if="kind === 'orders' && data.status === 'pending_approval'"
title="审批中,尚未生效。请以订单完成状态及实际截止日为准。"
@@ -209,6 +213,47 @@
void load()
}
)
// 作废待支付订单:需要发起延期的权限(与生成二维码相同)
const canCloseOrder = computed(
() =>
props.kind === 'orders' &&
data.value?.status === 'pending_payment' &&
data.value?.payment_method !== 'offline' &&
allowed.value &&
hasAuth(P.extend)
)
async function closeOrder() {
if (handling.value || !data.value) return
const scope = pollingScope(user),
path = route.fullPath,
id = silenceId(Number(data.value.id))
handling.value = true
try {
requireGatewayAccess(canCloseOrder.value)
const { value } = await ElMessageBox.prompt(
'作废后该订单不能再支付,同一套餐可以重新下单。作废前会先向支付渠道确认,已支付的会按支付成功办理延期。可填写作废原因(选填)。',
'作废延期订单',
{
type: 'warning',
confirmButtonText: '确认作废',
cancelButtonText: '取消',
inputPlaceholder: '作废原因(选填)'
}
)
requireGatewayAccess(
active && canCloseOrder.value && scope === pollingScope(user) && path === route.fullPath
)
silenceData(await Service.closeOrder(id, value?.trim() || undefined))
if (active && scope === pollingScope(user) && path === route.fullPath) await load()
} catch (e) {
if (active && e !== 'cancel' && e !== 'close') {
actionError.value = gatewayError(e)
await load()
}
} finally {
handling.value = false
}
}
async function handle(row: Record<string, any>, action: 'retry' | 'close') {
if (handling.value) return
const scope = pollingScope(user),
@@ -281,4 +326,16 @@
margin: 4px;
}
}
.silence-order-actions {
display: flex;
flex-wrap: wrap;
gap: 12px;
align-items: center;
margin: 12px 0;
}
.silence-order-tip {
font-size: 13px;
color: var(--el-text-color-secondary);
}
</style>