fix(overseas): expose permission-gated cargo discard review

This commit is contained in:
2026-10-04 16:57:16 +08:00
parent 1d73a40a07
commit cc973c72c0
6 changed files with 152 additions and 1 deletions
@@ -17,6 +17,7 @@ import QueryToolbar, { type QueryField, type QueryModel } from '@/shared/compone
import RowActions, { type RowActionItem } from '@/shared/components/RowActions.vue'
import { changeContainerReceivingWarehouse, convertLastMileContainerToInboundPlans, createManualInboundPlan, downloadLastMileOrders, getContainerInboundPlanPreview, getContainerPlanProgress, getLastMileOrderManualNodes, listContainerPlanProgress, listLastMileOrders, reviewDirectRelabelOrder, reviewReturnOrder, transferLastMileOrders, updateLastMileOrderHold, updateLastMileOrderManualNodes, type ContainerInboundPlanPreviewDto, type ContainerInboundPlanPreviewGroupDto, type ContainerInboundPlanPreviewOrderDto, type ContainerPlanProgressDetailDto, type ContainerPlanProgressSummaryDto, type ManualNodeCode } from '../api/lastMileOrders'
import OrderReferenceText from '../components/OrderReferenceText.vue'
import { reviewCargoDiscard } from '../api/lastMileOrders'
import WarehouseTransferReviewDialog from '../components/WarehouseTransferReviewDialog.vue'
import { confirmRelabelCompletion, createReturnPackingPlan, getRelabelReviewTask, returnRelabelForRework, type ReturnPackingPlanBox } from '../api/relabelOrders'
import { useAccessPreviewStore } from '@/core/access/accessPreview'
@@ -843,6 +844,44 @@ watch(containerConvertOpen, (open) => {
containerConversionIdempotencyKey = ''
})
const discardReviewBusy = ref(false)
function canReviewDiscard(row: LastMileOrderListItem) {
return access.can(permission.cargoDiscardApprove)
&& row.orderTypeCode === 'CARGO_DISCARD'
&& row.currentStatusCode === 'PENDING_REVIEW'
&& Boolean(row.orderNo && row.orderNo !== '—')
&& /^[1-9]\d*$/.test(row.customerId)
}
async function reviewDiscard(row: LastMileOrderListItem) {
if (discardReviewBusy.value || !canReviewDiscard(row)) return
discardReviewBusy.value = true
try {
let decision: 'APPROVE' | 'REJECT' = 'APPROVE'
let remark: string | undefined
try {
await ElMessageBox.confirm(`请核对废弃申请 ${row.orderNo},确认审核结论。`, '废弃申请审核', {
customClass: 'admin-density-confirm', confirmButtonText: '审核通过', cancelButtonText: '驳回', distinguishCancelAndClose: true,
})
} catch (action) {
if (action !== 'cancel') throw action
const { value } = await ElMessageBox.prompt('请填写驳回原因', '驳回废弃申请', {
customClass: 'admin-density-confirm', inputType: 'textarea',
inputValidator: (input) => Boolean(input?.trim()) && input.trim().length <= 1000 || '请填写 1 至 1000 字驳回原因',
confirmButtonText: '确认驳回', cancelButtonText: '取消',
})
decision = 'REJECT'
remark = value.trim()
}
await reviewCargoDiscard(row.orderNo, row.customerId, decision, remark)
ElMessage.success(decision === 'APPROVE' ? '废弃申请已审核通过' : '废弃申请已驳回')
await load()
} catch (error) {
if (error !== 'cancel' && error !== 'close') ElMessage.error(getApiErrorDetails(error, '废弃申请审核失败').message)
} finally {
discardReviewBusy.value = false
}
}
async function reviewReturn(source: object) {
const row = source as LastMileOrderListItem
const returnNo = row.sourceOrderNo
@@ -906,6 +945,7 @@ function lastMileRowActions(row: LastMileOrderListItem): RowActionItem[] {
const inboundPlanCreated = hasInboundPlan(row)
return [
{ key: 'detail', label: '查看', priority: 500 },
{ key: 'review-discard', label: '审核', priority: 480, tone: 'warning', visible: canReviewDiscard(row), disabled: discardReviewBusy.value },
{ key: 'review-direct-relabel', label: '审核', priority: 470, tone: 'warning', visible: access.can(permission.lastMileOrderTransfer) && row.orderTypeCode === 'RELABEL_APPLICATION' && row.currentStatusCode === 'PENDING_REVIEW' },
{ key: 'review-return', label: '审核', priority: 460, tone: 'warning', visible: access.can(permission.returnOrderReview) && row.orderTypeCode === 'RETURN_RELABEL' && row.currentStatusCode === 'PENDING_REVIEW' },
{ key: 'review', label: '审核', priority: 450, tone: 'warning', visible: access.can(permission.warehouseTransferApprove) && row.orderTypeCode === 'WAREHOUSE_TRANSFER' && row.currentStatusCode === 'PENDING_REVIEW' },
@@ -918,6 +958,7 @@ function lastMileRowActions(row: LastMileOrderListItem): RowActionItem[] {
}
function handleLastMileRowAction(command: string, row: LastMileOrderListItem) {
if (command === 'detail') openDetail(row)
else if (command === 'review-discard') void reviewDiscard(row)
else if (command === 'review-direct-relabel') void reviewDirectRelabel(row)
else if (command === 'review-return') void reviewReturn(row)
else if (command === 'review') openTransferReview(row)