Merge branch 'master' into feature/bfi-api-rate
# Conflicts: # src/components/vehicle-attachment-table/main.vue # src/option/payment/paymentApplication.js # src/views/payment/payment-application.vue # src/views/payment/receipt-claim-record.vue # src/views/vehicle/customer-archive.vue
This commit is contained in:
@@ -529,7 +529,7 @@ export default {
|
||||
|
||||
<style scoped lang="scss">
|
||||
.bill-ledger-form-page__form :deep(.el-form-item) {
|
||||
margin-bottom: 14px;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
.bill-ledger-form-page__basic-grid {
|
||||
display: grid;
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
<template>
|
||||
<basic-container class="bill-ledger-page">
|
||||
<bill-ledger-search
|
||||
v-if="searchVisible"
|
||||
:query="query"
|
||||
:loading="loading"
|
||||
@search="handleSearch"
|
||||
@@ -20,10 +21,12 @@
|
||||
:rows="rows"
|
||||
:loading="loading"
|
||||
:page="page"
|
||||
v-model:search-visible="searchVisible"
|
||||
@add="openCreate"
|
||||
@view="openView"
|
||||
@edit="openEdit"
|
||||
@delete="handleDelete"
|
||||
@refresh="loadData"
|
||||
@page-change="handlePageChange"
|
||||
@size-change="handleSizeChange"
|
||||
/>
|
||||
@@ -124,6 +127,7 @@ export default {
|
||||
return {
|
||||
query: emptyQuery(),
|
||||
counts: { all: 0, within30: 0, within90: 0, over90: 0 },
|
||||
searchVisible: true,
|
||||
rows: [],
|
||||
loading: false,
|
||||
page: { current: 1, size: 10, total: 0 },
|
||||
|
||||
@@ -367,7 +367,7 @@ export default {
|
||||
|
||||
<style scoped lang="scss">
|
||||
.bill-payment-form-page__form :deep(.el-form-item) {
|
||||
margin-bottom: 14px;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
.bill-payment-form-page__form :deep(.el-input),
|
||||
.bill-payment-form-page__form :deep(.el-input-number),
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
<template>
|
||||
<basic-container class="bill-payment-page">
|
||||
<bill-payment-search
|
||||
v-if="searchVisible"
|
||||
:query="query"
|
||||
:loading="loading"
|
||||
@search="handleSearch"
|
||||
@@ -11,6 +12,7 @@
|
||||
:loading="loading"
|
||||
:page="page"
|
||||
:mk-enabled="mkEnabled"
|
||||
v-model:search-visible="searchVisible"
|
||||
@add="openCreate"
|
||||
@view="openView"
|
||||
@edit="openEdit"
|
||||
@@ -20,6 +22,7 @@
|
||||
@approve="handleApprove"
|
||||
@return="handleReturn"
|
||||
@void="handleVoid"
|
||||
@refresh="loadTable"
|
||||
@page-change="handlePageChange"
|
||||
@size-change="handleSizeChange"
|
||||
/>
|
||||
@@ -47,6 +50,7 @@ export default {
|
||||
data() {
|
||||
return {
|
||||
query: emptyQuery(),
|
||||
searchVisible: true,
|
||||
rows: [],
|
||||
loading: false,
|
||||
page: { current: 1, size: 10, total: 0 },
|
||||
|
||||
@@ -4,11 +4,19 @@
|
||||
<el-button v-if="hasPermission('bill_ledger_add')" type="primary" @click="$emit('add')">
|
||||
新增
|
||||
</el-button>
|
||||
<table-header-tools
|
||||
:columns="columns"
|
||||
v-model:visible-column-keys="visibleColumnKeys"
|
||||
v-model:table-size="tableSize"
|
||||
:search-visible="searchVisible"
|
||||
@update:search-visible="$emit('update:searchVisible', $event)"
|
||||
@refresh="$emit('refresh')"
|
||||
/>
|
||||
</div>
|
||||
<el-table v-loading="loading" :data="rows" border>
|
||||
<el-table v-loading="loading" :data="rows" :size="tableSize" border>
|
||||
<el-table-column type="index" label="序号" width="64" fixed="left" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
v-for="column in visibleColumns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
@@ -60,20 +68,30 @@
|
||||
<script>
|
||||
import { mapGetters } from 'vuex';
|
||||
import { billLedgerTableColumns } from '@/option/payment/billLedger';
|
||||
import TableHeaderTools from '@/components/table-header-tools/main.vue';
|
||||
|
||||
export default {
|
||||
name: 'BillLedgerTable',
|
||||
components: { TableHeaderTools },
|
||||
props: {
|
||||
rows: { type: Array, default: () => [] },
|
||||
loading: { type: Boolean, default: false },
|
||||
page: { type: Object, required: true },
|
||||
searchVisible: { type: Boolean, default: true },
|
||||
},
|
||||
emits: ['add', 'view', 'edit', 'delete', 'page-change', 'size-change'],
|
||||
emits: ['add', 'view', 'edit', 'delete', 'page-change', 'size-change', 'refresh', 'update:searchVisible'],
|
||||
data() {
|
||||
return { columns: billLedgerTableColumns };
|
||||
return {
|
||||
columns: billLedgerTableColumns,
|
||||
visibleColumnKeys: billLedgerTableColumns.map(column => column.prop),
|
||||
tableSize: 'default',
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission']),
|
||||
visibleColumns() {
|
||||
return this.columns.filter(column => this.visibleColumnKeys.includes(column.prop));
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
hasPermission(code) {
|
||||
@@ -96,7 +114,7 @@ export default {
|
||||
.bill-ledger-table__toolbar {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: flex-start;
|
||||
justify-content: space-between;
|
||||
padding: 12px 0;
|
||||
}
|
||||
.bill-ledger-table__links {
|
||||
|
||||
@@ -4,11 +4,19 @@
|
||||
<el-button v-if="hasPermission('bill_payment_add')" type="primary" @click="$emit('add')">
|
||||
新增
|
||||
</el-button>
|
||||
<table-header-tools
|
||||
:columns="columns"
|
||||
v-model:visible-column-keys="visibleColumnKeys"
|
||||
v-model:table-size="tableSize"
|
||||
:search-visible="searchVisible"
|
||||
@update:search-visible="$emit('update:searchVisible', $event)"
|
||||
@refresh="$emit('refresh')"
|
||||
/>
|
||||
</div>
|
||||
<el-table v-loading="loading" :data="rows" border>
|
||||
<el-table v-loading="loading" :data="rows" :size="tableSize" border>
|
||||
<el-table-column type="index" label="序号" width="64" fixed="left" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
v-for="column in visibleColumns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
@@ -61,7 +69,7 @@
|
||||
<el-link
|
||||
v-if="
|
||||
mkEnabled &&
|
||||
row.approvalStatus === 'reviewing' &&
|
||||
['reviewing', 'approved'].includes(row.approvalStatus) &&
|
||||
hasPermission('bill_payment_approve')
|
||||
"
|
||||
type="primary"
|
||||
@@ -115,15 +123,18 @@
|
||||
<script>
|
||||
import { mapGetters } from 'vuex';
|
||||
import { billPaymentTableColumns } from '@/option/payment/billPayment';
|
||||
import TableHeaderTools from '@/components/table-header-tools/main.vue';
|
||||
import { isAdministrator } from '@/utils/auth';
|
||||
|
||||
export default {
|
||||
name: 'BillPaymentTable',
|
||||
components: { TableHeaderTools },
|
||||
props: {
|
||||
rows: { type: Array, default: () => [] },
|
||||
loading: { type: Boolean, default: false },
|
||||
page: { type: Object, required: true },
|
||||
mkEnabled: { type: Boolean, default: false },
|
||||
searchVisible: { type: Boolean, default: true },
|
||||
},
|
||||
emits: [
|
||||
'add',
|
||||
@@ -137,12 +148,21 @@ export default {
|
||||
'void',
|
||||
'page-change',
|
||||
'size-change',
|
||||
'refresh',
|
||||
'update:searchVisible',
|
||||
],
|
||||
data() {
|
||||
return { columns: billPaymentTableColumns };
|
||||
return {
|
||||
columns: billPaymentTableColumns,
|
||||
visibleColumnKeys: billPaymentTableColumns.map(column => column.prop),
|
||||
tableSize: 'default',
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission', 'userInfo']),
|
||||
visibleColumns() {
|
||||
return this.columns.filter(column => this.visibleColumnKeys.includes(column.prop));
|
||||
},
|
||||
isAdmin() {
|
||||
return isAdministrator(this.userInfo);
|
||||
},
|
||||
@@ -173,7 +193,8 @@ export default {
|
||||
}
|
||||
.bill-payment-table__toolbar {
|
||||
display: flex;
|
||||
justify-content: flex-start;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
padding: 12px 0;
|
||||
}
|
||||
.bill-payment-table__links {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<basic-container class="invoice-page">
|
||||
<section class="invoice-page__search">
|
||||
<section v-if="searchVisible" class="invoice-page__search">
|
||||
<el-form :model="query" label-position="right" label-width="88px" @submit.prevent>
|
||||
<div class="invoice-page__search-grid">
|
||||
<el-form-item label="单据号">
|
||||
@@ -79,18 +79,26 @@
|
||||
>导出</el-button
|
||||
>
|
||||
</div>
|
||||
<div class="invoice-page__toolbar-right">
|
||||
<el-tooltip content="刷新" placement="top">
|
||||
<el-button text :icon="Refresh" @click="loadTable" />
|
||||
</el-tooltip>
|
||||
</div>
|
||||
<table-header-tools
|
||||
:columns="columns"
|
||||
v-model:visible-column-keys="visibleColumnKeys"
|
||||
v-model:table-size="tableSize"
|
||||
v-model:search-visible="searchVisible"
|
||||
@refresh="loadTable"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<el-table v-loading="loading" :data="rows" border @selection-change="selection = $event">
|
||||
<el-table
|
||||
v-loading="loading"
|
||||
:data="rows"
|
||||
:size="tableSize"
|
||||
border
|
||||
@selection-change="selection = $event"
|
||||
>
|
||||
<el-table-column type="selection" width="52" fixed="left" align="center" />
|
||||
<el-table-column type="index" label="序号" width="64" fixed="left" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
v-for="column in visibleColumns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
@@ -161,7 +169,7 @@
|
||||
v-if="
|
||||
mkEnabled &&
|
||||
hasPermission('invoice_application_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
['reviewing', 'approved'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="handleMkAudit(row)"
|
||||
@@ -218,12 +226,13 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { ArrowDown, ArrowUp, Refresh } from '@element-plus/icons-vue';
|
||||
import { ArrowDown, ArrowUp } from '@element-plus/icons-vue';
|
||||
import { mapGetters } from 'vuex';
|
||||
import * as XLSX from 'xlsx';
|
||||
import * as api from '@/api/payment/invoiceApplication';
|
||||
import * as formalSettlementApi from '@/api/settlement/formalSettlement';
|
||||
import { invoiceApplicationTableColumns } from '@/option/payment/invoiceApplication';
|
||||
import TableHeaderTools from '@/components/table-header-tools/main.vue';
|
||||
import organizationSearch from '@/mixins/organization-search';
|
||||
import { getMKApprovalUrl } from '@/api/system/business-process';
|
||||
import { loadMkEnabled, submitMkApprovalFlow } from '@/utils/mk-approval';
|
||||
@@ -239,17 +248,20 @@ const emptyQuery = () => ({
|
||||
|
||||
export default {
|
||||
name: 'InvoiceApplication',
|
||||
components: { TableHeaderTools },
|
||||
mixins: [organizationSearch],
|
||||
data() {
|
||||
return {
|
||||
ArrowDown,
|
||||
ArrowUp,
|
||||
Refresh,
|
||||
query: emptyQuery(),
|
||||
searchExpanded: false,
|
||||
searchVisible: true,
|
||||
tableSize: 'default',
|
||||
approvalStatusOptions: api.approvalStatusOptions,
|
||||
kingdeeStatusOptions: api.kingdeeStatusOptions,
|
||||
columns: invoiceApplicationTableColumns,
|
||||
visibleColumnKeys: invoiceApplicationTableColumns.map(column => column.prop),
|
||||
rows: [],
|
||||
selection: [],
|
||||
loading: false,
|
||||
@@ -260,6 +272,9 @@ export default {
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission']),
|
||||
visibleColumns() {
|
||||
return this.columns.filter(column => this.visibleColumnKeys.includes(column.prop));
|
||||
},
|
||||
},
|
||||
mounted() {
|
||||
this.loadOrganizationOptions();
|
||||
@@ -531,7 +546,6 @@ export default {
|
||||
padding: 12px 0;
|
||||
}
|
||||
.invoice-page__toolbar-left,
|
||||
.invoice-page__toolbar-right,
|
||||
.invoice-page__links {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
@@ -610,7 +610,7 @@ export default {
|
||||
padding-bottom: 72px;
|
||||
}
|
||||
.receipt-form-page__form :deep(.el-form-item) {
|
||||
margin-bottom: 14px;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
.receipt-form-page__form :deep(.el-select),
|
||||
.receipt-form-page__form :deep(.el-input-number) {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<basic-container class="receipt-page">
|
||||
<section class="receipt-page__search">
|
||||
<section v-if="searchVisible" class="receipt-page__search">
|
||||
<el-form :model="query" label-position="right" label-width="88px" @submit.prevent>
|
||||
<div class="receipt-page__search-grid">
|
||||
<el-form-item label="发票号码">
|
||||
@@ -85,18 +85,26 @@
|
||||
>导出</el-button
|
||||
>
|
||||
</div>
|
||||
<div class="receipt-page__toolbar-right">
|
||||
<el-tooltip content="刷新" placement="top">
|
||||
<el-button text :icon="Refresh" @click="loadTable" />
|
||||
</el-tooltip>
|
||||
</div>
|
||||
<table-header-tools
|
||||
:columns="columns"
|
||||
v-model:visible-column-keys="visibleColumnKeys"
|
||||
v-model:table-size="tableSize"
|
||||
v-model:search-visible="searchVisible"
|
||||
@refresh="loadTable"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<el-table v-loading="loading" :data="rows" border @selection-change="selection = $event">
|
||||
<el-table
|
||||
v-loading="loading"
|
||||
:data="rows"
|
||||
:size="tableSize"
|
||||
border
|
||||
@selection-change="selection = $event"
|
||||
>
|
||||
<el-table-column type="selection" width="52" fixed="left" align="center" />
|
||||
<el-table-column type="index" label="序号" width="64" fixed="left" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
v-for="column in visibleColumns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
@@ -150,7 +158,7 @@
|
||||
v-if="
|
||||
mkEnabled &&
|
||||
hasPermission('invoice_receipt_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
['reviewing', 'approved'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="handleMkAudit(row)"
|
||||
@@ -203,11 +211,12 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { ArrowDown, ArrowUp, Refresh } from '@element-plus/icons-vue';
|
||||
import { ArrowDown, ArrowUp } from '@element-plus/icons-vue';
|
||||
import { mapGetters } from 'vuex';
|
||||
import * as XLSX from 'xlsx';
|
||||
import * as api from '@/api/payment/invoiceReceipt';
|
||||
import { invoiceReceiptTableColumns } from '@/option/payment/invoiceReceipt';
|
||||
import TableHeaderTools from '@/components/table-header-tools/main.vue';
|
||||
import organizationSearch from '@/mixins/organization-search';
|
||||
import { getMKApprovalUrl } from '@/api/system/business-process';
|
||||
import { loadMkEnabled, submitMkApprovalFlow } from '@/utils/mk-approval';
|
||||
@@ -224,17 +233,20 @@ const emptyQuery = () => ({
|
||||
|
||||
export default {
|
||||
name: 'InvoiceReceipt',
|
||||
components: { TableHeaderTools },
|
||||
mixins: [organizationSearch],
|
||||
data() {
|
||||
return {
|
||||
ArrowDown,
|
||||
ArrowUp,
|
||||
Refresh,
|
||||
query: emptyQuery(),
|
||||
searchExpanded: false,
|
||||
searchVisible: true,
|
||||
tableSize: 'default',
|
||||
approvalStatusOptions: api.approvalStatusOptions,
|
||||
kingdeePushStatusOptions: api.kingdeePushStatusOptions,
|
||||
columns: invoiceReceiptTableColumns,
|
||||
visibleColumnKeys: invoiceReceiptTableColumns.map(column => column.prop),
|
||||
rows: [],
|
||||
selection: [],
|
||||
loading: false,
|
||||
@@ -245,6 +257,9 @@ export default {
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission']),
|
||||
visibleColumns() {
|
||||
return this.columns.filter(column => this.visibleColumnKeys.includes(column.prop));
|
||||
},
|
||||
},
|
||||
mounted() {
|
||||
this.loadOrganizationOptions();
|
||||
@@ -461,7 +476,6 @@ export default {
|
||||
padding: 12px 0;
|
||||
}
|
||||
.receipt-page__toolbar-left,
|
||||
.receipt-page__toolbar-right,
|
||||
.receipt-page__links {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
@@ -36,23 +36,25 @@
|
||||
<el-col v-if="isSettlementRelatedType" :span="6"
|
||||
><el-form-item label="结算单号" prop="referenceId">
|
||||
<div class="payment-form-page__settlement-nos">
|
||||
<template v-if="referenceSettlementLinks.length">
|
||||
<el-link
|
||||
v-for="item in referenceSettlementLinks"
|
||||
:key="`${item.id || item.settlementNo}`"
|
||||
type="primary"
|
||||
@click="openSettlementDetail(item)"
|
||||
>
|
||||
{{ item.settlementNo }}
|
||||
</el-link>
|
||||
</template>
|
||||
<el-input
|
||||
v-else
|
||||
v-model="referenceLabel"
|
||||
readonly
|
||||
<el-select
|
||||
ref="settlementNoSelectRef"
|
||||
:model-value="referenceSettlementNos"
|
||||
multiple
|
||||
collapse-tags
|
||||
collapse-tags-tooltip
|
||||
:max-collapse-tags="1"
|
||||
:disabled="readonly"
|
||||
placeholder="请选择预结算/正式结算单"
|
||||
/>
|
||||
class="payment-form-page__settlement-select"
|
||||
@visible-change="handleSettlementSelectVisible"
|
||||
>
|
||||
<el-option
|
||||
v-for="item in referenceSettlementLinks"
|
||||
:key="`${item.id || item.settlementNo}`"
|
||||
:label="item.settlementNo"
|
||||
:value="item.settlementNo"
|
||||
/>
|
||||
</el-select>
|
||||
<el-button
|
||||
v-if="!readonly"
|
||||
class="payment-form-page__settlement-select-btn"
|
||||
@@ -100,7 +102,7 @@
|
||||
<el-option
|
||||
v-for="item in contractOptions"
|
||||
:key="item.id"
|
||||
:label="item.contractName || item.contractNo"
|
||||
:label="formatContractOptionLabel(item)"
|
||||
:value="item.id"
|
||||
/>
|
||||
</el-select>
|
||||
@@ -251,7 +253,7 @@
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</section-card>
|
||||
<section-card v-if="isSettlementRelatedType" title="发票信息">
|
||||
<section-card v-if="showInvoiceSection" title="发票信息">
|
||||
<el-table :data="form.invoices" border>
|
||||
<el-table-column type="index" label="序号" width="70" />
|
||||
<el-table-column prop="settlementNo" label="结算单号" min-width="120">
|
||||
@@ -355,19 +357,22 @@
|
||||
value="special_approval" /><el-option
|
||||
label="其他"
|
||||
value="other" /></el-select></template></el-table-column
|
||||
><el-table-column label="文件名" min-width="220"
|
||||
><el-table-column
|
||||
label="文件名"
|
||||
min-width="220"
|
||||
show-overflow-tooltip
|
||||
class-name="is-ellipsis-link"
|
||||
><template #default="{ row }"
|
||||
><div
|
||||
class="payment-form-page__attachment-file-name-cell"
|
||||
:title="attachmentFileName(row) || '-'"
|
||||
>
|
||||
<span
|
||||
class="payment-form-page__attachment-file-name"
|
||||
:class="{ 'is-disabled': !attachmentFileUrl(row) }"
|
||||
@click="attachmentFileUrl(row) && previewAttachment(row)"
|
||||
>{{ attachmentFileName(row) || '-' }}</span
|
||||
>
|
||||
</div></template
|
||||
><span
|
||||
class="attachment-file-name"
|
||||
:class="{ 'is-disabled': !attachmentFileUrl(row) }"
|
||||
role="button"
|
||||
tabindex="0"
|
||||
@click="attachmentFileUrl(row) && previewAttachment(row)"
|
||||
@keydown.enter="attachmentFileUrl(row) && previewAttachment(row)"
|
||||
@keydown.space.prevent="attachmentFileUrl(row) && previewAttachment(row)"
|
||||
>{{ attachmentFileName(row) || '-' }}</span
|
||||
></template
|
||||
></el-table-column
|
||||
><el-table-column label="附件描述" min-width="220"
|
||||
><template #default="{ row }"
|
||||
@@ -671,6 +676,7 @@ import {
|
||||
getList as getCustomerArchiveList,
|
||||
} from '@/api/vehicle/customer-archive';
|
||||
import { readSettlementTransfer, removeSettlementTransfer } from '@/utils/settlement-transfer';
|
||||
import { formatContractOptionLabel } from '@/utils/contract';
|
||||
import { downloadFileByUrl } from '@/utils/util';
|
||||
import { submitMkApprovalFlow } from '@/utils/mk-approval';
|
||||
import {
|
||||
@@ -887,6 +893,10 @@ export default {
|
||||
isSettlementRelatedType() {
|
||||
return ['progress_advance', 'settlement_payment'].includes(this.form.paymentType);
|
||||
},
|
||||
// 项目预付、进度预付不展示发票信息,仅尾款付款展示
|
||||
showInvoiceSection() {
|
||||
return this.form.paymentType === 'settlement_payment';
|
||||
},
|
||||
canSelectPreSettlement() {
|
||||
// 进度预付仅预结算;尾款付款可正式/预结算
|
||||
return ['progress_advance', 'settlement_payment'].includes(this.form.paymentType);
|
||||
@@ -939,6 +949,9 @@ export default {
|
||||
referenceType: this.form.preSettlementId ? 'pre' : 'formal',
|
||||
}));
|
||||
},
|
||||
referenceSettlementNos() {
|
||||
return this.referenceSettlementLinks.map(item => item.settlementNo).filter(Boolean);
|
||||
},
|
||||
settlementRows() {
|
||||
if (this.referenceRows.length) {
|
||||
return this.referenceRows.map(item => ({
|
||||
@@ -1038,6 +1051,7 @@ export default {
|
||||
this.initialize();
|
||||
},
|
||||
methods: {
|
||||
formatContractOptionLabel,
|
||||
hasPermission(code) {
|
||||
return this.permission?.[code] !== false;
|
||||
},
|
||||
@@ -1122,7 +1136,7 @@ export default {
|
||||
callback();
|
||||
},
|
||||
validateInvoices() {
|
||||
if (this.form.paymentType === 'project_advance') return;
|
||||
if (!this.showInvoiceSection) return;
|
||||
for (const invoice of this.form.invoices || []) {
|
||||
if (String(invoice.settlementNo || '').length > 100) {
|
||||
throw new Error('结算单号不能超过100个字符');
|
||||
@@ -1904,6 +1918,7 @@ export default {
|
||||
this.contractPaymentRatioExceeded = exceeded;
|
||||
},
|
||||
handleTypeChange() {
|
||||
// 切换类型时清空发票;预付类型本身也不再展示/提交发票
|
||||
this.form.invoices = [];
|
||||
this.paymentRecords = [];
|
||||
Object.assign(this.form, {
|
||||
@@ -2091,8 +2106,20 @@ export default {
|
||||
const project = this.projectOptions.find(item => String(item.id) === String(projectId));
|
||||
this.form.projectName = project?.projectName || project?.projectShortName || '';
|
||||
Object.assign(this.form, {
|
||||
deptId: project?.undertakeDeptId || project?.businessDeptId || null,
|
||||
deptName: project?.undertakeDeptName || project?.businessDeptName || '',
|
||||
deptId:
|
||||
String(project?.undertakeDeptId || '')
|
||||
.split(/[,,]/)
|
||||
.map(item => item.trim())
|
||||
.find(Boolean) ||
|
||||
project?.businessDeptId ||
|
||||
null,
|
||||
deptName:
|
||||
String(project?.undertakeDeptName || '')
|
||||
.split(/[,,、]/)
|
||||
.map(item => item.trim())
|
||||
.find(Boolean) ||
|
||||
project?.businessDeptName ||
|
||||
'',
|
||||
contractId: null,
|
||||
contractNo: '',
|
||||
contractName: '',
|
||||
@@ -2260,6 +2287,13 @@ export default {
|
||||
}
|
||||
return Promise.all(loaders);
|
||||
},
|
||||
handleSettlementSelectVisible(visible) {
|
||||
// 结算单号仅做展示,通过「选择」按钮维护,避免下拉改值
|
||||
if (!visible) return;
|
||||
this.$nextTick(() => {
|
||||
this.$refs.settlementNoSelectRef?.blur?.();
|
||||
});
|
||||
},
|
||||
handleReferenceSearch() {
|
||||
this.formalPage.current = 1;
|
||||
this.prePage.current = 1;
|
||||
@@ -2623,7 +2657,7 @@ export default {
|
||||
attachmentsJson: JSON.stringify(attachments || []),
|
||||
remark,
|
||||
invoices:
|
||||
paymentType === 'project_advance'
|
||||
paymentType === 'project_advance' || paymentType === 'progress_advance'
|
||||
? []
|
||||
: invoices.map(invoice => ({
|
||||
settlementNo: invoice.settlementNo || '',
|
||||
@@ -2704,13 +2738,18 @@ export default {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
flex-wrap: wrap;
|
||||
width: 100%;
|
||||
min-height: 32px;
|
||||
}
|
||||
.payment-form-page__settlement-nos :deep(.el-input) {
|
||||
.payment-form-page__settlement-select {
|
||||
flex: 1;
|
||||
min-width: 120px;
|
||||
min-width: 0;
|
||||
}
|
||||
.payment-form-page__settlement-select :deep(.el-select__wrapper) {
|
||||
width: 100%;
|
||||
}
|
||||
.payment-form-page__settlement-select :deep(.el-tag__close) {
|
||||
display: none;
|
||||
}
|
||||
.payment-form-page__settlement-select-btn {
|
||||
flex-shrink: 0;
|
||||
@@ -2787,38 +2826,6 @@ export default {
|
||||
justify-content: center;
|
||||
gap: 8px;
|
||||
}
|
||||
.payment-form-page__attachment-file-name-cell {
|
||||
display: block;
|
||||
width: 100%;
|
||||
min-width: 0;
|
||||
overflow: hidden;
|
||||
text-align: left;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.payment-form-page__attachment-file-name {
|
||||
display: block;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
color: var(--el-text-color-regular);
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
cursor: pointer;
|
||||
transition: color 0.2s ease;
|
||||
|
||||
&:hover {
|
||||
color: #409eff;
|
||||
}
|
||||
|
||||
&.is-disabled {
|
||||
color: var(--el-text-color-regular);
|
||||
cursor: default;
|
||||
|
||||
&:hover {
|
||||
color: var(--el-text-color-regular);
|
||||
}
|
||||
}
|
||||
}
|
||||
.payment-form-page__attachment-upload .vehicle-attachment-upload {
|
||||
width: auto;
|
||||
}
|
||||
@@ -2826,7 +2833,7 @@ export default {
|
||||
display: inline-flex;
|
||||
}
|
||||
.payment-form-page :deep(.el-form-item) {
|
||||
margin-bottom: 14px;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
.payment-form-page :deep(.el-input-number .el-input__inner) {
|
||||
text-align: left;
|
||||
|
||||
@@ -1,297 +1,179 @@
|
||||
<template>
|
||||
<basic-container class="payment-page">
|
||||
<section class="payment-page__search">
|
||||
<el-form :model="query" label-position="right" label-width="88px">
|
||||
<div class="payment-page__search-grid">
|
||||
<el-form-item label="单据号"
|
||||
><el-input v-model="query.paymentNo" clearable
|
||||
/></el-form-item>
|
||||
<el-form-item label="日期"
|
||||
><el-date-picker
|
||||
v-model="query.applyDateRange"
|
||||
type="daterange"
|
||||
value-format="YYYY-MM-DD"
|
||||
range-separator="~"
|
||||
start-placeholder="年/月/日"
|
||||
end-placeholder="年/月/日"
|
||||
/></el-form-item>
|
||||
<el-form-item label="客户名称"
|
||||
><el-input v-model="query.payeeName" clearable
|
||||
/></el-form-item>
|
||||
<el-form-item label="项目名称"
|
||||
><el-input v-model="query.projectName" clearable
|
||||
/></el-form-item>
|
||||
<template v-if="searchExpanded">
|
||||
<el-form-item label="所属组织"
|
||||
><el-cascader
|
||||
v-model="query.deptPath"
|
||||
:options="organizationTreeOptions"
|
||||
:props="organizationCascaderProps"
|
||||
filterable
|
||||
clearable
|
||||
style="width: 100%"
|
||||
placeholder="请选择 所属组织"
|
||||
@change="val => { query.deptName = findOrgById(val)?.rawLabel || '' }"
|
||||
/></el-form-item>
|
||||
<el-form-item label="关联结算单"
|
||||
><el-input v-model="query.settlementNo" clearable
|
||||
/></el-form-item>
|
||||
<el-form-item label="付款类型"
|
||||
><el-select v-model="query.paymentType" clearable
|
||||
><el-option
|
||||
v-for="item in paymentTypeOptions"
|
||||
:key="item.value"
|
||||
v-bind="item" /></el-select
|
||||
></el-form-item>
|
||||
<el-form-item label="审核状态"
|
||||
><el-select v-model="query.approvalStatus" clearable
|
||||
><el-option
|
||||
v-for="item in approvalStatusOptions"
|
||||
:key="item.value"
|
||||
v-bind="item" /></el-select
|
||||
></el-form-item>
|
||||
<el-form-item label="金蝶单据状态"
|
||||
><el-select v-model="query.kingdeeStatus" clearable
|
||||
><el-option
|
||||
v-for="item in kingdeeStatusOptions"
|
||||
:key="item.value"
|
||||
v-bind="item" /></el-select
|
||||
></el-form-item>
|
||||
</template>
|
||||
</div>
|
||||
<div class="payment-page__search-actions">
|
||||
<el-button type="primary" @click="handleSearch">查询</el-button>
|
||||
<el-button @click="resetSearch">重置</el-button>
|
||||
<el-button text @click="searchExpanded = !searchExpanded"
|
||||
><el-icon><component :is="searchExpanded ? ArrowUp : ArrowDown" /></el-icon
|
||||
></el-button>
|
||||
</div>
|
||||
</el-form>
|
||||
</section>
|
||||
<section class="payment-page__table-panel">
|
||||
<div class="payment-page__toolbar">
|
||||
<div class="payment-page__toolbar-left">
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_add')"
|
||||
type="primary"
|
||||
@click="openCreate"
|
||||
>新增付款申请</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_sync')"
|
||||
type="primary"
|
||||
plain
|
||||
:loading="syncLoading"
|
||||
@click="handleSync"
|
||||
>批量同步</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_sync')"
|
||||
type="primary"
|
||||
plain
|
||||
:loading="resultSyncing"
|
||||
@click="handleSyncResult"
|
||||
>同步付款结果</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_add')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="openSettlementPayment"
|
||||
>申请付尾款</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_add')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="openProjectAdvance"
|
||||
>预付申请</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_export')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="handleExport"
|
||||
>导出</el-button
|
||||
>
|
||||
</div>
|
||||
<el-button text :icon="Refresh" @click="loadTable" />
|
||||
</div>
|
||||
<el-table v-loading="loading" :data="rows" border @selection-change="selection = $event">
|
||||
<el-table-column type="selection" width="52" fixed="left" align="center" />
|
||||
<el-table-column type="index" label="序号" width="64" fixed="left" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
show-overflow-tooltip
|
||||
<avue-crud
|
||||
ref="crud"
|
||||
:option="option"
|
||||
:table-loading="loading"
|
||||
:data="rows"
|
||||
v-model:page="page"
|
||||
@search-change="searchChange"
|
||||
@search-reset="searchReset"
|
||||
@selection-change="selectionChange"
|
||||
@current-change="currentChange"
|
||||
@size-change="sizeChange"
|
||||
@refresh-change="refreshChange"
|
||||
@on-load="onLoad"
|
||||
>
|
||||
<template #menu-left>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_add')"
|
||||
type="primary"
|
||||
@click="openCreate"
|
||||
>新增付款申请</el-button
|
||||
>
|
||||
<template #default="{ row }">
|
||||
<el-link v-if="column.link" type="primary" @click="openView(row)">{{
|
||||
row[column.prop]
|
||||
}}</el-link>
|
||||
<el-tag
|
||||
v-else-if="column.status"
|
||||
:type="statusType(row.approvalStatus)"
|
||||
class="status-text"
|
||||
>{{ row[column.prop] || '-' }}</el-tag
|
||||
>
|
||||
<span v-else-if="column.money">{{ formatMoney(row[column.prop]) }}</span>
|
||||
<template v-else-if="column.prop === 'kingdeeLockStatus'">
|
||||
<el-tooltip v-if="lockTag(row).show" :content="lockTag(row).tip" placement="top">
|
||||
<el-tag :type="lockTag(row).type" class="status-text">{{ lockTag(row).label }}</el-tag>
|
||||
</el-tooltip>
|
||||
<span v-else>-</span>
|
||||
</template>
|
||||
<span v-else>{{ displayValue(row[column.prop]) }}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="操作" width="320" fixed="right" align="center">
|
||||
<template #default="{ row }"
|
||||
><div class="payment-page__links">
|
||||
<el-link
|
||||
v-if="hasPermission('payment_application_view')"
|
||||
type="primary"
|
||||
@click="openView(row)"
|
||||
>查看</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
hasPermission('payment_application_edit') &&
|
||||
['draft', 'returned'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="openEdit(row)"
|
||||
>编辑</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
hasPermission('payment_application_submit') &&
|
||||
['draft', 'returned'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="handleSubmit(row)"
|
||||
>提交</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
mkEnabled &&
|
||||
hasPermission('payment_application_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
"
|
||||
type="primary"
|
||||
@click="handleMkAudit(row)"
|
||||
>流程</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
!mkEnabled &&
|
||||
hasPermission('payment_application_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
"
|
||||
type="primary"
|
||||
@click="handleApprove(row)"
|
||||
>通过</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
!mkEnabled &&
|
||||
hasPermission('payment_application_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
"
|
||||
type="danger"
|
||||
@click="handleReturn(row)"
|
||||
>驳回</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
hasPermission('payment_application_void') &&
|
||||
row.approvalStatus === 'approved' &&
|
||||
row.kingdeeLockStatus !== 'locked'
|
||||
"
|
||||
type="danger"
|
||||
@click="handleVoid(row)"
|
||||
>作废</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="hasPermission('payment_application_delete') && row.approvalStatus === 'draft'"
|
||||
type="danger"
|
||||
@click="handleDelete(row)"
|
||||
>删除</el-link
|
||||
>
|
||||
</div></template
|
||||
>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
<div class="payment-page__pagination">
|
||||
<el-pagination
|
||||
v-model:current-page="page.current"
|
||||
v-model:page-size="page.size"
|
||||
:total="page.total"
|
||||
:page-sizes="[10, 20, 50, 100]"
|
||||
layout="total, sizes, prev, pager, next, jumper"
|
||||
@current-change="loadTable"
|
||||
@size-change="handleSizeChange"
|
||||
/>
|
||||
</div>
|
||||
</section>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_sync')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="handleSync"
|
||||
>批量同步</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_add')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="openSettlementPayment"
|
||||
>申请付尾款</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_add')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="openProjectAdvance"
|
||||
>预付申请</el-button
|
||||
>
|
||||
<el-button
|
||||
v-if="hasPermission('payment_application_export')"
|
||||
type="primary"
|
||||
plain
|
||||
@click="handleExport"
|
||||
>导出</el-button
|
||||
>
|
||||
</template>
|
||||
|
||||
<template #paymentNo="{ row }">
|
||||
<el-link type="primary" @click="openView(row)">{{ row.paymentNo }}</el-link>
|
||||
</template>
|
||||
|
||||
<template #approvalStatusName="{ row }">
|
||||
<el-tag :type="statusType(row.approvalStatus)" class="status-text">{{
|
||||
row.approvalStatusName || '-'
|
||||
}}</el-tag>
|
||||
</template>
|
||||
|
||||
<template #menu="{ row }">
|
||||
<el-link
|
||||
v-if="hasPermission('payment_application_view')"
|
||||
type="primary"
|
||||
@click="openView(row)"
|
||||
>查看</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
hasPermission('payment_application_edit') &&
|
||||
['draft', 'returned'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="openEdit(row)"
|
||||
>编辑</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
hasPermission('payment_application_submit') &&
|
||||
['draft', 'returned'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="handleSubmit(row)"
|
||||
>提交</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
mkEnabled &&
|
||||
hasPermission('payment_application_approve') &&
|
||||
['reviewing', 'approved'].includes(row.approvalStatus)
|
||||
"
|
||||
type="primary"
|
||||
@click="handleMkAudit(row)"
|
||||
>流程</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
!mkEnabled &&
|
||||
hasPermission('payment_application_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
"
|
||||
type="primary"
|
||||
@click="handleApprove(row)"
|
||||
>通过</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="
|
||||
!mkEnabled &&
|
||||
hasPermission('payment_application_approve') &&
|
||||
row.approvalStatus === 'reviewing'
|
||||
"
|
||||
type="danger"
|
||||
@click="handleReturn(row)"
|
||||
>驳回</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="hasPermission('payment_application_void') && row.approvalStatus === 'approved'"
|
||||
type="danger"
|
||||
@click="handleVoid(row)"
|
||||
>作废</el-link
|
||||
>
|
||||
<el-link
|
||||
v-if="hasPermission('payment_application_delete') && row.approvalStatus === 'draft'"
|
||||
type="danger"
|
||||
@click="handleDelete(row)"
|
||||
>删除</el-link
|
||||
>
|
||||
</template>
|
||||
</avue-crud>
|
||||
</basic-container>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { ArrowDown, ArrowUp, Refresh } from '@element-plus/icons-vue';
|
||||
import { mapGetters } from 'vuex';
|
||||
import * as api from '@/api/payment/paymentApplication';
|
||||
import { paymentApplicationTableColumns } from '@/option/payment/paymentApplication';
|
||||
import { paymentApplicationOption } from '@/option/payment/paymentApplication';
|
||||
import organizationSearch from '@/mixins/organization-search';
|
||||
import { getMKApprovalUrl } from '@/api/system/business-process';
|
||||
import { loadMkEnabled, submitMkApprovalFlow } from '@/utils/mk-approval';
|
||||
|
||||
const emptyQuery = () => ({
|
||||
paymentNo: '',
|
||||
applyDateRange: [],
|
||||
payeeName: '',
|
||||
projectName: '',
|
||||
deptName: '',
|
||||
deptPath: [],
|
||||
settlementNo: '',
|
||||
paymentType: '',
|
||||
approvalStatus: '',
|
||||
kingdeeStatus: '',
|
||||
});
|
||||
export default {
|
||||
name: 'PaymentApplication',
|
||||
mixins: [organizationSearch],
|
||||
data() {
|
||||
return {
|
||||
ArrowDown,
|
||||
ArrowUp,
|
||||
Refresh,
|
||||
query: emptyQuery(),
|
||||
searchExpanded: false,
|
||||
paymentTypeOptions: api.paymentTypeOptions,
|
||||
approvalStatusOptions: api.approvalStatusOptions,
|
||||
kingdeeStatusOptions: api.kingdeeStatusOptions,
|
||||
columns: paymentApplicationTableColumns,
|
||||
rows: [],
|
||||
selection: [],
|
||||
loading: false,
|
||||
syncLoading: false,
|
||||
resultSyncing: false,
|
||||
page: { current: 1, size: 10, total: 0 },
|
||||
query: {},
|
||||
option: {},
|
||||
page: {
|
||||
currentPage: 1,
|
||||
pageSize: 10,
|
||||
pageSizes: [10, 20, 50, 100],
|
||||
total: 0,
|
||||
},
|
||||
mkEnabled: false,
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission']),
|
||||
visibleSearchFields() {
|
||||
return this.searchExpanded ? this.columns : this.columns.slice(0, 4);
|
||||
},
|
||||
},
|
||||
created() {
|
||||
this.option = paymentApplicationOption({
|
||||
paymentTypeOptions: api.paymentTypeOptions,
|
||||
approvalStatusOptions: api.approvalStatusOptions,
|
||||
kingdeeStatusOptions: api.kingdeeStatusOptions,
|
||||
});
|
||||
this.loadOrganizationOptions();
|
||||
},
|
||||
mounted() {
|
||||
this.loadOrganizationOptions();
|
||||
this.loadTable();
|
||||
loadMkEnabled()
|
||||
.then(enabled => {
|
||||
this.mkEnabled = !!enabled;
|
||||
@@ -308,39 +190,52 @@ export default {
|
||||
const body = response?.data || response || {};
|
||||
return body?.data || body;
|
||||
},
|
||||
buildParams() {
|
||||
const params = { ...this.query };
|
||||
onLoad(page) {
|
||||
this.loading = true;
|
||||
api
|
||||
.getList(page.currentPage, page.pageSize, { ...this.query })
|
||||
.then(res => {
|
||||
const data = this.unwrapData(res);
|
||||
this.rows = data.records || [];
|
||||
this.page.total = Number(data.total || 0);
|
||||
})
|
||||
.finally(() => {
|
||||
this.loading = false;
|
||||
this.selection = [];
|
||||
this.$refs.crud?.toggleSelection?.();
|
||||
});
|
||||
},
|
||||
searchChange(params, done) {
|
||||
// 所属组织级联返回 id 路径数组,转成部门名称给后端
|
||||
this.normalizeOrganizationSearch(params, 'deptName');
|
||||
// 日期区间拆成后端需要的起止字段
|
||||
const range = params.applyDateRange || [];
|
||||
delete params.applyDateRange;
|
||||
if (range.length === 2) {
|
||||
params.applyStartDate = range[0];
|
||||
params.applyEndDate = range[1];
|
||||
}
|
||||
return params;
|
||||
this.query = {
|
||||
...params,
|
||||
applyStartDate: range[0] || '',
|
||||
applyEndDate: range[1] || '',
|
||||
};
|
||||
this.page.currentPage = 1;
|
||||
this.onLoad(this.page);
|
||||
done();
|
||||
},
|
||||
async loadTable() {
|
||||
this.loading = true;
|
||||
try {
|
||||
const data = this.unwrapData(
|
||||
await api.getList(this.page.current, this.page.size, this.buildParams())
|
||||
);
|
||||
this.rows = data.records || [];
|
||||
this.page.total = data.total || 0;
|
||||
} finally {
|
||||
this.loading = false;
|
||||
}
|
||||
searchReset() {
|
||||
this.query = {};
|
||||
this.page.currentPage = 1;
|
||||
this.onLoad(this.page);
|
||||
},
|
||||
handleSearch() {
|
||||
this.page.current = 1;
|
||||
this.loadTable();
|
||||
currentChange(currentPage) {
|
||||
this.page.currentPage = currentPage;
|
||||
},
|
||||
resetSearch() {
|
||||
this.query = emptyQuery();
|
||||
this.handleSearch();
|
||||
sizeChange(pageSize) {
|
||||
this.page.pageSize = pageSize;
|
||||
},
|
||||
handleSizeChange() {
|
||||
this.page.current = 1;
|
||||
this.loadTable();
|
||||
refreshChange() {
|
||||
this.onLoad(this.page);
|
||||
},
|
||||
selectionChange(list) {
|
||||
this.selection = list;
|
||||
},
|
||||
openCreate() {
|
||||
this.$router.push({ path: '/payment/payment-application/form', query: { mode: 'add' } });
|
||||
@@ -380,7 +275,7 @@ export default {
|
||||
await this.$confirm('确认删除该付款申请?', '提示', { type: 'warning' });
|
||||
await api.remove(row.id);
|
||||
this.$message.success('删除成功');
|
||||
this.loadTable();
|
||||
this.refreshChange();
|
||||
},
|
||||
async handleSubmit(row) {
|
||||
const previousApprovalStatus = row.approvalStatus || '';
|
||||
@@ -392,7 +287,7 @@ export default {
|
||||
approvalStatus: previousApprovalStatus,
|
||||
});
|
||||
this.$message.success('提交成功');
|
||||
this.loadTable();
|
||||
this.refreshChange();
|
||||
},
|
||||
async handleApprove(row) {
|
||||
const res = await api.approve({ id: row.id });
|
||||
@@ -402,7 +297,7 @@ export default {
|
||||
} else {
|
||||
this.$message.success(res.data.msg || '审批通过');
|
||||
}
|
||||
this.loadTable();
|
||||
this.refreshChange();
|
||||
},
|
||||
handleMkAudit(row) {
|
||||
if (!row?.id) {
|
||||
@@ -426,18 +321,18 @@ export default {
|
||||
const { value } = await this.$prompt('请输入驳回原因', '审批驳回');
|
||||
await api.returnBill({ id: row.id, reason: value });
|
||||
this.$message.success('已驳回');
|
||||
this.loadTable();
|
||||
this.refreshChange();
|
||||
},
|
||||
async handleVoid(row) {
|
||||
const { value } = await this.$prompt('请输入作废原因', '作废付款申请');
|
||||
await api.voidBill({ id: row.id, reason: value });
|
||||
this.$message.success('作废成功');
|
||||
this.loadTable();
|
||||
this.refreshChange();
|
||||
},
|
||||
async handleSyncRow(row) {
|
||||
const data = this.unwrapData(await api.syncKingdee(row.id));
|
||||
this.$message.success(`已生成金蝶付款单:${data}`);
|
||||
await this.loadTable();
|
||||
await this.refreshChange();
|
||||
this.warnAttachmentNotUploaded([row.id]);
|
||||
},
|
||||
async handleSync() {
|
||||
@@ -460,7 +355,7 @@ export default {
|
||||
} else {
|
||||
this.$message.success(`已同步${data.length}条付款申请`);
|
||||
}
|
||||
await this.loadTable();
|
||||
await this.refreshChange();
|
||||
this.warnAttachmentNotUploaded(rows.map(row => row.id));
|
||||
} finally {
|
||||
this.syncLoading = false;
|
||||
@@ -490,9 +385,15 @@ export default {
|
||||
this.resultSyncing = false;
|
||||
}
|
||||
},
|
||||
|
||||
handleExport() {
|
||||
const headers = this.columns.map(item => item.label);
|
||||
const rows = this.rows.map(row => this.columns.map(item => row[item.prop] || ''));
|
||||
const columns = this.option.column.filter(column => !column.hide && column.prop);
|
||||
const headers = columns.map(item => item.label);
|
||||
const rows = this.rows.map(row =>
|
||||
columns.map(item =>
|
||||
row[item.prop] === null || row[item.prop] === undefined ? '' : row[item.prop]
|
||||
)
|
||||
);
|
||||
const csv = [headers, ...rows]
|
||||
.map(item => item.map(value => `"${String(value).replaceAll('"', '""')}"`).join(','))
|
||||
.join('\n');
|
||||
@@ -542,54 +443,6 @@ export default {
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.payment-page__search {
|
||||
padding: 12px 12px 4px;
|
||||
background: #fff;
|
||||
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.04);
|
||||
}
|
||||
.payment-page__search-grid {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(4, minmax(0, 1fr));
|
||||
gap: 8px 24px;
|
||||
}
|
||||
.payment-page__search :deep(.el-form-item) {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
.payment-page__search :deep(.el-input),
|
||||
.payment-page__search :deep(.el-select),
|
||||
.payment-page__search :deep(.el-date-editor) {
|
||||
width: 100%;
|
||||
}
|
||||
.payment-page__search-actions {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
gap: 8px;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
.payment-page__table-panel {
|
||||
margin-top: 8px;
|
||||
}
|
||||
.payment-page__toolbar {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding: 12px 0;
|
||||
}
|
||||
.payment-page__toolbar-left {
|
||||
display: flex;
|
||||
gap: 8px;
|
||||
}
|
||||
.payment-page__links {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
justify-content: center;
|
||||
gap: 8px;
|
||||
}
|
||||
.payment-page__pagination {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
margin-top: 12px;
|
||||
}
|
||||
.payment-page :deep(.el-table) {
|
||||
--el-table-border-color: #eff1f7;
|
||||
}
|
||||
@@ -599,14 +452,4 @@ export default {
|
||||
:deep(.payment-page.basic-container .basic-container__card > .el-card__body) {
|
||||
padding: 0;
|
||||
}
|
||||
@media (max-width: 1200px) {
|
||||
.payment-page__search-grid {
|
||||
grid-template-columns: repeat(2, minmax(0, 1fr));
|
||||
}
|
||||
}
|
||||
@media (max-width: 760px) {
|
||||
.payment-page__search-grid {
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<basic-container class="claim-record-page">
|
||||
<section-card class="claim-record-page__search">
|
||||
<section-card v-if="searchVisible" class="claim-record-page__search">
|
||||
<el-form :model="query" label-position="right" label-width="88px" @submit.prevent>
|
||||
<div class="claim-record-page__search-grid">
|
||||
<el-form-item label="认领通知单">
|
||||
@@ -96,9 +96,19 @@
|
||||
</el-button>
|
||||
</div>
|
||||
<el-table v-loading="loading" :data="rows" border>
|
||||
<div class="claim-record-page__toolbar">
|
||||
<table-header-tools
|
||||
:columns="columns"
|
||||
v-model:visible-column-keys="visibleColumnKeys"
|
||||
v-model:table-size="tableSize"
|
||||
v-model:search-visible="searchVisible"
|
||||
@refresh="loadTable"
|
||||
/>
|
||||
</div>
|
||||
<el-table v-loading="loading" :data="rows" :size="tableSize" border>
|
||||
<el-table-column type="index" label="序号" width="64" fixed="left" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
v-for="column in visibleColumns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
@@ -157,6 +167,7 @@ import { mapGetters } from 'vuex';
|
||||
import * as api from '@/api/payment/receiptClaimRecord';
|
||||
import { receiptClaimRecordTableColumns } from '@/option/payment/receiptClaimRecord';
|
||||
import SectionCard from '@/components/section-card/main.vue';
|
||||
import TableHeaderTools from '@/components/table-header-tools/main.vue';
|
||||
import { isAdministrator } from '@/utils/auth';
|
||||
|
||||
const emptyQuery = () => ({
|
||||
@@ -176,17 +187,20 @@ const emptyQuery = () => ({
|
||||
|
||||
export default {
|
||||
name: 'ReceiptClaimRecord',
|
||||
components: { SectionCard },
|
||||
components: { SectionCard, TableHeaderTools },
|
||||
data() {
|
||||
return {
|
||||
ArrowDown,
|
||||
ArrowUp,
|
||||
query: emptyQuery(),
|
||||
searchExpanded: false,
|
||||
searchVisible: true,
|
||||
tableSize: 'default',
|
||||
claimStatusOptions: api.claimStatusOptions,
|
||||
kingdeeBillStatusOptions: api.kingdeeBillStatusOptions,
|
||||
pushStatusOptions: api.pushStatusOptions,
|
||||
columns: receiptClaimRecordTableColumns,
|
||||
visibleColumnKeys: receiptClaimRecordTableColumns.map(column => column.prop),
|
||||
rows: [],
|
||||
loading: false,
|
||||
refreshing: false,
|
||||
@@ -195,6 +209,9 @@ export default {
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission', 'userInfo']),
|
||||
visibleColumns() {
|
||||
return this.columns.filter(column => this.visibleColumnKeys.includes(column.prop));
|
||||
},
|
||||
isAdmin() {
|
||||
return isAdministrator(this.userInfo);
|
||||
},
|
||||
@@ -314,9 +331,8 @@ export default {
|
||||
}
|
||||
.claim-record-page__toolbar {
|
||||
display: flex;
|
||||
justify-content: flex-start;
|
||||
justify-content: flex-end;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
padding: 12px 0;
|
||||
}
|
||||
.claim-record-page__pagination {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<basic-container class="receipt-flow-page">
|
||||
<section class="receipt-flow-page__search">
|
||||
<section v-if="searchVisible" class="receipt-flow-page__search">
|
||||
<el-form :model="query" label-position="right" label-width="88px" @submit.prevent>
|
||||
<div class="receipt-flow-page__search-grid">
|
||||
<el-form-item label="认领通知单">
|
||||
@@ -97,33 +97,43 @@
|
||||
|
||||
<section class="receipt-flow-page__table-panel">
|
||||
<div class="receipt-flow-page__toolbar">
|
||||
<el-button
|
||||
v-if="hasPermission('receipt_flow_sync')"
|
||||
type="primary"
|
||||
:loading="syncing"
|
||||
@click="handleSync"
|
||||
>
|
||||
手动同步流水
|
||||
</el-button>
|
||||
<el-button
|
||||
v-if="hasPermission('receipt_flow_claim')"
|
||||
type="primary"
|
||||
:disabled="!selectedRows.length"
|
||||
@click="openBatchClaim"
|
||||
>
|
||||
批量认领
|
||||
</el-button>
|
||||
<div class="receipt-flow-page__toolbar-left">
|
||||
<el-button
|
||||
v-if="hasPermission('receipt_flow_sync')"
|
||||
type="primary"
|
||||
:loading="syncing"
|
||||
@click="handleSync"
|
||||
>
|
||||
手动同步流水
|
||||
</el-button>
|
||||
<el-button
|
||||
v-if="hasPermission('receipt_flow_claim')"
|
||||
type="primary"
|
||||
:disabled="!selectedRows.length"
|
||||
@click="openBatchClaim"
|
||||
>
|
||||
批量认领
|
||||
</el-button>
|
||||
</div>
|
||||
<table-header-tools
|
||||
:columns="columns"
|
||||
v-model:visible-column-keys="visibleColumnKeys"
|
||||
v-model:table-size="tableSize"
|
||||
v-model:search-visible="searchVisible"
|
||||
@refresh="loadTable"
|
||||
/>
|
||||
</div>
|
||||
<el-table
|
||||
v-loading="loading"
|
||||
:data="rows"
|
||||
:size="tableSize"
|
||||
border
|
||||
@selection-change="selectedRows = $event"
|
||||
>
|
||||
<el-table-column type="selection" width="52" align="center" />
|
||||
<el-table-column type="index" label="序号" width="64" align="center" />
|
||||
<el-table-column
|
||||
v-for="column in columns"
|
||||
v-for="column in visibleColumns"
|
||||
:key="column.prop"
|
||||
v-bind="column"
|
||||
align="center"
|
||||
@@ -271,6 +281,7 @@ import { ArrowDown, ArrowUp } from '@element-plus/icons-vue';
|
||||
import { mapGetters } from 'vuex';
|
||||
import * as api from '@/api/payment/receiptFlow';
|
||||
import { receiptFlowTableColumns } from '@/option/payment/receiptFlow';
|
||||
import TableHeaderTools from '@/components/table-header-tools/main.vue';
|
||||
import { isAdministrator } from '@/utils/auth';
|
||||
|
||||
const emptyQuery = () => ({
|
||||
@@ -291,6 +302,7 @@ const emptyQuery = () => ({
|
||||
|
||||
export default {
|
||||
name: 'ReceiptFlow',
|
||||
components: { TableHeaderTools },
|
||||
data() {
|
||||
return {
|
||||
ArrowDown,
|
||||
@@ -300,6 +312,9 @@ export default {
|
||||
pushStatusOptions: api.pushStatusOptions,
|
||||
kingdeeBillStatusOptions: api.kingdeeBillStatusOptions,
|
||||
columns: receiptFlowTableColumns,
|
||||
visibleColumnKeys: receiptFlowTableColumns.map(column => column.prop),
|
||||
searchVisible: true,
|
||||
tableSize: 'default',
|
||||
rows: [],
|
||||
selectedRows: [],
|
||||
loading: false,
|
||||
@@ -312,6 +327,9 @@ export default {
|
||||
},
|
||||
computed: {
|
||||
...mapGetters(['permission', 'userInfo']),
|
||||
visibleColumns() {
|
||||
return this.columns.filter(column => this.visibleColumnKeys.includes(column.prop));
|
||||
},
|
||||
isAdmin() {
|
||||
return isAdministrator(this.userInfo);
|
||||
},
|
||||
@@ -507,11 +525,15 @@ export default {
|
||||
}
|
||||
.receipt-flow-page__toolbar {
|
||||
display: flex;
|
||||
justify-content: flex-start;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
padding: 12px 0;
|
||||
}
|
||||
.receipt-flow-page__toolbar-left {
|
||||
display: flex;
|
||||
gap: 8px;
|
||||
}
|
||||
.receipt-flow-page__pagination {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
|
||||
Reference in New Issue
Block a user