新增打单产品明细保存接口,优化附加费管理逻辑

This commit is contained in:
wuweihua
2026-11-12 16:53:40 +08:00
parent 90147ed4e3
commit 8ca5af1ff0
10 changed files with 200 additions and 97 deletions
@@ -87,7 +87,7 @@
</div>
<el-drawer v-model="detailVisible" :title="detailTitle" size="78%" destroy-on-close append-to-body>
<pay-config-detail :product="detailProduct" :editable="false" :bill-select="true" />
<pay-config-detail :product="detailProduct" :editable="false" />
<template #footer>
<el-button @click="detailVisible = false">关闭</el-button>
</template>
@@ -187,9 +187,7 @@ async function onFile(uploadFile) {
const data = res.data || {}
data.products = (data.products || []).map((item, index) => ({
...item,
rowKey: `${item.sheetName || ''}-${item.productName || ''}-${index}`,
// 解析后默认不计费,勾选后才入 pay_surcharge
surcharges: (item.surcharges || []).map(fee => ({ ...fee, needBill: fee?.needBill === true }))
rowKey: `${item.sheetName || ''}-${item.productName || ''}-${index}`
}))
preview.value = data
const picked = data.products.filter(row => canSelect(row))
@@ -312,17 +310,16 @@ async function submit(payload = {}) {
const productsPayload = (payload.products && payload.products.length)
? payload.products
: selected.value.map(row => ({ ...row, productType: 'AR' }))
const filteredProducts = productsPayload.map(product => ({
const productsForSave = productsPayload.map(product => ({
...product,
productType: product.productType || 'AR',
surcharges: (product.surcharges || []).filter(fee => fee && fee.needBill === true)
productType: product.productType || 'AR'
}))
const res = await saveLabelImport({
priceSetId: payload.priceSetId || null,
priceSetName: String(payload.priceSetName || '').trim(),
priceSetNote: payload.priceSetNote || '',
overwrite: payload.overwrite != null ? payload.overwrite : overwrite.value,
products: filteredProducts
products: productsForSave
})
const data = res.data || {}
return {
@@ -22,11 +22,11 @@
<el-table-column :label="colTerm" min-width="180" align="center">
<template #default="{ row }">{{ termText(row) }}</template>
</el-table-column>
<el-table-column :label="colStatus" width="90" align="center">
<!-- <el-table-column :label="colStatus" width="90" align="center">
<template #default="{ row }">
<el-tag :type="termStatusTag(row.termStatus)" size="small">{{ termStatusText(row.termStatus) }}</el-tag>
</template>
</el-table-column>
</el-table-column> -->
<el-table-column prop="weightCount" :label="colWeight" width="80" align="center" />
<el-table-column prop="surchargeCount" :label="colSc" width="80" align="center" />
<el-table-column :label="colBoundChannels" min-width="180" show-overflow-tooltip>
@@ -34,16 +34,29 @@
</el-table-column>
<el-table-column :label="colAction" width="160" align="center" fixed="right">
<template #default="{ row }">
<el-button link type="primary" @click="openProduct(row)" v-hasPermi="['price:label:query']">查看</el-button>
<el-button link type="primary" @click="openProduct(row)" v-hasPermi="['price:label:query', 'price:label:edit']">编辑</el-button>
<el-button link type="primary" @click="openBindList(row)" v-hasPermi="['price:label:edit']">绑定</el-button>
</template>
</el-table-column>
</el-table>
<el-drawer v-model="detailVisible" :title="detailTitle" size="78%" destroy-on-close append-to-body>
<pay-config-detail v-loading="detailLoading" :product="detail" :editable="false" />
<pay-config-detail
v-loading="detailLoading"
:product="detail"
:editable="canEditDetail"
:saving-row-key="savingRowKey"
@save-row="saveDetailRow"
/>
<template #footer>
<el-button @click="detailVisible = false">关闭</el-button>
<el-button
v-if="canEditDetail"
type="primary"
:loading="detailSaving"
v-hasPermi="['price:label:edit']"
@click="saveDetail"
>保存明细</el-button>
</template>
</el-drawer>
@@ -125,9 +138,11 @@
import {
listLabelProducts,
getLabelProduct,
updateLabelProduct,
listLabelProductChannels,
replaceLabelProductChannels
} from '@/api/price/label'
import { checkPermi } from '@/utils/permission'
import { listChannelOptions } from '@/api/masterdata/serviceChannel'
import PayConfigDetail from '@/views/price/basic/pay/components/PayConfigDetail.vue'
@@ -144,7 +159,10 @@ const rows = ref([])
const keyword = ref('')
const detailVisible = ref(false)
const detailLoading = ref(false)
const detailSaving = ref(false)
const savingRowKey = ref('')
const detail = ref(null)
const canEditDetail = computed(() => checkPermi(['price:label:edit']))
const bindListVisible = ref(false)
const bindListLoading = ref(false)
@@ -258,9 +276,66 @@ async function load() {
}
}
function cleanMoney(product) {
if (!product) return
;(product.weightBands || []).forEach(row => {
if (row && row.price === '') row.price = null
})
;(product.surcharges || []).forEach(row => {
if (row && row.amount === '') row.amount = null
})
}
async function persistDetail() {
if (!detail.value?.productId) {
throw new Error('NO_PRODUCT')
}
cleanMoney(detail.value)
await updateLabelProduct(detail.value)
const termId = detail.value.termId
const res = await getLabelProduct(detail.value.productId, termId)
detail.value = res.data || detail.value
await load()
emit('changed')
}
async function saveDetail() {
if (!detail.value || detailSaving.value || savingRowKey.value) return
detailSaving.value = true
try {
await persistDetail()
proxy.$modal.msgSuccess('明细已保存')
} catch (e) {
// request 拦截器已提示
} finally {
detailSaving.value = false
}
}
async function saveDetailRow(payload) {
if (!detail.value || savingRowKey.value || detailSaving.value) {
payload?.done?.(false)
return
}
savingRowKey.value = payload?.rowKey || 'row'
let ok = false
try {
await persistDetail()
ok = true
proxy.$modal.msgSuccess('该行已保存')
} catch (e) {
ok = false
} finally {
savingRowKey.value = ''
payload?.done?.(ok)
}
}
async function openProduct(row) {
detailVisible.value = true
detailLoading.value = true
detailSaving.value = false
savingRowKey.value = ''
detail.value = null
try {
const res = await getLabelProduct(row.productId, row.termId)
@@ -38,11 +38,11 @@
<el-table-column label="失效时间" min-width="170" align="center">
<template #default="{ row }">{{ formatHour(row.expireTime) || '-' }}</template>
</el-table-column>
<el-table-column label="状态" width="100" align="center">
<!-- <el-table-column label="状态" width="100" align="center">
<template #default="{ row }">
<el-tag :type="statusTag(row.status)" size="small">{{ statusText(row.status) }}</el-tag>
</template>
</el-table-column>
</el-table-column> -->
<el-table-column label="产品数" width="90" align="center">
<template #default="{ row }">{{ row.productCount || 0 }}</template>
</el-table-column>