From 32a35a2ae4cd198335788866181c7aa4579cc90d Mon Sep 17 00:00:00 2001
From: gaoluyang <2820782392@qq.com>
Date: 星期五, 16 一月 2026 14:53:41 +0800
Subject: [PATCH] 进销存-升级 1.修改上传组件bug 2.付款流水和回款流水添加删除功能 3.调整财务管理页面样式和运用组件
---
src/views/financialManagement/expenseManagement/index.vue | 187 ++++++++
src/views/procurementManagement/paymentHistory/index.vue | 87 ++++
/dev/null | 202 ----------
src/views/financialManagement/expenseManagement/Modal.vue | 192 +++++++--
src/components/PIMTable/PIMTable.vue | 2
src/views/financialManagement/loanManagement/index.vue | 9
src/views/financialManagement/revenueManagement/index.vue | 191 ++++++++-
src/views/procurementManagement/paymentEntry/index.vue | 2
src/views/financialManagement/revenueManagement/Modal.vue | 192 +++++++--
src/components/Dialog/FileListDialog.vue | 7
src/views/salesManagement/receiptPaymentHistory/index.vue | 91 ++++
11 files changed, 819 insertions(+), 343 deletions(-)
diff --git a/src/components/Dialog/FileListDialog.vue b/src/components/Dialog/FileListDialog.vue
index ebe81dd..0721a55 100644
--- a/src/components/Dialog/FileListDialog.vue
+++ b/src/components/Dialog/FileListDialog.vue
@@ -229,10 +229,9 @@
const handleUpload = async () => {
if (props.uploadMethod) {
- const newItem = await props.uploadMethod()
- if (newItem) {
- addAttachment(newItem)
- }
+ // 濡傛灉鎻愪緵浜嗚嚜瀹氫箟涓婁紶鏂规硶锛岀敱鐖剁粍浠惰礋璐f洿鏂板垪琛紙閫氳繃 setList锛�
+ // 杩欓噷涓嶅啀鑷姩娣诲姞锛岄伩鍏嶄笌鐖剁粍浠剁殑 setList 閲嶅
+ await props.uploadMethod()
}
emit('upload')
}
diff --git a/src/components/PIMTable/PIMTable.vue b/src/components/PIMTable/PIMTable.vue
index 01462f0..1480893 100644
--- a/src/components/PIMTable/PIMTable.vue
+++ b/src/components/PIMTable/PIMTable.vue
@@ -40,7 +40,7 @@
:fixed="item.fixed"
:label="item.label"
:prop="item.prop"
- :show-overflow-tooltip="item.dataType !== 'action'"
+ :show-overflow-tooltip="item.dataType !== 'action' && item.dataType !== 'slot'"
:align="item.align"
:sortable="!!item.sortable"
:type="item.type"
diff --git a/src/views/financialManagement/expenseManagement/Form.vue b/src/views/financialManagement/expenseManagement/Form.vue
deleted file mode 100644
index 9cfe5da..0000000
--- a/src/views/financialManagement/expenseManagement/Form.vue
+++ /dev/null
@@ -1,123 +0,0 @@
-<template>
- <el-form :model="form" label-width="100px" :rules="formRules" ref="formRef">
- <el-form-item label="鏀嚭鏃ユ湡" prop="expenseDate">
- <el-date-picker
- style="width: 100%"
- v-model="form.expenseDate"
- format="YYYY-MM-DD"
- value-format="YYYY-MM-DD"
- type="date"
- placeholder="璇烽�夋嫨鏃ユ湡"
- clearable
- />
- </el-form-item>
- <el-form-item label="鏀嚭绫诲瀷" prop="expenseType">
- <el-select
- v-model="form.expenseType"
- placeholder="璇烽�夋嫨"
- clearable
- >
- <el-option :label="item.label" :value="item.value" v-for="(item,index) in expense_types" :key="index" />
- </el-select>
- </el-form-item>
- <el-form-item label="渚涘簲鍟嗗悕绉�" prop="supplierName">
- <el-input v-model="form.supplierName" placeholder="璇疯緭鍏�" />
- </el-form-item>
- <el-form-item label="鏀嚭閲戦" prop="expenseMoney">
- <el-input-number :step="0.01" :min="0" style="width: 100%"
- v-model="form.expenseMoney"
- placeholder="璇疯緭鍏�"
- />
- </el-form-item>
- <el-form-item label="鏀嚭鎻忚堪" prop="expenseDescribed">
- <el-input v-model="form.expenseDescribed" placeholder="璇疯緭鍏�" />
- </el-form-item>
- <el-form-item label="浠樻鏂瑰紡" prop="expenseMethod">
- <el-select
- v-model="form.expenseMethod"
- placeholder="璇烽�夋嫨"
- clearable
- >
- <el-option :label="item.label" :value="item.value" v-for="(item,index) in checkout_payment" :key="index" />
- </el-select>
- </el-form-item>
- <el-form-item label="鍙戠エ鍙风爜" prop="invoiceNumber">
- <el-input v-model="form.invoiceNumber" placeholder="璇疯緭鍏�" />
- </el-form-item>
- <el-form-item label="澶囨敞" prop="note">
- <el-input
- v-model="form.note"
- placeholder="澶囨敞"
- />
- </el-form-item>
-
- </el-form>
-</template>
-
-<script setup>
-import useFormData from "@/hooks/useFormData";
-import { getAccountExpense } from "@/api/financialManagement/expenseManagement";
-import {ref} from "vue";
-const { proxy } = getCurrentInstance();
-
-
-defineOptions({
- name: "鏂板鏀嚭",
-});
-const { expense_types } = proxy.useDict("expense_types");
-const { checkout_payment } = proxy.useDict("checkout_payment");
-const formRef = ref(null);
-const formRules = {
- supplierName: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
- expenseMoney: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
- expenseDescribed: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
- expenseDate: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
- expenseType: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
- expenseMethod: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
-}
-
-const { form, resetForm } = useFormData({
- expenseDate: undefined, // 鏀嚭鏃ユ湡
- expenseType: undefined, // 鏀嚭绫诲瀷
- supplierName: undefined, // 瀹㈡埛鍚嶇О
- expenseMoney: undefined, // 鏀嚭閲戦
- expenseDescribed: undefined, // 鏀嚭鎻忚堪
- expenseMethod: undefined, // 鏀舵鏂瑰紡
- invoiceNumber: undefined, // 鍙戠エ鍙风爜
- note: undefined, // 澶囨敞
-});
-
-const loadForm = async (id) => {
- const { code, data } = await getAccountExpense(id);
- if (code == 200) {
- form.expenseDate = data.expenseDate;
- form.expenseType = data.expenseType;
- form.supplierName = data.supplierName;
- form.expenseMoney = data.expenseMoney;
- form.expenseDescribed = data.expenseDescribed;
- form.expenseMethod = data.expenseMethod;
- form.invoiceNumber = data.invoiceNumber;
- form.note = data.note;
- }
-};
-
-// 娓呴櫎琛ㄥ崟鏍¢獙鐘舵��
-const clearValidate = () => {
- formRef.value?.clearValidate();
-};
-
-// 閲嶇疆琛ㄥ崟鏁版嵁鍜屾牎楠岀姸鎬�
-const resetFormAndValidate = () => {
- resetForm();
- clearValidate();
-};
-
-defineExpose({
- form,
- loadForm,
- resetForm,
- clearValidate,
- resetFormAndValidate,
- formRef,
-});
-</script>
diff --git a/src/views/financialManagement/expenseManagement/Modal.vue b/src/views/financialManagement/expenseManagement/Modal.vue
index 8e5b171..4d743c1 100644
--- a/src/views/financialManagement/expenseManagement/Modal.vue
+++ b/src/views/financialManagement/expenseManagement/Modal.vue
@@ -1,20 +1,75 @@
<template>
- <el-dialog :title="modalOptions.title" v-model="visible" @close="close" width="30%">
- <Form ref="formRef"></Form>
- <template #footer>
- <el-button type="primary" @click="sendForm" :loading="loading">
- {{ modalOptions.confirmText }}
- </el-button>
- <el-button @click="closeModal">{{ modalOptions.cancelText }}</el-button>
- </template>
- </el-dialog>
+ <FormDialog
+ v-model="dialogVisible"
+ :title="dialogTitle"
+ :operationType="operationType"
+ width="50%"
+ @confirm="sendForm"
+ @close="close"
+ @cancel="close"
+ >
+ <el-form :model="form" label-width="100px" :rules="formRules" ref="formRef">
+ <el-form-item label="鏀嚭鏃ユ湡" prop="expenseDate">
+ <el-date-picker
+ style="width: 100%"
+ v-model="form.expenseDate"
+ format="YYYY-MM-DD"
+ value-format="YYYY-MM-DD"
+ type="date"
+ placeholder="璇烽�夋嫨鏃ユ湡"
+ clearable
+ />
+ </el-form-item>
+ <el-form-item label="鏀嚭绫诲瀷" prop="expenseType">
+ <el-select
+ v-model="form.expenseType"
+ placeholder="璇烽�夋嫨"
+ clearable
+ >
+ <el-option :label="item.label" :value="item.value" v-for="(item,index) in expense_types" :key="index" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="渚涘簲鍟嗗悕绉�" prop="supplierName">
+ <el-input v-model="form.supplierName" placeholder="璇疯緭鍏�" />
+ </el-form-item>
+ <el-form-item label="鏀嚭閲戦" prop="expenseMoney">
+ <el-input-number :step="0.01" :min="0" style="width: 100%"
+ v-model="form.expenseMoney"
+ placeholder="璇疯緭鍏�"
+ />
+ </el-form-item>
+ <el-form-item label="鏀嚭鎻忚堪" prop="expenseDescribed">
+ <el-input v-model="form.expenseDescribed" placeholder="璇疯緭鍏�" />
+ </el-form-item>
+ <el-form-item label="浠樻鏂瑰紡" prop="expenseMethod">
+ <el-select
+ v-model="form.expenseMethod"
+ placeholder="璇烽�夋嫨"
+ clearable
+ >
+ <el-option :label="item.label" :value="item.value" v-for="(item,index) in checkout_payment" :key="index" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="鍙戠エ鍙风爜" prop="invoiceNumber">
+ <el-input v-model="form.invoiceNumber" placeholder="璇疯緭鍏�" />
+ </el-form-item>
+ <el-form-item label="澶囨敞" prop="note">
+ <el-input
+ v-model="form.note"
+ placeholder="澶囨敞"
+ />
+ </el-form-item>
+ </el-form>
+ </FormDialog>
</template>
<script setup>
-import { useModal } from "@/hooks/useModal";
-import { add, update } from "@/api/financialManagement/expenseManagement";
-import Form from "./Form.vue";
+import { add, update, getAccountExpense } from "@/api/financialManagement/expenseManagement";
import { ElMessage } from "element-plus";
+import useFormData from "@/hooks/useFormData";
+import FormDialog from "@/components/Dialog/FormDialog.vue";
+import { ref } from "vue";
+
const { proxy } = getCurrentInstance()
defineOptions({
@@ -23,43 +78,96 @@
const emits = defineEmits(["success"]);
-const formRef = ref();
-const {
- id,
- visible,
- loading,
- openModal,
- modalOptions,
- handleConfirm,
- closeModal,
-} = useModal({ title: "鏀嚭" });
+const formRef = ref(null);
+const dialogVisible = ref(false);
+const operationType = ref("add"); // add | edit
+const id = ref(undefined);
+const submitting = ref(false);
+
+const dialogTitle = (type) => {
+ if (type === "edit") return "缂栬緫鏀嚭";
+ return "鏂板鏀嚭";
+};
+
+const { expense_types } = proxy.useDict("expense_types");
+const { checkout_payment } = proxy.useDict("checkout_payment");
+
+const formRules = {
+ supplierName: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
+ expenseMoney: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
+ expenseDescribed: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
+ expenseDate: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
+ expenseType: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
+ expenseMethod: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
+}
+
+const { form, resetForm } = useFormData({
+ expenseDate: undefined, // 鏀嚭鏃ユ湡
+ expenseType: undefined, // 鏀嚭绫诲瀷
+ supplierName: undefined, // 渚涘簲鍟嗗悕绉�
+ expenseMoney: undefined, // 鏀嚭閲戦
+ expenseDescribed: undefined, // 鏀嚭鎻忚堪
+ expenseMethod: undefined, // 浠樻鏂瑰紡
+ invoiceNumber: undefined, // 鍙戠エ鍙风爜
+ note: undefined, // 澶囨敞
+});
const sendForm = () => {
- proxy.$refs.formRef.$refs.formRef.validate(async valid => {
- if (valid) {
- const {code} = id.value
- ? await update({id: id.value, ...formRef.value.form})
- : await add(formRef.value.form);
- if (code == 200) {
- emits("success");
- ElMessage({message: "鎿嶄綔鎴愬姛", type: "success"});
- close();
- } else {
- loading.value = false;
- }
- }
- })
+ if (submitting.value) return;
+ formRef.value?.validate(async (valid) => {
+ if (valid) {
+ submitting.value = true;
+ try {
+ const { code } = id.value
+ ? await update({ id: id.value, ...form })
+ : await add(form);
+ if (code == 200) {
+ emits("success");
+ ElMessage({ message: "鎿嶄綔鎴愬姛", type: "success" });
+ close();
+ }
+ } finally {
+ submitting.value = false;
+ }
+ }
+ })
};
const close = () => {
- formRef.value.resetFormAndValidate();
- closeModal();
+ resetForm();
+ formRef.value?.clearValidate();
+ id.value = undefined;
+ dialogVisible.value = false;
};
-const loadForm = async (id) => {
- openModal(id);
- await nextTick();
- formRef.value.loadForm(id);
+const loadForm = async (rowId) => {
+ operationType.value = "edit";
+ id.value = rowId;
+ dialogVisible.value = true;
+ if (rowId) {
+ const { code, data } = await getAccountExpense(rowId);
+ if (code == 200) {
+ form.expenseDate = data.expenseDate;
+ form.expenseType = data.expenseType;
+ form.supplierName = data.supplierName;
+ form.expenseMoney = data.expenseMoney;
+ form.expenseDescribed = data.expenseDescribed;
+ form.expenseMethod = data.expenseMethod;
+ form.invoiceNumber = data.invoiceNumber;
+ form.note = data.note;
+ }
+ } else {
+ resetForm();
+ formRef.value?.clearValidate();
+ }
+};
+
+const openModal = () => {
+ operationType.value = "add";
+ id.value = undefined;
+ resetForm();
+ formRef.value?.clearValidate();
+ dialogVisible.value = true;
};
defineExpose({
diff --git a/src/views/financialManagement/expenseManagement/index.vue b/src/views/financialManagement/expenseManagement/index.vue
index a45c32d..2f84e84 100644
--- a/src/views/financialManagement/expenseManagement/index.vue
+++ b/src/views/financialManagement/expenseManagement/index.vue
@@ -55,12 +55,12 @@
@pagination="changePage"
>
<template #operation="{ row }">
- <el-button type="primary" text @click="edit(row.id)" icon="editPen">
+ <el-button type="primary" link @click="edit(row.id)">
缂栬緫
</el-button>
<el-button
type="primary"
- text
+ link
@click="openFilesFormDia(row)"
>
闄勪欢
@@ -69,18 +69,27 @@
</PIMTable>
</div>
<Modal ref="modalRef" @success="getTableData"></Modal>
- <files-dia ref="filesDia"></files-dia>
+ <FileListDialog
+ ref="fileListRef"
+ v-model="fileListDialogVisible"
+ :show-upload-button="true"
+ :show-delete-button="true"
+ :upload-method="handleUpload"
+ :delete-method="handleFileDelete"
+ />
</div>
</template>
<script setup>
import { usePaginationApi } from "@/hooks/usePaginationApi";
-import { listPage, delAccountExpense } from "@/api/financialManagement/expenseManagement";
+import { listPage, delAccountExpense, fileListPage, fileAdd, fileDel } from "@/api/financialManagement/expenseManagement";
import { onMounted, getCurrentInstance } from "vue";
import Modal from "./Modal.vue";
import { ElMessageBox, ElMessage } from "element-plus";
import dayjs from "dayjs";
-import FilesDia from "../revenueManagement/filesDia.vue";
+import FileListDialog from "@/components/Dialog/FileListDialog.vue";
+import request from "@/utils/request";
+import { getToken } from "@/utils/auth";
defineOptions({
name: "鏀嚭绠$悊",
@@ -92,7 +101,10 @@
const modalRef = ref();
const { checkout_payment } = proxy.useDict("checkout_payment");
const { expense_types } = proxy.useDict("expense_types");
-const filesDia = ref()
+const fileListRef = ref(null);
+const fileListDialogVisible = ref(false);
+const currentFileRow = ref(null);
+const accountType = ref('鏀嚭');
const {
filters,
@@ -111,7 +123,6 @@
[
{
label: "鏀嚭鏃ユ湡",
- align: "center",
prop: "expenseDate",
},
{
@@ -129,19 +140,16 @@
},
{
label: "渚涘簲鍟嗗悕绉�",
- align: "center",
prop: "supplierName",
},
{
label: "鏀嚭閲戦",
- align: "center",
prop: "expenseMoney",
},
{
label: "鏀嚭鎻忚堪",
- align: "center",
prop: "expenseDescribed",
},
@@ -149,6 +157,7 @@
label: "浠樻鏂瑰紡",
align: "center",
prop: "expenseMethod",
+ width: '120',
dataType: "tag",
formatData: (params) => {
if (checkout_payment.value.find((m) => m.value == params)) {
@@ -160,24 +169,20 @@
},
{
label: "鍙戠エ鍙风爜",
- align: "center",
prop: "invoiceNumber",
},
{
label: "澶囨敞",
- align: "center",
prop: "note",
},
{
label: "褰曞叆浜�",
- align: "center",
prop: "inputUser",
},
{
label: "褰曞叆鏃ユ湡",
- align: "center",
prop: "inputTime",
},
@@ -187,7 +192,7 @@
dataType: "slot",
slot: "operation",
align: "center",
- width: "200px",
+ width: "160px",
},
]
);
@@ -252,10 +257,154 @@
});
};
// 鎵撳紑闄勪欢寮规
-const openFilesFormDia = (row) => {
- nextTick(() => {
- filesDia.value?.openDialog( row,'鏀嚭')
- })
+const openFilesFormDia = async (row) => {
+ currentFileRow.value = row;
+ accountType.value = '鏀嚭';
+ try {
+ const res = await fileListPage({
+ accountId: row.id,
+ accountType: accountType.value,
+ current: 1,
+ size: 100
+ });
+ if (res.code === 200 && fileListRef.value) {
+ // 灏嗘暟鎹浆鎹负 FileListDialog 闇�瑕佺殑鏍煎紡
+ const fileList = (res.data?.records || []).map(item => ({
+ name: item.name,
+ url: item.url,
+ id: item.id,
+ ...item
+ }));
+ fileListRef.value.open(fileList);
+ fileListDialogVisible.value = true;
+ }
+ } catch (error) {
+ proxy.$modal.msgError("鑾峰彇闄勪欢鍒楄〃澶辫触");
+ }
+};
+
+// 涓婁紶闄勪欢
+const handleUpload = async () => {
+ if (!currentFileRow.value) {
+ proxy.$modal.msgWarning("璇峰厛閫夋嫨鏁版嵁");
+ return null;
+ }
+
+ return new Promise((resolve) => {
+ // 鍒涘缓涓�涓殣钘忕殑鏂囦欢杈撳叆鍏冪礌
+ const input = document.createElement('input');
+ input.type = 'file';
+ input.style.display = 'none';
+ input.onchange = async (e) => {
+ const file = e.target.files[0];
+ if (!file) {
+ resolve(null);
+ return;
+ }
+
+ try {
+ // 浣跨敤 FormData 涓婁紶鏂囦欢
+ const formData = new FormData();
+ formData.append('file', file);
+
+ const uploadRes = await request({
+ url: '/file/upload',
+ method: 'post',
+ data: formData,
+ headers: {
+ 'Content-Type': 'multipart/form-data',
+ Authorization: `Bearer ${getToken()}`
+ }
+ });
+
+ if (uploadRes.code === 200) {
+ // 淇濆瓨闄勪欢淇℃伅
+ const fileData = {
+ accountId: currentFileRow.value.id,
+ accountType: accountType.value,
+ name: uploadRes.data.originalName || file.name,
+ url: uploadRes.data.tempPath || uploadRes.data.url
+ };
+
+ const saveRes = await fileAdd(fileData);
+ if (saveRes.code === 200) {
+ proxy.$modal.msgSuccess("鏂囦欢涓婁紶鎴愬姛");
+ // 閲嶆柊鍔犺浇鏂囦欢鍒楄〃
+ const listRes = await fileListPage({
+ accountId: currentFileRow.value.id,
+ accountType: accountType.value,
+ current: 1,
+ size: 100
+ });
+ if (listRes.code === 200 && fileListRef.value) {
+ const fileList = (listRes.data?.records || []).map(item => ({
+ name: item.name,
+ url: item.url,
+ id: item.id,
+ ...item
+ }));
+ fileListRef.value.setList(fileList);
+ }
+ // 杩斿洖鏂版枃浠朵俊鎭�
+ resolve({
+ name: fileData.name,
+ url: fileData.url,
+ id: saveRes.data?.id
+ });
+ } else {
+ proxy.$modal.msgError(saveRes.msg || "鏂囦欢淇濆瓨澶辫触");
+ resolve(null);
+ }
+ } else {
+ proxy.$modal.msgError(uploadRes.msg || "鏂囦欢涓婁紶澶辫触");
+ resolve(null);
+ }
+ } catch (error) {
+ proxy.$modal.msgError("鏂囦欢涓婁紶澶辫触");
+ resolve(null);
+ } finally {
+ document.body.removeChild(input);
+ }
+ };
+
+ document.body.appendChild(input);
+ input.click();
+ });
+};
+
+// 鍒犻櫎闄勪欢
+const handleFileDelete = async (row) => {
+ try {
+ const res = await fileDel([row.id]);
+ if (res.code === 200) {
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ // 閲嶆柊鍔犺浇鏂囦欢鍒楄〃
+ if (currentFileRow.value && fileListRef.value) {
+ const listRes = await fileListPage({
+ accountId: currentFileRow.value.id,
+ accountType: accountType.value,
+ current: 1,
+ size: 100
+ });
+ if (listRes.code === 200) {
+ const fileList = (listRes.data?.records || []).map(item => ({
+ name: item.name,
+ url: item.url,
+ id: item.id,
+ ...item
+ }));
+ fileListRef.value.setList(fileList);
+ }
+ }
+ return true; // 杩斿洖 true 琛ㄧず鍒犻櫎鎴愬姛锛岀粍浠朵細鏇存柊鍒楄〃
+ } else {
+ proxy.$modal.msgError(res.msg || "鍒犻櫎澶辫触");
+ return false;
+ }
+ } catch (error) {
+ proxy.$modal.msgError("鍒犻櫎澶辫触");
+ return false;
+ }
};
onMounted(() => {
diff --git a/src/views/financialManagement/loanManagement/index.vue b/src/views/financialManagement/loanManagement/index.vue
index 202313a..7580d3b 100644
--- a/src/views/financialManagement/loanManagement/index.vue
+++ b/src/views/financialManagement/loanManagement/index.vue
@@ -72,7 +72,7 @@
缂栬緫
</el-button>
<el-button
- v-if="row.status == 1"
+ :disabled="row.status !== 1"
type="primary"
link
@click="repay(row)"
@@ -122,12 +122,10 @@
{
label: "鍊熸浜哄鍚�",
prop: "borrowerName",
- width: 150,
},
{
label: "鍊熸閲戦锛堝厓锛�",
prop: "borrowAmount",
- width: 150,
formatData: (val) => {
return val ? `楼${parseFloat(val).toLocaleString('zh-CN', { minimumFractionDigits: 2, maximumFractionDigits: 2 })}` : '楼0.00';
},
@@ -135,7 +133,6 @@
{
label: "鍊熸鍒╃巼锛�%锛�",
prop: "interestRate",
- width: 130,
formatData: (val) => {
return val ? `${parseFloat(val).toFixed(2)}%` : '-';
},
@@ -143,18 +140,16 @@
{
label: "鍊熸鏃ユ湡",
prop: "borrowDate",
- width: 120,
},
{
label: "瀹為檯杩樻鏃ユ湡",
prop: "repayDate",
- width: 130,
},
{
label: "鍊熸鐘舵��",
prop: "status",
- width: 100,
dataType: "tag",
+ align: 'center',
formatData: (params) => {
if (params == 1) {
return "寰呰繕娆�";
diff --git a/src/views/financialManagement/revenueManagement/Form.vue b/src/views/financialManagement/revenueManagement/Form.vue
deleted file mode 100644
index 67b175e..0000000
--- a/src/views/financialManagement/revenueManagement/Form.vue
+++ /dev/null
@@ -1,123 +0,0 @@
-<template>
- <el-form :model="form" label-width="100px" :rules="formRules" ref="formRef">
- <el-form-item label="鏀跺叆鏃ユ湡" prop="incomeDate">
- <el-date-picker
- style="width: 100%"
- v-model="form.incomeDate"
- format="YYYY-MM-DD"
- value-format="YYYY-MM-DD"
- type="date"
- placeholder="璇烽�夋嫨鏃ユ湡"
- clearable
- />
- </el-form-item>
- <el-form-item label="鏀跺叆绫诲瀷" prop="incomeType">
- <el-select
- v-model="form.incomeType"
- placeholder="璇烽�夋嫨"
- clearable
- >
- <el-option :label="item.label" :value="item.value" v-for="(item,index) in income_types" :key="index" />
- </el-select>
- </el-form-item>
- <el-form-item label="瀹㈡埛鍚嶇О" prop="customerName">
- <el-input v-model="form.customerName" placeholder="璇疯緭鍏�" />
- </el-form-item>
- <el-form-item label="鏀跺叆閲戦" prop="incomeMoney">
- <el-input-number :step="0.01" :min="0" style="width: 100%"
- v-model="form.incomeMoney"
- placeholder="璇疯緭鍏�"
- />
- </el-form-item>
- <el-form-item label="鏀跺叆鎻忚堪" prop="incomeDescribed">
- <el-input v-model="form.incomeDescribed" placeholder="璇疯緭鍏�" />
- </el-form-item>
- <el-form-item label="鏀舵鏂瑰紡" prop="incomeMethod">
- <el-select
- v-model="form.incomeMethod"
- placeholder="璇烽�夋嫨"
- clearable
- >
- <el-option :label="item.label" :value="item.value" v-for="(item,index) in payment_methods" :key="index" />
- </el-select>
- </el-form-item>
- <el-form-item label="鍙戠エ鍙风爜" prop="invoiceNumber">
- <el-input v-model="form.invoiceNumber" placeholder="璇疯緭鍏�" />
- </el-form-item>
- <el-form-item label="澶囨敞" prop="note">
- <el-input
- v-model="form.note"
- placeholder="澶囨敞"
- />
- </el-form-item>
-
- </el-form>
-</template>
-
-<script setup>
-import useFormData from "@/hooks/useFormData";
-import { getAccountIncome } from "@/api/financialManagement/revenueManagement";
-import {ref} from "vue";
-const { proxy } = getCurrentInstance();
-
-
-defineOptions({
- name: "鏂板鏀跺叆",
-});
-const { income_types } = proxy.useDict("income_types");
-const { payment_methods } = proxy.useDict("payment_methods");
-const formRef = ref(null);
-const formRules = {
- customerName: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
- incomeMoney: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
- incomeDescribed: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
- incomeDate: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
- incomeType: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
- incomeMethod: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
-}
-
-const { form, resetForm } = useFormData({
- incomeDate: undefined, // 鏀跺叆鏃ユ湡
- incomeType: undefined, // 鏀跺叆绫诲瀷
- customerName: undefined, // 瀹㈡埛鍚嶇О
- incomeMoney: undefined, // 鏀跺叆閲戦
- incomeDescribed: undefined, // 鏀跺叆鎻忚堪
- incomeMethod: undefined, // 鏀舵鏂瑰紡
- invoiceNumber: undefined, // 鍙戠エ鍙风爜
- note: undefined, // 澶囨敞
-});
-
-const loadForm = async (id) => {
- const { code, data } = await getAccountIncome(id);
- if (code == 200) {
- form.incomeDate = data.incomeDate;
- form.incomeType = data.incomeType;
- form.customerName = data.customerName;
- form.incomeMoney = data.incomeMoney;
- form.incomeDescribed = data.incomeDescribed;
- form.incomeMethod = data.incomeMethod;
- form.invoiceNumber = data.invoiceNumber;
- form.note = data.note;
- }
-};
-
-// 娓呴櫎琛ㄥ崟鏍¢獙鐘舵��
-const clearValidate = () => {
- formRef.value?.clearValidate();
-};
-
-// 閲嶇疆琛ㄥ崟鏁版嵁鍜屾牎楠岀姸鎬�
-const resetFormAndValidate = () => {
- resetForm();
- clearValidate();
-};
-
-defineExpose({
- form,
- loadForm,
- resetForm,
- clearValidate,
- resetFormAndValidate,
- formRef,
-});
-</script>
diff --git a/src/views/financialManagement/revenueManagement/Modal.vue b/src/views/financialManagement/revenueManagement/Modal.vue
index 480b4fd..245cdf2 100644
--- a/src/views/financialManagement/revenueManagement/Modal.vue
+++ b/src/views/financialManagement/revenueManagement/Modal.vue
@@ -1,20 +1,75 @@
<template>
- <el-dialog :title="modalOptions.title" v-model="visible" @close="close" width="30%">
- <Form ref="formRef"></Form>
- <template #footer>
- <el-button type="primary" @click="sendForm" :loading="loading">
- {{ modalOptions.confirmText }}
- </el-button>
- <el-button @click="closeModal">{{ modalOptions.cancelText }}</el-button>
- </template>
- </el-dialog>
+ <FormDialog
+ v-model="dialogVisible"
+ :title="dialogTitle"
+ :operationType="operationType"
+ width="30%"
+ @confirm="sendForm"
+ @close="close"
+ @cancel="close"
+ >
+ <el-form :model="form" label-width="100px" :rules="formRules" ref="formRef">
+ <el-form-item label="鏀跺叆鏃ユ湡" prop="incomeDate">
+ <el-date-picker
+ style="width: 100%"
+ v-model="form.incomeDate"
+ format="YYYY-MM-DD"
+ value-format="YYYY-MM-DD"
+ type="date"
+ placeholder="璇烽�夋嫨鏃ユ湡"
+ clearable
+ />
+ </el-form-item>
+ <el-form-item label="鏀跺叆绫诲瀷" prop="incomeType">
+ <el-select
+ v-model="form.incomeType"
+ placeholder="璇烽�夋嫨"
+ clearable
+ >
+ <el-option :label="item.label" :value="item.value" v-for="(item,index) in income_types" :key="index" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="瀹㈡埛鍚嶇О" prop="customerName">
+ <el-input v-model="form.customerName" placeholder="璇疯緭鍏�" />
+ </el-form-item>
+ <el-form-item label="鏀跺叆閲戦" prop="incomeMoney">
+ <el-input-number :step="0.01" :min="0" style="width: 100%"
+ v-model="form.incomeMoney"
+ placeholder="璇疯緭鍏�"
+ />
+ </el-form-item>
+ <el-form-item label="鏀跺叆鎻忚堪" prop="incomeDescribed">
+ <el-input v-model="form.incomeDescribed" placeholder="璇疯緭鍏�" />
+ </el-form-item>
+ <el-form-item label="鏀舵鏂瑰紡" prop="incomeMethod">
+ <el-select
+ v-model="form.incomeMethod"
+ placeholder="璇烽�夋嫨"
+ clearable
+ >
+ <el-option :label="item.label" :value="item.value" v-for="(item,index) in payment_methods" :key="index" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="鍙戠エ鍙风爜" prop="invoiceNumber">
+ <el-input v-model="form.invoiceNumber" placeholder="璇疯緭鍏�" />
+ </el-form-item>
+ <el-form-item label="澶囨敞" prop="note">
+ <el-input
+ v-model="form.note"
+ placeholder="澶囨敞"
+ />
+ </el-form-item>
+ </el-form>
+ </FormDialog>
</template>
<script setup>
-import { useModal } from "@/hooks/useModal";
-import { add, update } from "@/api/financialManagement/revenueManagement";
-import Form from "./Form.vue";
+import { add, update, getAccountIncome } from "@/api/financialManagement/revenueManagement";
import { ElMessage } from "element-plus";
+import useFormData from "@/hooks/useFormData";
+import FormDialog from "@/components/Dialog/FormDialog.vue";
+import { ref } from "vue";
+
const { proxy } = getCurrentInstance()
defineOptions({
@@ -23,43 +78,96 @@
const emits = defineEmits(["success"]);
-const formRef = ref();
-const {
- id,
- visible,
- loading,
- openModal,
- modalOptions,
- handleConfirm,
- closeModal,
-} = useModal({ title: "鏀跺叆" });
+const formRef = ref(null);
+const dialogVisible = ref(false);
+const operationType = ref("add"); // add | edit
+const id = ref(undefined);
+const submitting = ref(false);
+
+const dialogTitle = (type) => {
+ if (type === "edit") return "缂栬緫鏀跺叆";
+ return "鏂板鏀跺叆";
+};
+
+const { income_types } = proxy.useDict("income_types");
+const { payment_methods } = proxy.useDict("payment_methods");
+
+const formRules = {
+ customerName: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
+ incomeMoney: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
+ incomeDescribed: [{ required: true, trigger: "blur", message: "璇疯緭鍏�" }],
+ incomeDate: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
+ incomeType: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
+ incomeMethod: [{ required: true, trigger: "change", message: "璇烽�夋嫨" }],
+}
+
+const { form, resetForm } = useFormData({
+ incomeDate: undefined, // 鏀跺叆鏃ユ湡
+ incomeType: undefined, // 鏀跺叆绫诲瀷
+ customerName: undefined, // 瀹㈡埛鍚嶇О
+ incomeMoney: undefined, // 鏀跺叆閲戦
+ incomeDescribed: undefined, // 鏀跺叆鎻忚堪
+ incomeMethod: undefined, // 鏀舵鏂瑰紡
+ invoiceNumber: undefined, // 鍙戠エ鍙风爜
+ note: undefined, // 澶囨敞
+});
const sendForm = () => {
- proxy.$refs.formRef.$refs.formRef.validate(async valid => {
- if (valid) {
- const {code} = id.value
- ? await update({id: id.value, ...formRef.value.form})
- : await add(formRef.value.form);
- if (code == 200) {
- emits("success");
- ElMessage({message: "鎿嶄綔鎴愬姛", type: "success"});
- close();
- } else {
- loading.value = false;
- }
- }
- })
+ if (submitting.value) return;
+ formRef.value?.validate(async (valid) => {
+ if (valid) {
+ submitting.value = true;
+ try {
+ const { code } = id.value
+ ? await update({ id: id.value, ...form })
+ : await add(form);
+ if (code == 200) {
+ emits("success");
+ ElMessage({ message: "鎿嶄綔鎴愬姛", type: "success" });
+ close();
+ }
+ } finally {
+ submitting.value = false;
+ }
+ }
+ })
};
const close = () => {
- formRef.value.resetFormAndValidate();
- closeModal();
+ resetForm();
+ formRef.value?.clearValidate();
+ id.value = undefined;
+ dialogVisible.value = false;
};
-const loadForm = async (id) => {
- openModal(id);
- await nextTick();
- formRef.value.loadForm(id);
+const loadForm = async (rowId) => {
+ operationType.value = "edit";
+ id.value = rowId;
+ dialogVisible.value = true;
+ if (rowId) {
+ const { code, data } = await getAccountIncome(rowId);
+ if (code == 200) {
+ form.incomeDate = data.incomeDate;
+ form.incomeType = data.incomeType;
+ form.customerName = data.customerName;
+ form.incomeMoney = data.incomeMoney;
+ form.incomeDescribed = data.incomeDescribed;
+ form.incomeMethod = data.incomeMethod;
+ form.invoiceNumber = data.invoiceNumber;
+ form.note = data.note;
+ }
+ } else {
+ resetForm();
+ formRef.value?.clearValidate();
+ }
+};
+
+const openModal = () => {
+ operationType.value = "add";
+ id.value = undefined;
+ resetForm();
+ formRef.value?.clearValidate();
+ dialogVisible.value = true;
};
defineExpose({
diff --git a/src/views/financialManagement/revenueManagement/filesDia.vue b/src/views/financialManagement/revenueManagement/filesDia.vue
deleted file mode 100644
index f752496..0000000
--- a/src/views/financialManagement/revenueManagement/filesDia.vue
+++ /dev/null
@@ -1,202 +0,0 @@
-<template>
- <div>
- <el-dialog
- v-model="dialogFormVisible"
- title="涓婁紶闄勪欢"
- width="50%"
- @close="closeDia"
- >
- <div style="margin-bottom: 10px;text-align: right">
- <el-upload
- v-model:file-list="fileList"
- class="upload-demo"
- :action="uploadUrl"
- :on-success="handleUploadSuccess"
- :on-error="handleUploadError"
- name="file"
- :show-file-list="false"
- :headers="headers"
- style="display: inline;margin-right: 10px"
- >
- <el-button type="primary">涓婁紶闄勪欢</el-button>
- </el-upload>
- <el-button type="danger" plain @click="handleDelete">鍒犻櫎</el-button>
- </div>
- <PIMTable
- rowKey="id"
- :column="tableColumn"
- :tableData="tableData"
- :tableLoading="tableLoading"
- :isSelection="true"
- @selection-change="handleSelectionChange"
- height="500"
- >
- </PIMTable>
- <pagination
- style="margin: 10px 0"
- v-show="total > 0"
- @pagination="paginationSearch"
- :total="total"
- :page="page.current"
- :limit="page.size"
- />
- <template #footer>
- <div class="dialog-footer">
- <el-button @click="closeDia">鍙栨秷</el-button>
- </div>
- </template>
- </el-dialog>
- <filePreview ref="filePreviewRef" />
- </div>
-</template>
-
-<script setup>
-import {ref} from "vue";
-import {ElMessageBox} from "element-plus";
-import {getToken} from "@/utils/auth.js";
-import filePreview from '@/components/filePreview/index.vue'
-import {
- fileAdd,
- fileDel,
- fileListPage
-} from "@/api/financialManagement/revenueManagement.js";
-import Pagination from "@/components/PIMTable/Pagination.vue";
-const { proxy } = getCurrentInstance()
-const emit = defineEmits(['close'])
-
-const dialogFormVisible = ref(false);
-const currentId = ref('')
-const selectedRows = ref([]);
-const filePreviewRef = ref()
-const tableColumn = ref([
- {
- label: "鏂囦欢鍚嶇О",
- prop: "name",
- },
- {
- dataType: "action",
- label: "鎿嶄綔",
- align: "center",
- operation: [
- {
- name: "涓嬭浇",
- type: "text",
- clickFun: (row) => {
- downLoadFile(row);
- },
- },
- {
- name: "棰勮",
- type: "text",
- clickFun: (row) => {
- lookFile(row);
- },
- }
- ],
- },
-]);
-const page = reactive({
- current: 1,
- size: 100,
-});
-const total = ref(0);
-const tableData = ref([]);
-const fileList = ref([]);
-const tableLoading = ref(false);
-const accountType = ref('')
-const headers = ref({
- Authorization: "Bearer " + getToken(),
-});
-const uploadUrl = ref(import.meta.env.VITE_APP_BASE_API + "/file/upload"); // 涓婁紶鐨勫浘鐗囨湇鍔″櫒鍦板潃
-
-// 鎵撳紑寮规
-const openDialog = (row,type) => {
- accountType.value = type;
- dialogFormVisible.value = true;
- currentId.value = row.id;
- getList()
-}
-const paginationSearch = (obj) => {
- page.current = obj.page;
- page.size = obj.limit;
- getList();
-};
-const getList = () => {
- fileListPage({accountId: currentId.value,accountType:accountType.value, ...page}).then(res => {
- tableData.value = res.data.records;
- total.value = res.data.total;
- })
-}
-// 琛ㄦ牸閫夋嫨鏁版嵁
-const handleSelectionChange = (selection) => {
- selectedRows.value = selection;
-};
-
-// 鍏抽棴寮规
-const closeDia = () => {
- dialogFormVisible.value = false;
- emit('close')
-};
-// 涓婁紶鎴愬姛澶勭悊
-function handleUploadSuccess(res, file) {
- // 濡傛灉涓婁紶鎴愬姛
- if (res.code == 200) {
- const fileRow = {}
- fileRow.name = res.data.originalName
- fileRow.url = res.data.tempPath
- uploadFile(fileRow)
- } else {
- proxy.$modal.msgError("鏂囦欢涓婁紶澶辫触");
- }
-}
-function uploadFile(file) {
- file.accountId = currentId.value;
- file.accountType = accountType.value;
- fileAdd(file).then(res => {
- proxy.$modal.msgSuccess("鏂囦欢涓婁紶鎴愬姛");
- getList()
- })
-}
-// 涓婁紶澶辫触澶勭悊
-function handleUploadError() {
- proxy.$modal.msgError("鏂囦欢涓婁紶澶辫触");
-}
-// 涓嬭浇闄勪欢
-const downLoadFile = (row) => {
- proxy.$download.name(row.url);
-}
-// 鍒犻櫎
-const handleDelete = () => {
- let ids = [];
- if (selectedRows.value.length > 0) {
- ids = selectedRows.value.map((item) => item.id);
- } else {
- proxy.$modal.msgWarning("璇烽�夋嫨鏁版嵁");
- return;
- }
- ElMessageBox.confirm("閫変腑鐨勫唴瀹瑰皢琚垹闄わ紝鏄惁纭鍒犻櫎锛�", "瀵煎嚭", {
- confirmButtonText: "纭",
- cancelButtonText: "鍙栨秷",
- type: "warning",
- }).then(() => {
- fileDel(ids).then((res) => {
- proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
- getList();
- });
- }).catch(() => {
- proxy.$modal.msg("宸插彇娑�");
- });
-};
-// 棰勮闄勪欢
-const lookFile = (row) => {
- filePreviewRef.value.open(row.url)
-}
-
-defineExpose({
- openDialog,
-});
-</script>
-
-<style scoped>
-
-</style>
\ No newline at end of file
diff --git a/src/views/financialManagement/revenueManagement/index.vue b/src/views/financialManagement/revenueManagement/index.vue
index 9dcd23e..47961e5 100644
--- a/src/views/financialManagement/revenueManagement/index.vue
+++ b/src/views/financialManagement/revenueManagement/index.vue
@@ -55,12 +55,12 @@
@pagination="changePage"
>
<template #operation="{ row }">
- <el-button type="primary" text @click="edit(row.id)" icon="editPen">
+ <el-button type="primary" link @click="edit(row.id)">
缂栬緫
</el-button>
<el-button
type="primary"
- text
+ link
@click="openFilesFormDia(row)"
>
闄勪欢
@@ -69,18 +69,27 @@
</PIMTable>
</div>
<Modal ref="modalRef" @success="getTableData"></Modal>
- <files-dia ref="filesDia"></files-dia>
+ <FileListDialog
+ ref="fileListRef"
+ v-model="fileListDialogVisible"
+ :show-upload-button="true"
+ :show-delete-button="true"
+ :upload-method="handleUpload"
+ :delete-method="handleFileDelete"
+ />
</div>
</template>
<script setup>
import { usePaginationApi } from "@/hooks/usePaginationApi";
-import { listPage, delAccountIncome } from "@/api/financialManagement/revenueManagement";
+import { listPage, delAccountIncome, fileListPage, fileAdd, fileDel } from "@/api/financialManagement/revenueManagement";
import { onMounted, getCurrentInstance } from "vue";
import Modal from "./Modal.vue";
import { ElMessageBox, ElMessage } from "element-plus";
import dayjs from "dayjs";
-import FilesDia from "./filesDia.vue";
+import FileListDialog from "@/components/Dialog/FileListDialog.vue";
+import request from "@/utils/request";
+import { getToken } from "@/utils/auth";
defineOptions({
name: "鏀跺叆绠$悊",
@@ -92,7 +101,10 @@
const modalRef = ref();
const { payment_methods } = proxy.useDict("payment_methods");
const { income_types } = proxy.useDict("income_types");
-const filesDia = ref()
+const fileListRef = ref(null);
+const fileListDialogVisible = ref(false);
+const currentFileRow = ref(null);
+const accountType = ref('鏀跺叆');
const {
filters,
@@ -111,12 +123,10 @@
[
{
label: "鏀跺叆鏃ユ湡",
- align: "center",
prop: "incomeDate",
},
{
label: "鏀跺叆绫诲瀷",
- align: "center",
prop: "incomeType",
dataType: "tag",
formatData: (params) => {
@@ -129,26 +139,25 @@
},
{
label: "瀹㈡埛鍚嶇О",
- align: "center",
prop: "customerName",
+ width: '200'
},
{
label: "鏀跺叆閲戦",
- align: "center",
prop: "incomeMoney",
},
{
label: "鏀跺叆鎻忚堪",
- align: "center",
prop: "incomeDescribed",
},
{
label: "鏀舵鏂瑰紡",
- align: "center",
prop: "incomeMethod",
+ align: 'center',
+ width: '100',
dataType: "tag",
formatData: (params) => {
if (payment_methods.value.find((m) => m.value == params)) {
@@ -160,24 +169,20 @@
},
{
label: "鍙戠エ鍙风爜",
- align: "center",
prop: "invoiceNumber",
},
{
label: "澶囨敞",
- align: "center",
prop: "note",
},
{
label: "褰曞叆浜�",
- align: "center",
prop: "inputUser",
},
{
label: "褰曞叆鏃ユ湡",
- align: "center",
prop: "inputTime",
},
@@ -187,7 +192,7 @@
dataType: "slot",
slot: "operation",
align: "center",
- width: "200px",
+ width: "160px",
},
]
);
@@ -252,10 +257,154 @@
});
};
// 鎵撳紑闄勪欢寮规
-const openFilesFormDia = (row) => {
- nextTick(() => {
- filesDia.value?.openDialog( row,'鏀跺叆')
- })
+const openFilesFormDia = async (row) => {
+ currentFileRow.value = row;
+ accountType.value = '鏀跺叆';
+ try {
+ const res = await fileListPage({
+ accountId: row.id,
+ accountType: accountType.value,
+ current: 1,
+ size: 100
+ });
+ if (res.code === 200 && fileListRef.value) {
+ // 灏嗘暟鎹浆鎹负 FileListDialog 闇�瑕佺殑鏍煎紡
+ const fileList = (res.data?.records || []).map(item => ({
+ name: item.name,
+ url: item.url,
+ id: item.id,
+ ...item
+ }));
+ fileListRef.value.open(fileList);
+ fileListDialogVisible.value = true;
+ }
+ } catch (error) {
+ proxy.$modal.msgError("鑾峰彇闄勪欢鍒楄〃澶辫触");
+ }
+};
+
+// 涓婁紶闄勪欢
+const handleUpload = async () => {
+ if (!currentFileRow.value) {
+ proxy.$modal.msgWarning("璇峰厛閫夋嫨鏁版嵁");
+ return null;
+ }
+
+ return new Promise((resolve) => {
+ // 鍒涘缓涓�涓殣钘忕殑鏂囦欢杈撳叆鍏冪礌
+ const input = document.createElement('input');
+ input.type = 'file';
+ input.style.display = 'none';
+ input.onchange = async (e) => {
+ const file = e.target.files[0];
+ if (!file) {
+ resolve(null);
+ return;
+ }
+
+ try {
+ // 浣跨敤 FormData 涓婁紶鏂囦欢
+ const formData = new FormData();
+ formData.append('file', file);
+
+ const uploadRes = await request({
+ url: '/file/upload',
+ method: 'post',
+ data: formData,
+ headers: {
+ 'Content-Type': 'multipart/form-data',
+ Authorization: `Bearer ${getToken()}`
+ }
+ });
+
+ if (uploadRes.code === 200) {
+ // 淇濆瓨闄勪欢淇℃伅
+ const fileData = {
+ accountId: currentFileRow.value.id,
+ accountType: accountType.value,
+ name: uploadRes.data.originalName || file.name,
+ url: uploadRes.data.tempPath || uploadRes.data.url
+ };
+
+ const saveRes = await fileAdd(fileData);
+ if (saveRes.code === 200) {
+ proxy.$modal.msgSuccess("鏂囦欢涓婁紶鎴愬姛");
+ // 閲嶆柊鍔犺浇鏂囦欢鍒楄〃
+ const listRes = await fileListPage({
+ accountId: currentFileRow.value.id,
+ accountType: accountType.value,
+ current: 1,
+ size: 100
+ });
+ if (listRes.code === 200 && fileListRef.value) {
+ const fileList = (listRes.data?.records || []).map(item => ({
+ name: item.name,
+ url: item.url,
+ id: item.id,
+ ...item
+ }));
+ fileListRef.value.setList(fileList);
+ }
+ // 杩斿洖鏂版枃浠朵俊鎭�
+ resolve({
+ name: fileData.name,
+ url: fileData.url,
+ id: saveRes.data?.id
+ });
+ } else {
+ proxy.$modal.msgError(saveRes.msg || "鏂囦欢淇濆瓨澶辫触");
+ resolve(null);
+ }
+ } else {
+ proxy.$modal.msgError(uploadRes.msg || "鏂囦欢涓婁紶澶辫触");
+ resolve(null);
+ }
+ } catch (error) {
+ proxy.$modal.msgError("鏂囦欢涓婁紶澶辫触");
+ resolve(null);
+ } finally {
+ document.body.removeChild(input);
+ }
+ };
+
+ document.body.appendChild(input);
+ input.click();
+ });
+};
+
+// 鍒犻櫎闄勪欢
+const handleFileDelete = async (row) => {
+ try {
+ const res = await fileDel([row.id]);
+ if (res.code === 200) {
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ // 閲嶆柊鍔犺浇鏂囦欢鍒楄〃
+ if (currentFileRow.value && fileListRef.value) {
+ const listRes = await fileListPage({
+ accountId: currentFileRow.value.id,
+ accountType: accountType.value,
+ current: 1,
+ size: 100
+ });
+ if (listRes.code === 200) {
+ const fileList = (listRes.data?.records || []).map(item => ({
+ name: item.name,
+ url: item.url,
+ id: item.id,
+ ...item
+ }));
+ fileListRef.value.setList(fileList);
+ }
+ }
+ return true; // 杩斿洖 true 琛ㄧず鍒犻櫎鎴愬姛锛岀粍浠朵細鏇存柊鍒楄〃
+ } else {
+ proxy.$modal.msgError(res.msg || "鍒犻櫎澶辫触");
+ return false;
+ }
+ } catch (error) {
+ proxy.$modal.msgError("鍒犻櫎澶辫触");
+ return false;
+ }
};
onMounted(() => {
diff --git a/src/views/procurementManagement/paymentEntry/index.vue b/src/views/procurementManagement/paymentEntry/index.vue
index 89152bf..5ee8d17 100644
--- a/src/views/procurementManagement/paymentEntry/index.vue
+++ b/src/views/procurementManagement/paymentEntry/index.vue
@@ -537,7 +537,7 @@
})
.then(() => {
tableLoading.value = true;
- delPaymentRegistration(row.id)
+ delPaymentRegistration([row.id])
.then((res) => {
proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
getList();
diff --git a/src/views/procurementManagement/paymentHistory/index.vue b/src/views/procurementManagement/paymentHistory/index.vue
index c38b4b0..179373b 100644
--- a/src/views/procurementManagement/paymentHistory/index.vue
+++ b/src/views/procurementManagement/paymentHistory/index.vue
@@ -43,6 +43,13 @@
鎼滅储
</el-button>
<el-button @click="handleExport">瀵煎嚭</el-button>
+ <el-button
+ type="danger"
+ :disabled="selectedRows.length === 0"
+ @click="handleBatchDelete"
+ >
+ 鎵归噺鍒犻櫎 ({{ selectedRows.length }})
+ </el-button>
</el-form-item>
</el-form>
<div class="table_list">
@@ -58,7 +65,18 @@
:tableLoading="tableLoading"
@pagination="pagination"
:total="page.total"
- ></PIMTable>
+ >
+ <template #operation="{ row }">
+ <el-button
+ type="primary"
+ link
+ size="small"
+ @click="handleDelete(row)"
+ >
+ 鍒犻櫎
+ </el-button>
+ </template>
+ </PIMTable>
</div>
</div>
</template>
@@ -66,7 +84,9 @@
<script setup>
import { ref, reactive, getCurrentInstance, onMounted } from "vue";
import { Search } from "@element-plus/icons-vue";
-import { paymentHistoryListPage } from "@/api/procurementManagement/paymentEntry.js";
+import { ElMessageBox } from "element-plus";
+import { paymentHistoryListPage} from "@/api/procurementManagement/paymentEntry.js";
+import {delPaymentRegistration } from "@/api/procurementManagement/procurementInvoiceLedger.js";
import useFormData from "@/hooks/useFormData";
import dayjs from "dayjs";
@@ -104,6 +124,13 @@
{
label: "鐧昏鏃ユ湡",
prop: "registrationtDate",
+ },
+ {
+ label: "鎿嶄綔",
+ dataType: "slot",
+ slot: "operation",
+ width: 100,
+ align: "center",
},
]);
const tableData = ref([]);
@@ -170,6 +197,62 @@
getList();
};
+// 鍒犻櫎
+const handleDelete = (row) => {
+ ElMessageBox.confirm("閫変腑鐨勫唴瀹瑰皢琚垹闄わ紝鏄惁纭鍒犻櫎锛�", "鍒犻櫎鎻愮ず", {
+ confirmButtonText: "纭",
+ cancelButtonText: "鍙栨秷",
+ type: "warning",
+ })
+ .then(() => {
+ tableLoading.value = true;
+ delPaymentRegistration([row.id])
+ .then((res) => {
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ getList();
+ })
+ .finally(() => {
+ tableLoading.value = false;
+ });
+ })
+ .catch(() => {
+ proxy.$modal.msg("宸插彇娑�");
+ });
+};
+
+// 鎵归噺鍒犻櫎
+const handleBatchDelete = () => {
+ if (selectedRows.value.length === 0) {
+ proxy.$modal.msgWarning("璇烽�夋嫨瑕佸垹闄ょ殑鏁版嵁");
+ return;
+ }
+ ElMessageBox.confirm(
+ `纭畾瑕佸垹闄ら�変腑鐨� ${selectedRows.value.length} 鏉℃暟鎹悧锛焋,
+ "鍒犻櫎鎻愮ず",
+ {
+ confirmButtonText: "纭",
+ cancelButtonText: "鍙栨秷",
+ type: "warning",
+ }
+ )
+ .then(() => {
+ tableLoading.value = true;
+ const ids = selectedRows.value.map((item) => item.id);
+ delPaymentRegistration(ids)
+ .then((res) => {
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ selectedRows.value = [];
+ getList();
+ })
+ .finally(() => {
+ tableLoading.value = false;
+ });
+ })
+ .catch(() => {
+ proxy.$modal.msg("宸插彇娑�");
+ });
+};
+
// 瀵煎嚭
const handleExport = () => {
const { paymentDate, ...rest } = searchForm;
diff --git a/src/views/salesManagement/receiptPaymentHistory/index.vue b/src/views/salesManagement/receiptPaymentHistory/index.vue
index 7bcb433..f66bed7 100644
--- a/src/views/salesManagement/receiptPaymentHistory/index.vue
+++ b/src/views/salesManagement/receiptPaymentHistory/index.vue
@@ -27,6 +27,13 @@
<el-form-item>
<el-button type="primary" @click="handleQuery"> 鎼滅储 </el-button>
<el-button @click="handleExport">瀵煎嚭</el-button>
+ <el-button
+ type="danger"
+ :disabled="selectedRows.length === 0"
+ @click="handleBatchDelete"
+ >
+ 鎵归噺鍒犻櫎 ({{ selectedRows.length }})
+ </el-button>
</el-form-item>
</el-form>
<div class="table_list">
@@ -42,7 +49,18 @@
:total="page.total"
@pagination="pagination"
@selection-change="handleSelectionChange"
- ></PIMTable>
+ >
+ <template #operation="{ row }">
+ <el-button
+ type="primary"
+ link
+ size="small"
+ @click="handleDelete(row)"
+ >
+ 鍒犻櫎
+ </el-button>
+ </template>
+ </PIMTable>
</div>
</div>
</template>
@@ -50,7 +68,8 @@
<script setup>
import { ref, reactive, getCurrentInstance, onMounted } from "vue";
import { Search } from "@element-plus/icons-vue";
-import { receiptPaymentHistoryListPage } from "@/api/salesManagement/receiptPayment.js";
+import { ElMessageBox } from "element-plus";
+import { receiptPaymentHistoryListPage, receiptPaymentDel } from "@/api/salesManagement/receiptPayment.js";
import useFormData from "@/hooks/useFormData";
import dayjs from "dayjs";
@@ -104,6 +123,14 @@
label: "鐧昏鏃ユ湡",
prop: "createTime",
width:100
+ },
+ {
+ label: "鎿嶄綔",
+ dataType: "slot",
+ fixed: "right",
+ slot: "operation",
+ width: 100,
+ align: "center",
},
]);
const tableData = ref([]);
@@ -175,6 +202,66 @@
getList();
};
+// 鍒犻櫎
+const handleDelete = (row) => {
+ ElMessageBox.confirm("纭鍒犻櫎璇ヨ褰曞悧锛�", "鎻愮ず", {
+ confirmButtonText: "纭畾",
+ cancelButtonText: "鍙栨秷",
+ type: "warning",
+ })
+ .then(async () => {
+ try {
+ tableLoading.value = true;
+ await receiptPaymentDel([row.id]);
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ getList();
+ } catch (error) {
+ console.error("鍒犻櫎澶辫触:", error);
+ proxy.$modal.msgError("鍒犻櫎澶辫触");
+ } finally {
+ tableLoading.value = false;
+ }
+ })
+ .catch(() => {
+ proxy.$modal.msg("宸插彇娑堝垹闄�");
+ });
+};
+
+// 鎵归噺鍒犻櫎
+const handleBatchDelete = () => {
+ if (selectedRows.value.length === 0) {
+ proxy.$modal.msgWarning("璇烽�夋嫨瑕佸垹闄ょ殑鏁版嵁");
+ return;
+ }
+ ElMessageBox.confirm(
+ `纭畾瑕佸垹闄ら�変腑鐨� ${selectedRows.value.length} 鏉℃暟鎹悧锛焋,
+ "鍒犻櫎鎻愮ず",
+ {
+ confirmButtonText: "纭",
+ cancelButtonText: "鍙栨秷",
+ type: "warning",
+ }
+ )
+ .then(async () => {
+ try {
+ tableLoading.value = true;
+ const ids = selectedRows.value.map((item) => item.id);
+ await receiptPaymentDel(ids);
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ selectedRows.value = [];
+ getList();
+ } catch (error) {
+ console.error("鍒犻櫎澶辫触:", error);
+ proxy.$modal.msgError("鍒犻櫎澶辫触");
+ } finally {
+ tableLoading.value = false;
+ }
+ })
+ .catch(() => {
+ proxy.$modal.msg("宸插彇娑�");
+ });
+};
+
// 瀵煎嚭
const handleExport = () => {
const { receiptPaymentDate, ...rest } = searchForm;
--
Gitblit v1.9.3