优化
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
<script setup lang="ts">
|
||||
import { computed, onMounted, reactive, ref, watch } from 'vue'
|
||||
import { useRoute, useRouter } from 'vue-router'
|
||||
import { ElMessage, type FormInstance } from 'element-plus'
|
||||
import { ElMessage, ElMessageBox, type FormInstance } from 'element-plus'
|
||||
import TransportDemandForm from './TransportDemandForm.vue'
|
||||
import OrderFundingStatus from './OrderFundingStatus.vue'
|
||||
import { createTransportDemandForm, transportDemandError, buildTransportDemand, type TransportDemandForm as DemandFormModel } from '../transportDemandForm'
|
||||
@@ -10,6 +10,7 @@ import QueryToolbar, { type QueryField, type QueryModel } from '@/components/com
|
||||
import type { TableAction } from '@/components/common/tableActions'
|
||||
import { useAuthStore } from '@/modules/auth/public'
|
||||
import {
|
||||
cancelTruckOrder,
|
||||
createTransport,
|
||||
getBusinessOrder,
|
||||
listBusinessOrders,
|
||||
@@ -108,7 +109,17 @@ const queryFields = computed<QueryField[]>(() => [
|
||||
label: '状态',
|
||||
type: 'select',
|
||||
placeholder: '全部',
|
||||
options: [
|
||||
options: props.kind === 'trucking' ? [
|
||||
{ label: '订单受理中', value: 'FUNDING_PENDING' },
|
||||
{ label: '订单处理失败', value: 'FUNDING_FAILED' },
|
||||
{ label: '待审核', value: 'PENDING_REVIEW' },
|
||||
{ label: '待排车', value: 'PENDING_DISPATCH' },
|
||||
{ label: '待取货', value: 'DISPATCHED' },
|
||||
{ label: '运输中', value: 'IN_TRANSIT' },
|
||||
{ label: '已完成', value: 'COMPLETED' },
|
||||
{ label: '已拒绝', value: 'REJECTED' },
|
||||
{ label: '已取消', value: 'CANCELLED' },
|
||||
] : [
|
||||
{ label: '订单受理中', value: 'FUNDING_PENDING' },
|
||||
{ label: '订单处理失败', value: 'FUNDING_FAILED' },
|
||||
{ label: '待审核', value: 'PENDING_REVIEW' },
|
||||
@@ -155,6 +166,24 @@ const tableColumns = computed<DataTableColumn[]>(() => [
|
||||
})),
|
||||
])
|
||||
|
||||
const canCancelTruck = computed(() => props.kind === 'trucking' && detail.value?.summary.status === 'PENDING_REVIEW'
|
||||
&& auth.hasPermission('merchant:cross-border:domestic-trucking:edit'))
|
||||
/** 取消前核对客户意愿,失败保留订单并刷新服务端状态。 */
|
||||
async function cancelTruck() {
|
||||
if (!canCancelTruck.value || !detail.value || submitting.value) return
|
||||
let reason: string
|
||||
try {
|
||||
const result = await ElMessageBox.prompt('请填写取消原因', '取消订单', { inputValidator: value => Boolean(value?.trim()) || '请填写取消原因', confirmButtonText: '确认取消', cancelButtonText: '保留订单', type: 'warning' })
|
||||
reason = result.value.trim()
|
||||
} catch { return }
|
||||
submitting.value = true
|
||||
try {
|
||||
detail.value = await cancelTruckOrder(detail.value.summary.orderNo, { version: detail.value.summary.version, status: 'CANCELLED', idempotencyKey: idempotencyKey(), remark: reason })
|
||||
ElMessage.success('订单已取消')
|
||||
} catch (cause) { ElMessage.error(errorMessage(cause)); await loadDetail() }
|
||||
finally { submitting.value = false }
|
||||
}
|
||||
|
||||
const detailStatus = computed(() => detail.value ? statusLabel(detail.value.summary.status) : '—')
|
||||
|
||||
function emptyForm(): BusinessForm { return createTransportDemandForm() }
|
||||
@@ -224,7 +253,8 @@ function getRowActions(candidate: object): TableAction[] {
|
||||
}
|
||||
|
||||
function detailFieldClass(label: unknown) {
|
||||
return ['备注', props.kind === 'trucking' ? '取货地址' : '起运地址', props.kind === 'trucking' ? '送达地址' : '目的地址'].includes(String(label)) ? 'is-wide' : ''
|
||||
if (label === '备注') return 'is-full'
|
||||
return [props.kind === 'trucking' ? '取货地址' : '起运地址', props.kind === 'trucking' ? '送达地址' : '目的地址'].includes(String(label)) ? 'is-wide' : ''
|
||||
}
|
||||
|
||||
const listRouteName = computed(() => ({
|
||||
@@ -295,7 +325,7 @@ onMounted(() => { if (props.detailPage) void loadDetail(); else if (!props.creat
|
||||
<h2>{{ configuration.title }}下单</h2>
|
||||
|
||||
</div>
|
||||
<el-button v-if="kind === 'looseboard'" @click="returnToList">返回列表</el-button>
|
||||
<el-button @click="returnToList">返回列表</el-button>
|
||||
</header>
|
||||
|
||||
<template v-if="mode === 'list'">
|
||||
@@ -315,13 +345,13 @@ onMounted(() => { if (props.detailPage) void loadDetail(); else if (!props.creat
|
||||
<section v-else-if="mode === 'detail'" class="business-detail-page" aria-label="订单详情">
|
||||
<header class="business-detail-heading">
|
||||
<div class="business-detail-heading-main"><el-button link type="primary" @click="returnToList">← 返回列表</el-button><div><h2>{{ detail?.summary.orderNo || '订单详情' }}</h2></div></div>
|
||||
<div class="business-detail-heading-actions"><el-tag :type="statusTone(detail?.summary.status)" effect="light">{{ detailStatus }}</el-tag><el-button :disabled="loading" @click="loadDetail">刷新</el-button></div>
|
||||
<div class="business-detail-heading-actions"><el-button v-if="canCancelTruck" type="danger" :loading="submitting" :disabled="loading" @click="cancelTruck">取消订单</el-button><el-tag :type="statusTone(detail?.summary.status)" effect="light">{{ detailStatus }}</el-tag><el-button :disabled="loading" @click="loadDetail">刷新</el-button></div>
|
||||
</header>
|
||||
<OrderFundingStatus v-if="kind === 'trucking' && detail" kind="trucking" :order-no="detail.summary.orderNo" :status="detail.summary.status" :can-retry="canCreate" @changed="loadDetail" />
|
||||
<div v-if="error" class="business-detail-error" role="alert"><strong>{{ error }}</strong><el-button size="small" @click="loadDetail">重新加载</el-button></div>
|
||||
<section v-else class="business-detail-section">
|
||||
<h3>订单信息</h3>
|
||||
<dl class="detail-grid" :class="{ 'trucking-detail-grid': kind === 'trucking' }">
|
||||
<dl class="detail-grid" :class="{ 'trucking-detail-grid': kind === 'trucking', 'looseboard-detail-grid': kind === 'looseboard' }">
|
||||
<div v-for="field in detailFields" :key="String(field[0])" :class="detailFieldClass(field[0])"><dt>{{ field[0] }}</dt><dd>{{ text(field[1]) }}</dd></div>
|
||||
</dl>
|
||||
</section>
|
||||
@@ -374,6 +404,8 @@ onMounted(() => { if (props.detailPage) void loadDetail(); else if (!props.creat
|
||||
.detail-grid div { display: grid; min-width: 0; min-height: 34px; grid-template-columns: 76px minmax(0, 1fr); align-items: center; gap: 7px; padding: 3px 8px; border-right: 1px solid var(--border); border-bottom: 1px solid var(--border); }
|
||||
.trucking-detail-grid div { grid-template-columns: 112px minmax(0, 1fr); }
|
||||
.detail-grid div.is-wide { grid-column: span 2; }
|
||||
.detail-grid div.is-full { grid-column: 1 / -1; }
|
||||
.looseboard-detail-grid { grid-auto-flow: row dense; }
|
||||
.detail-grid dt { color: var(--muted); font-size: 10px; white-space: nowrap; }
|
||||
.arrangement-grid div { grid-template-columns: 124px minmax(0, 1fr); }
|
||||
.arrangement-grid dt { white-space: normal; overflow-wrap: anywhere; }
|
||||
|
||||
Reference in New Issue
Block a user