From 5df6d6cd93ed5655065652a008189d1630fbfeab Mon Sep 17 00:00:00 2001
From: zhangwencui <1064582902@qq.com>
Date: 星期四, 29 十月 2026 16:34:34 +0800
Subject: [PATCH] change
---
src/views/basicData/customerFile/index.vue | 1072 +++++++++++++++--------------------------------------------
1 files changed, 274 insertions(+), 798 deletions(-)
diff --git a/src/views/basicData/customerFile/index.vue b/src/views/basicData/customerFile/index.vue
index 84153b1..1c4e6e8 100644
--- a/src/views/basicData/customerFile/index.vue
+++ b/src/views/basicData/customerFile/index.vue
@@ -26,17 +26,18 @@
</div>
<div>
<el-button type="primary"
+ v-hasPermi="['basic:customer:add']"
@click="openForm('add')">鏂板瀹㈡埛</el-button>
- <el-button type="primary"
- plain
- @click="back">娴佸叆鍏捣</el-button>
- <el-button @click="handleOut">瀵煎嚭</el-button>
+ <el-button v-hasPermi="['basic:customer:export']"
+ @click="handleOut">瀵煎嚭</el-button>
<el-button type="info"
plain
icon="Upload"
+ v-hasPermi="['basic:customer:import']"
@click="handleImport">瀵煎叆</el-button>
<el-button type="danger"
plain
+ v-hasPermi="['basic:customer:remove']"
@click="handleDelete">鍒犻櫎</el-button>
</div>
</div>
@@ -132,6 +133,23 @@
value="涓夊ぇ娌�" />
<el-option label="澶栭攢"
value="澶栭攢" />
+ </el-select>
+ </el-form-item>
+ </el-col>
+ </el-row>
+ <el-row :gutter="30">
+ <el-col :span="12">
+ <el-form-item label="缁戝畾鐧诲綍璐﹀彿锛�"
+ prop="bindUserId">
+ <el-select v-model="form.bindUserId"
+ placeholder="璇烽�夋嫨璇ュ鎴风殑鐧诲綍璐﹀彿"
+ clearable
+ filterable
+ style="width: 100%">
+ <el-option v-for="item in userList"
+ :key="item.userId"
+ :label="item.nickName + '锛�' + item.userName + '锛�'"
+ :value="item.userId" />
</el-select>
</el-form-item>
</el-col>
@@ -244,127 +262,96 @@
</div>
</template>
</el-dialog>
- <!-- 鍥炶鎻愰啋瀵硅瘽妗� -->
- <el-dialog title="鍥炶鎻愰啋"
- v-model="reminderDialogVisible"
- width="500px"
- @close="closeReminderDialog">
- <el-form :model="reminderForm"
- label-width="100px"
- :rules="reminderRules"
- ref="reminderFormRef">
- <el-form-item label="瀹㈡埛鍚嶇О锛�">
- <el-input v-model="reminderForm.customerName"
- disabled />
+ <!-- 杩�3骞磋储鍔℃姤琛ㄤ笂浼� -->
+ <el-dialog title="杩�3骞磋储鍔℃姤琛ㄤ笂浼�"
+ v-model="reportDialogVisible"
+ width="900px"
+ @close="closeReportDialog">
+ <div class="report-customer">瀹㈡埛锛歿{ reportCustomer.customerName }}</div>
+ <el-form :model="reportForm"
+ label-width="90px"
+ inline
+ class="report-form">
+ <el-form-item label="鎶ヨ〃骞村害">
+ <el-select v-model="reportForm.reportYear"
+ placeholder="璇烽�夋嫨骞村害"
+ style="width: 150px">
+ <el-option v-for="year in reportYears"
+ :key="year"
+ :label="year + '骞�'"
+ :value="year" />
+ </el-select>
</el-form-item>
- <el-form-item label="鎻愰啋寮�鍏筹細">
- <el-switch v-model="reminderForm.reminderSwitch" />
- </el-form-item>
- <el-form-item label="鎻愰啋鍐呭锛�"
- prop="reminderContent">
- <el-input v-model="reminderForm.reminderContent"
- type="textarea"
- :maxlength="100"
- show-word-limit
- placeholder="璇疯緭鍏ユ彁閱掑唴瀹�" />
- </el-form-item>
- <el-form-item label="鎻愰啋鏃堕棿锛�"
- prop="reminderTime">
- <el-date-picker v-model="reminderForm.reminderTime"
- type="datetime"
- value-format="YYYY-MM-DD HH:mm:ss"
- format="YYYY-MM-DD HH:mm:ss"
- placeholder="璇烽�夋嫨鎻愰啋鏃堕棿"
- style="width: 100%" />
+ <el-form-item label="鎶ヨ〃鍚嶇О">
+ <el-input v-model="reportForm.reportName"
+ placeholder="渚嬪锛�2025骞村害璐㈠姟鎶ヨ〃"
+ style="width: 260px"
+ clearable />
</el-form-item>
</el-form>
+ <FileUpload v-model="reportForm.reportFiles"
+ :limit="5"
+ :file-size="20"
+ :file-type="['pdf', 'doc', 'docx', 'xls', 'xlsx', 'jpg', 'png', 'zip', 'rar']" />
+ <div class="report-actions">
+ <el-button type="primary"
+ :loading="reportSaving"
+ @click="saveReport">淇濆瓨涓婁紶</el-button>
+ <el-button @click="resetReportForm">閲嶇疆</el-button>
+ </div>
+ <el-table :data="reportRows"
+ border
+ size="small"
+ style="margin-top: 16px">
+ <el-table-column prop="reportYear"
+ label="骞村害"
+ width="90"
+ align="center" />
+ <el-table-column prop="reportName"
+ label="鎶ヨ〃鍚嶇О"
+ min-width="180"
+ show-overflow-tooltip />
+ <el-table-column label="鎶ヨ〃闄勪欢"
+ min-width="260">
+ <template #default="scope">
+ <FileUpload v-model="scope.row.reportFiles"
+ disabled
+ :is-show-tip="false" />
+ </template>
+ </el-table-column>
+ <el-table-column prop="uploadUserName"
+ label="涓婁紶浜�"
+ width="110" />
+ <el-table-column prop="updateTime"
+ label="涓婁紶鏃堕棿"
+ width="170" />
+ <el-table-column label="瀹℃壒鐘舵��"
+ width="100"
+ align="center">
+ <template #default="scope">
+ <el-tag :type="reportStatusTag(scope.row.auditStatus)">
+ {{ reportStatusText(scope.row.auditStatus) }}
+ </el-tag>
+ </template>
+ </el-table-column>
+ <el-table-column label="鎿嶄綔"
+ width="140"
+ align="center">
+ <template #default="scope">
+ <el-button type="primary"
+ link
+ @click="editReport(scope.row)">淇敼</el-button>
+ <el-button type="danger"
+ link
+ @click="deleteReport(scope.row)">鍒犻櫎</el-button>
+ </template>
+ </el-table-column>
+ </el-table>
+ <div v-if="reportRows.length === 0"
+ class="no-record">鏆傛棤璐㈠姟鎶ヨ〃锛岃鎸夊勾搴︿笂浼犺繎3骞磋储鍔℃姤琛�</div>
<template #footer>
<div class="dialog-footer">
- <el-button type="primary" @click="submitReminderForm">纭</el-button>
- <el-button @click="closeReminderDialog">鍙栨秷</el-button>
- </div>
- </template>
- </el-dialog>
- <!-- 娣诲姞/淇敼娲借皥杩涘害瀵硅瘽妗� -->
- <el-dialog :title="negotiationForm.editIndex !== undefined ? '淇敼杩涘害' : '娣诲姞杩涘害'"
- v-model="negotiationDialogVisible"
- width="600px"
- @close="closeNegotiationDialog">
- <el-form :model="negotiationForm"
- label-width="100px"
- :rules="negotiationRules"
- ref="negotiationFormRef">
- <el-row :gutter="20">
- <el-col :span="12">
- <el-form-item label="璺熻繘鏂瑰紡锛�"
- prop="followUpMethod">
- <el-select v-model="negotiationForm.followUpMethod"
- placeholder="璇烽�夋嫨"
- style="width: 100%">
- <el-option label="鐢佃瘽"
- value="鐢佃瘽" />
- <el-option label="閭欢"
- value="閭欢" />
- <el-option label="涓婇棬"
- value="涓婇棬" />
- <el-option label="寰俊"
- value="寰俊" />
- <el-option label="鍏朵粬"
- value="鍏朵粬" />
- </el-select>
- </el-form-item>
- </el-col>
- <el-col :span="12">
- <el-form-item label="璺熻繘绋嬪害锛�"
- prop="followUpLevel">
- <el-select v-model="negotiationForm.followUpLevel"
- placeholder="璇烽�夋嫨"
- style="width: 100%">
- <el-option label="娼滃湪瀹㈡埛"
- value="娼滃湪瀹㈡埛" />
- <el-option label="鍒濇鎷滆"
- value="鍒濇鎷滆" />
- <el-option label="澶氭鎷滆"
- value="澶氭鎷滆" />
- <el-option label="鎰忓悜瀹㈡埛"
- value="鎰忓悜瀹㈡埛" />
- <el-option label="宸茬绾﹀鎴�"
- value="宸茬绾﹀鎴�" />
- </el-select>
- </el-form-item>
- </el-col>
- </el-row>
- <el-row :gutter="20">
- <el-col :span="12">
- <el-form-item label="璺熻繘鏃堕棿锛�"
- prop="followUpTime">
- <el-date-picker v-model="negotiationForm.followUpTime"
- type="datetime"
- value-format="YYYY-MM-DD HH:mm:ss"
- format="YYYY-MM-DD HH:mm:ss"
- placeholder="璇烽�夋嫨"
- style="width: 100%" />
- </el-form-item>
- </el-col>
- <el-col :span="12">
- <el-form-item label="璺熻繘浜猴細">
- <el-input v-model="negotiationForm.followerUserName"
- disabled />
- </el-form-item>
- </el-col>
- </el-row>
- <el-form-item label="鍐呭锛�"
- prop="content">
- <el-input v-model="negotiationForm.content"
- type="textarea"
- :rows="4"
- placeholder="璇疯緭鍏�" />
- </el-form-item>
- </el-form>
- <template #footer>
- <div class="dialog-footer">
- <el-button type="primary" @click="submitNegotiationForm">纭</el-button>
- <el-button @click="closeNegotiationDialog">鍙栨秷</el-button>
+ <el-button @click="closeReportDialog">鍏抽棴</el-button>
</div>
</template>
</el-dialog>
@@ -373,7 +360,6 @@
v-model="detailDialogVisible"
width="1000px"
@close="closeDetailDialog">
- <!-- 瀹㈡埛鍩烘湰淇℃伅 -->
<div class="detail-section">
<h3 class="section-title">瀹㈡埛鍩烘湰淇℃伅</h3>
<div class="info-display">
@@ -450,10 +436,18 @@
<el-row :gutter="20">
<el-col :span="12">
<div class="info-item">
+ <span class="info-label">缁戝畾鐧诲綍璐﹀彿锛�</span>
+ <span class="info-value">{{ detailForm.bindUserName || '-' }}</span>
+ </div>
+ </el-col>
+ <el-col :span="12">
+ <div class="info-item">
<span class="info-label">缁存姢浜猴細</span>
<span class="info-value">{{ detailForm.maintainer }}</span>
</div>
</el-col>
+ </el-row>
+ <el-row :gutter="20">
<el-col :span="12">
<div class="info-item">
<span class="info-label">缁存姢鏃堕棿锛�</span>
@@ -463,149 +457,41 @@
</el-row>
</div>
</div>
- <!-- 娲借皥杩涘害璁板綍 -->
<div class="detail-section">
- <div class="section-header">
- <h3 class="section-title">娲借皥杩涘害璁板綍</h3>
- <el-button type="primary"
- size="small"
- @click="openNegotiationDialog(detailForm)">
- 娣诲姞杩涘害
- </el-button>
- </div>
- <el-table :data="negotiationRecords"
+ <h3 class="section-title">杩�3骞磋储鍔℃姤琛�</h3>
+ <el-table :data="detailReports"
border
+ size="small"
style="width: 100%">
- <el-table-column prop="followUpTime"
- label="璺熻繘鏃堕棿"
- width="160" />
- <el-table-column prop="followUpMethod"
- label="璺熻繘鏂瑰紡"
- width="100" />
- <el-table-column prop="followUpLevel"
- label="璺熻繘绋嬪害" />
- <el-table-column prop="followerUserName"
- label="璺熻繘浜�"
- width="100" />
- <el-table-column prop="content"
- label="鍐呭"
+ <el-table-column prop="reportYear"
+ label="骞村害"
+ width="90"
+ align="center" />
+ <el-table-column prop="reportName"
+ label="鎶ヨ〃鍚嶇О"
+ min-width="180"
show-overflow-tooltip />
- <el-table-column label="闄勪欢"
- width="100"
- align="center">
- <template #default="{ row }">
- <el-button type="info"
- link
- @click="openAttachmentDialog(row)">
- <el-icon>
- <Paperclip />
- </el-icon>
- 闄勪欢
- <!-- {{ row.fileList && row.fileList.length > 0 ? row.fileList.length : '涓婁紶' }} -->
- </el-button>
+ <el-table-column label="鎶ヨ〃闄勪欢"
+ min-width="260">
+ <template #default="scope">
+ <FileUpload v-model="scope.row.reportFiles"
+ disabled
+ :is-show-tip="false" />
</template>
</el-table-column>
- <el-table-column label="鎿嶄綔"
- width="150"
- align="center">
- <template #default="{ row, $index }">
- <el-button type="primary"
- link
- @click="editNegotiationRecord(row, $index)">
- 淇敼
- </el-button>
- <el-button type="danger"
- link
- @click="deleteNegotiationRecord(row, $index)">
- 鍒犻櫎
- </el-button>
- </template>
- </el-table-column>
+ <el-table-column prop="uploadUserName"
+ label="涓婁紶浜�"
+ width="110" />
+ <el-table-column prop="updateTime"
+ label="涓婁紶鏃堕棿"
+ width="170" />
</el-table>
- <div v-if="negotiationRecords.length === 0"
- class="no-records">
- 鏆傛棤娲借皥杩涘害璁板綍
- </div>
+ <div v-if="detailReports.length === 0"
+ class="no-record">鏆傛棤璐㈠姟鎶ヨ〃</div>
</div>
<template #footer>
<div class="dialog-footer">
<el-button @click="closeDetailDialog">鍏抽棴</el-button>
- </div>
- </template>
- </el-dialog>
- <!-- 闄勪欢涓婁紶寮圭獥 -->
- <el-dialog title="闄勪欢绠$悊"
- v-model="attachmentDialogVisible"
- width="600px"
- @close="closeAttachmentDialog">
- <div class="attachment-section">
- <div class="upload-area">
- <el-upload ref="attachmentUploadRef"
- :action="getAttachmentUploadUrl()"
- :headers="attachmentUploadHeaders"
- :file-list="currentAttachmentList"
- :on-success="handleAttachmentSuccess"
- :on-error="handleAttachmentError"
- :on-remove="handleAttachmentRemove"
- :before-upload="beforeAttachmentUpload"
- multiple
- :limit="10"
- name="files">
- <el-button type="primary">
- <el-icon>
- <Upload />
- </el-icon>
- 涓婁紶闄勪欢
- </el-button>
- <template #tip>
- <div class="el-upload__tip">
- 鏀寔涓婁紶鍥剧墖銆佹枃妗g瓑鏂囦欢锛屽崟涓枃浠朵笉瓒呰繃50MB
- </div>
- </template>
- </el-upload>
- </div>
- <div v-if="currentAttachmentList.length > 0"
- class="attachment-list">
- <h4>宸蹭笂浼犻檮浠讹細</h4>
- <el-table :data="currentAttachmentList"
- border
- size="small">
- <el-table-column prop="name"
- label="鏂囦欢鍚�"
- show-overflow-tooltip />
- <el-table-column prop="size"
- label="澶у皬"
- width="100">
- <template #default="{ row }">
- {{ formatFileSize(row.size) }}
- </template>
- </el-table-column>
- <el-table-column label="鎿嶄綔"
- width="120"
- align="center">
- <template #default="{ row, $index }">
- <el-button type="primary"
- link
- @click="downloadAttachment(row)">
- 涓嬭浇
- </el-button>
- <el-button type="danger"
- link
- @click="deleteAttachment(row, $index)">
- 鍒犻櫎
- </el-button>
- </template>
- </el-table-column>
- </el-table>
- </div>
- <div v-else
- class="no-attachment">
- 鏆傛棤闄勪欢
- </div>
- </div>
- <template #footer>
- <div class="dialog-footer">
- <el-button @click="closeAttachmentDialog">鍏抽棴</el-button>
</div>
</template>
</el-dialog>
@@ -614,68 +500,24 @@
<script setup>
import { onMounted, ref, reactive, getCurrentInstance, toRefs } from "vue";
- import { Search, Paperclip, Upload } from "@element-plus/icons-vue";
+ import { Search, Close } from "@element-plus/icons-vue";
+ import { listCustomer, getCustomer, addCustomer, updateCustomer, delCustomer } from "@/api/basicData/customer.js";
import {
- addCustomerFollow,
- updateCustomerFollow,
- delCustomerFollow,
- addReturnVisit,
- getReturnVisit,
- } from "@/api/basicData/customerFile.js";
- import {listCustomer, getCustomer, addCustomer, updateCustomer, delCustomer, backCustomer} from "@/api/basicData/customer.js";
+ listCustomerFinancialReport,
+ saveCustomerFinancialReport,
+ delCustomerFinancialReport,
+ } from "@/api/basicData/customerFinancialReport.js";
import { ElMessageBox } from "element-plus";
import { userListNoPage } from "@/api/system/user.js";
import useUserStore from "@/store/modules/user";
import { getToken } from "@/utils/auth.js";
+ import FileUpload from "@/components/FileUpload/index.vue";
const { proxy } = getCurrentInstance();
const userStore = useUserStore();
- // 鍥炶鎻愰啋鐩稿叧
- const reminderDialogVisible = ref(false);
- const reminderFormRef = ref();
- const currentCustomerId = ref();
- const reminderForm = reactive({
- customerName: "",
- reminderSwitch: false,
- reminderContent: "",
- reminderTime: "",
- });
- const reminderRules = {
- reminderContent: [
- { required: true, message: "璇疯緭鍏ユ彁閱掑唴瀹�", trigger: "blur" },
- ],
- reminderTime: [
- { required: true, message: "璇烽�夋嫨鎻愰啋鏃堕棿", trigger: "change" },
- ],
- };
-
- // 娲借皥杩涘害鐩稿叧
- const negotiationDialogVisible = ref(false);
- const negotiationFormRef = ref();
- const negotiationForm = reactive({
- customerName: "",
- customerId: "",
- followUpMethod: "",
- followUpLevel: "",
- followUpTime: "",
- followerUserName: "",
- content: "",
- });
- const negotiationRules = {
- followUpMethod: [
- { required: true, message: "璇烽�夋嫨璺熻繘鏂瑰紡", trigger: "change" },
- ],
- followUpLevel: [
- { required: true, message: "璇烽�夋嫨璺熻繘绋嬪害", trigger: "change" },
- ],
- followUpTime: [
- { required: true, message: "璇烽�夋嫨璺熻繘鏃堕棿", trigger: "change" },
- ],
- content: [{ required: true, message: "璇疯緭鍏ュ唴瀹�", trigger: "blur" }],
- };
-
// 璇︽儏鐩稿叧
const detailDialogVisible = ref(false);
+ const detailReports = ref([]);
const detailForm = reactive({
customerName: "",
customerType: "",
@@ -687,26 +529,20 @@
bankCode: "",
contactPerson: "",
contactPhone: "",
+ bindUserId: "",
+ bindUserName: "",
maintainer: "",
maintenanceTime: "",
});
- const negotiationRecords = ref([]);
- // 闄勪欢鐩稿叧
- const attachmentDialogVisible = ref(false);
- const attachmentUploadRef = ref();
- const currentAttachmentList = ref([]);
- const currentFollowRecord = ref({});
- const attachmentUploadHeaders = { Authorization: "Bearer " + getToken() };
-
- // 鍔ㄦ�佹瀯寤轰笂浼燯RL
- const getAttachmentUploadUrl = () => {
- const baseUrl =
- import.meta.env.VITE_APP_BASE_API + "/basic/customer-follow/upload";
- return currentFollowRecord.value.id
- ? `${baseUrl}/${currentFollowRecord.value.id}`
- : baseUrl;
- };
+ // 杩�3骞磋储鍔℃姤琛ㄧ浉鍏�
+ const reportDialogVisible = ref(false);
+ const reportSaving = ref(false);
+ const reportCustomer = reactive({ id: "", customerName: "" });
+ const reportRows = ref([]);
+ const nowYear = new Date().getFullYear();
+ const reportYears = [nowYear, nowYear - 1, nowYear - 2];
+ const reportForm = reactive({ reportYear: nowYear, reportName: "", reportFiles: "" });
const tableColumn = ref([
{
@@ -726,7 +562,7 @@
},
{
label: "鍦板潃鍙婅仈绯绘柟寮�",
- prop: "companyAddress",
+ prop: "addressPhone",
width: 250,
},
{
@@ -739,97 +575,36 @@
width: 150,
},
{
- label: "璺熻繘杩涘害",
- prop: "followUpLevel",
- width: 120,
- },
- {
- label: "璺熻繘鏃堕棿",
- prop: "followUpTime",
- width: 120,
- },
- {
- label: "閾惰鍩烘湰鎴�",
- prop: "basicBankAccount",
- width: 220,
- },
- {
- label: "閾惰璐﹀彿",
- prop: "bankAccount",
- width: 220,
- },
- {
- label: "寮�鎴疯鍙�",
- prop: "bankCode",
- width: 220,
- },
- {
- label: "缁存姢浜�",
- prop: "maintainer",
- },
- {
- label: "瀹㈡埛鏉ユ簮",
- prop: "type",
- dataType: "tag",
- width: 100,
- formatData: value => {
- if (value === 1 || value === "1") {
- return "鍏捣";
- }
- return "绉佹捣";
- },
- formatType: value => {
- if (value === 1 || value === "1") {
- return "warning";
- }
- return "success";
- },
- },
- {
- label: "缁存姢鏃堕棿",
- prop: "maintenanceTime",
- width: 100,
- },
- {
dataType: "action",
label: "鎿嶄綔",
align: "center",
fixed: "right",
- width: 290,
+ width: 240,
operation: [
{
name: "缂栬緫",
type: "text",
- showHide: row => !isCustomerEditLocked(row),
+ showHide: () => proxy.$auth.hasPermi("basic:customer:edit"),
clickFun: row => {
- if (isCustomerEditLocked(row)) {
- proxy.$modal.msgWarning("宸茶閿�鍞ā鍧楀紩鐢ㄧ殑绉佹捣瀹㈡埛涓嶈兘缂栬緫");
- return;
- }
openForm("edit", row);
},
},
- {
- name: "娣诲姞娲借皥杩涘害",
- type: "text",
- clickFun: row => {
- openNegotiationDialog(row);
- },
- },
{
- name: "鍥炶鎻愰啋",
+ name: "杩�3骞磋储鍔℃姤琛�",
type: "text",
+ showHide: () => proxy.$auth.hasPermi("basic:customer:report"),
clickFun: row => {
- openReminderDialog(row);
+ openReportDialog(row);
},
},
- {
- name: "璇︽儏",
- type: "text",
- clickFun: row => {
- openDetailDialog(row);
- },
- },
+ {
+ name: "璇︽儏",
+ type: "text",
+ showHide: () => proxy.$auth.hasPermi("basic:customer:query"),
+ clickFun: row => {
+ openDetailDialog(row);
+ },
+ },
],
},
]);
@@ -842,13 +617,11 @@
size: 100,
total: 0,
});
- const total = ref(0);
// 鐢ㄦ埛淇℃伅琛ㄥ崟寮规鏁版嵁
const operationType = ref("");
const dialogFormVisible = ref(false);
const formYYs = ref({
- // 鍏朵粬瀛楁...
contactList: [
{
contactPerson: "",
@@ -869,6 +642,7 @@
companyPhone: "",
contactPerson: "",
contactPhone: "",
+ bindUserId: "",
maintainer: "",
maintenanceTime: "",
basicBankAccount: "",
@@ -884,8 +658,6 @@
],
companyAddress: [{ required: true, message: "璇疯緭鍏�", trigger: "blur" }],
companyPhone: [{ required: true, message: "璇疯緭鍏�", trigger: "blur" }],
- // contactPerson: [{ required: true, message: "璇疯緭鍏�", trigger: "blur" }],
- // contactPhone: [{ required: true, message: "璇疯緭鍏�", trigger: "blur" }],
maintainer: [{ required: false, message: "璇烽�夋嫨", trigger: "change" }],
maintenanceTime: [
{ required: false, message: "璇烽�夋嫨", trigger: "change" },
@@ -912,7 +684,6 @@
},
// 鏂囦欢涓婁紶鍓嶇殑鍥炶皟
beforeUpload: file => {
- console.log("鏂囦欢鍗冲皢涓婁紶", file);
// 鍙互鍦ㄦ澶勫仛鏂囦欢绫诲瀷鎴栧ぇ灏忔牎楠�
const isValid =
file.type ===
@@ -930,7 +701,6 @@
},
// 鏂囦欢涓婁紶鎴愬姛鏃剁殑鍥炶皟
onSuccess: (response, file, fileList) => {
- console.log("涓婁紶鎴愬姛", response, file, fileList);
upload.isUploading = false;
if (response.code === 200) {
proxy.$modal.msgSuccess("鏂囦欢涓婁紶鎴愬姛");
@@ -945,12 +715,11 @@
},
// 鏂囦欢涓婁紶澶辫触鏃剁殑鍥炶皟
onError: (error, file, fileList) => {
- console.error("涓婁紶澶辫触", error, file, fileList);
upload.isUploading = false;
proxy.$modal.msgError("鏂囦欢涓婁紶澶辫触");
},
// 鏂囦欢涓婁紶杩涘害鍥炶皟
- onProgress: (event, file, fileList) => {
+ onProgress: event => {
console.log("涓婁紶涓�...", event.percent);
},
});
@@ -984,6 +753,8 @@
tableLoading.value = false;
tableData.value = res.data.records;
page.total = res.data.total;
+ }).catch(() => {
+ tableLoading.value = false;
});
};
// 琛ㄦ牸閫夋嫨鏁版嵁
@@ -1006,10 +777,6 @@
}
// 鎵撳紑寮规
const openForm = (type, row) => {
- if (type === "edit" && isCustomerEditLocked(row)) {
- proxy.$modal.msgWarning("宸茶閿�鍞ā鍧楀紩鐢ㄧ殑绉佹捣瀹㈡埛涓嶈兘缂栬緫");
- return;
- }
operationType.value = type;
form.value = {};
form.value.maintainer = userStore.nickName;
@@ -1027,23 +794,21 @@
if (type === "edit") {
getCustomer(row.id).then(res => {
form.value = { ...res.data };
- formYYs.value.contactList = res.data.contactPerson
+ formYYs.value.contactList = (res.data.contactPerson || "")
.split(",")
+ .filter(item => item)
.map((item, index) => {
return {
contactPerson: item,
- contactPhone: res.data.contactPhone.split(",")[index],
+ contactPhone: (res.data.contactPhone || "").split(",")[index],
};
});
+ if (formYYs.value.contactList.length === 0) {
+ formYYs.value.contactList = [{ contactPerson: "", contactPhone: "" }];
+ }
});
}
dialogFormVisible.value = true;
- };
- const isCustomerEditLocked = row => {
- const salesReferenced = Number(row?.salesReferenceFlag || 0) === 1;
- const customerType = Number(row?.type);
- const usageStatus = Number(row?.usageStatus || 0);
- return salesReferenced && (customerType === 0 || (customerType === 1 && usageStatus === 1));
};
// 鎻愪氦琛ㄥ崟
const submitForm = () => {
@@ -1068,7 +833,7 @@
form.value.contactPhone = formYYs.value.contactList
.map(item => item.contactPhone)
.join(",");
- addCustomer(form.value).then(res => {
+ addCustomer(form.value).then(() => {
proxy.$modal.msgSuccess("鎻愪氦鎴愬姛");
closeDia();
getList();
@@ -1082,7 +847,7 @@
form.value.contactPhone = formYYs.value.contactList
.map(item => item.contactPhone)
.join(",");
- updateCustomer(form.value).then(res => {
+ updateCustomer(form.value).then(() => {
proxy.$modal.msgSuccess("鎻愪氦鎴愬姛");
closeDia();
getList();
@@ -1101,7 +866,7 @@
type: "warning",
})
.then(() => {
- proxy.download("/basic/customer/export", {type: 0}, "瀹㈡埛妗f.xlsx");
+ proxy.download("/basic/customer/export", { type: 0 }, "瀹㈡埛妗f.xlsx");
})
.catch(() => {
proxy.$modal.msg("宸插彇娑�");
@@ -1144,182 +909,98 @@
});
};
- const back = () => {
- if (selectedRows.value.length === 0) {
- proxy.$modal.msgWarning("璇烽�夋嫨鏁版嵁");
+ // 鎵撳紑杩�3骞磋储鍔℃姤琛ㄥ脊绐�
+ const openReportDialog = row => {
+ reportCustomer.id = row.id;
+ reportCustomer.customerName = row.customerName;
+ resetReportForm();
+ loadReports(row.id);
+ reportDialogVisible.value = true;
+ };
+
+ const loadReports = customerId => {
+ listCustomerFinancialReport({ customerId }).then(res => {
+ reportRows.value = res.data || [];
+ });
+ };
+
+ const reportStatusText = status => {
+ if (status === 1) return "宸查�氳繃";
+ if (status === 2) return "宸查��鍥�";
+ return "寰呭鎵�";
+ };
+ const reportStatusTag = status => {
+ if (status === 1) return "success";
+ if (status === 2) return "danger";
+ return "warning";
+ };
+
+ const resetReportForm = () => {
+ reportForm.reportYear = nowYear;
+ reportForm.reportName = "";
+ reportForm.reportFiles = "";
+ };
+
+ const editReport = row => {
+ reportForm.reportYear = row.reportYear;
+ reportForm.reportName = row.reportName;
+ reportForm.reportFiles = row.reportFiles;
+ };
+
+ const saveReport = () => {
+ if (!reportForm.reportFiles) {
+ proxy.$modal.msgWarning("璇蜂笂浼犺储鍔℃姤琛ㄩ檮浠�");
return;
}
- const ids = selectedRows.value.map(item => item.id);
- ElMessageBox.confirm("閫変腑鐨勫鎴峰皢娴佸叆鍏捣锛屾槸鍚︾‘璁わ紵", "娴佸叆鍏捣鎻愮ず", {
+ reportSaving.value = true;
+ saveCustomerFinancialReport({
+ customerId: reportCustomer.id,
+ reportYear: reportForm.reportYear,
+ reportName: reportForm.reportName,
+ reportFiles: reportForm.reportFiles,
+ }).then(() => {
+ proxy.$modal.msgSuccess("淇濆瓨鎴愬姛");
+ resetReportForm();
+ loadReports(reportCustomer.id);
+ }).finally(() => {
+ reportSaving.value = false;
+ });
+ };
+
+ const deleteReport = row => {
+ ElMessageBox.confirm("纭畾瑕佸垹闄よ骞村害璐㈠姟鎶ヨ〃鍚楋紵", "鍒犻櫎鎻愮ず", {
confirmButtonText: "纭",
cancelButtonText: "鍙栨秷",
type: "warning",
})
.then(() => {
- tableLoading.value = true;
- return Promise.all(ids.map(id => backCustomer(id)))
- .then(() => {
- proxy.$modal.msgSuccess("娴佸叆鍏捣鎴愬姛");
- selectedRows.value = [];
- getList();
- })
- .finally(() => {
- tableLoading.value = false;
- });
+ delCustomerFinancialReport(row.id).then(() => {
+ proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
+ loadReports(reportCustomer.id);
+ });
})
- .catch(error => {
- if (error === "cancel" || error === "close") {
- proxy.$modal.msg("宸插彇娑�");
- }
+ .catch(() => {
+ proxy.$modal.msg("宸插彇娑�");
});
};
- // 鎵撳紑鍥炶鎻愰啋寮圭獥
- const openReminderDialog = row => {
- currentCustomerId.value = row.id;
- reminderForm.customerName = row.customerName;
- reminderForm.reminderSwitch = false;
- reminderForm.reminderContent = "";
- reminderForm.reminderTime = "";
-
- // 灏濊瘯鑾峰彇宸叉湁鐨勫洖璁挎彁閱�
- getReturnVisit(row.id)
- .then(res => {
- if (res.code === 200 && res.data) {
- reminderForm.reminderSwitch = res.data.isEnabled === 1;
- reminderForm.reminderContent = res.data.content;
- reminderForm.reminderTime = res.data.reminderTime;
- reminderForm.id = res.data.id;
- }
- })
- .catch(error => {
- console.error("鑾峰彇鍥炶鎻愰啋澶辫触:", error);
- });
-
- reminderDialogVisible.value = true;
- };
-
- // 鍏抽棴鍥炶鎻愰啋寮圭獥
- const closeReminderDialog = () => {
- proxy.resetForm("reminderFormRef");
- reminderDialogVisible.value = false;
- };
- const submitvalue = ref({});
-
- // 鎻愪氦鍥炶鎻愰啋
- const submitReminderForm = () => {
- console.log("鎻愪氦鍥炶鎻愰啋鏁版嵁:", userStore.id, userStore);
- proxy.$refs.reminderFormRef.validate(valid => {
- if (valid) {
- if (reminderForm.id) {
- submitvalue.value = {
- id: reminderForm.id,
- customerId: currentCustomerId.value,
- isEnabled: reminderForm.reminderSwitch ? 1 : 0,
- content: reminderForm.reminderContent,
- reminderTime: reminderForm.reminderTime,
- remindUserId: userStore.id,
- };
- } else {
- submitvalue.value = {
- customerId: currentCustomerId.value,
- isEnabled: reminderForm.reminderSwitch ? 1 : 0,
- content: reminderForm.reminderContent,
- reminderTime: reminderForm.reminderTime,
- remindUserId: userStore.id,
- };
- }
-
- // 璋冪敤鎺ュ彛
- addReturnVisit(submitvalue.value)
- .then(res => {
- if (res.code === 200) {
- proxy.$modal.msgSuccess("鍥炶鎻愰啋璁剧疆鎴愬姛");
- closeReminderDialog();
- } else {
- proxy.$modal.msgError(res.msg || "璁剧疆澶辫触");
- }
- })
- .catch(error => {
- console.error("璁剧疆鍥炶鎻愰啋澶辫触:", error);
- proxy.$modal.msgError("璁剧疆澶辫触");
- });
- }
- });
- };
-
- // 鎵撳紑娲借皥杩涘害寮圭獥
- const openNegotiationDialog = row => {
- negotiationForm.customerName = row.customerName;
- negotiationForm.customerId = row.id;
- negotiationForm.followUpMethod = "";
- negotiationForm.followUpLevel = "";
- negotiationForm.followUpTime = "";
- negotiationForm.followerUserName = userStore.nickName; // 榛樿褰撳墠鐧诲綍浜�
- negotiationForm.content = "";
- negotiationDialogVisible.value = true;
- };
-
- // 鍏抽棴娲借皥杩涘害寮圭獥
- const closeNegotiationDialog = () => {
- proxy.resetForm("negotiationFormRef");
- // 娓呴櫎缂栬緫鐘舵��
- delete negotiationForm.editIndex;
- delete negotiationForm.id;
- negotiationDialogVisible.value = false;
- };
-
- // 鎻愪氦娲借皥杩涘害
- const submitNegotiationForm = () => {
- proxy.$refs.negotiationFormRef.validate(valid => {
- if (valid) {
- // 鍒ゆ柇鏄柊澧炶繕鏄慨鏀�
- const isEdit = negotiationForm.editIndex !== undefined;
-
- if (isEdit) {
- // 淇敼鎿嶄綔
- updateCustomerFollow(negotiationForm).then(res => {
- // 鏇存柊鏈湴鏁版嵁
- getCustomer(negotiationForm.customerId).then(res => {
- // 鏇存柊鏈湴鏁版嵁
- negotiationRecords.value = res.data.followUpList || [];
- });
- });
- proxy.$modal.msgSuccess("淇敼鎴愬姛");
- closeNegotiationDialog();
- } else {
- // 鏂板鎿嶄綔
- console.log("鎻愪氦娲借皥杩涘害鏁版嵁:", negotiationForm);
- addCustomerFollow(negotiationForm).then(res => {
- // 娣诲姞鎴愬姛鍚庢洿鏂拌鎯呴〉闈㈢殑杩涘害璁板綍
- const newRecord = {
- followUpTime: negotiationForm.followUpTime,
- followUpMethod: negotiationForm.followUpMethod,
- followUpLevel: negotiationForm.followUpLevel,
- followerUserName: negotiationForm.followerUserName,
- content: negotiationForm.content,
- };
- negotiationRecords.value.unshift(newRecord);
-
- proxy.$modal.msgSuccess("鎻愪氦鎴愬姛");
- closeNegotiationDialog();
- getList();
- });
- }
- }
- });
+ const closeReportDialog = () => {
+ reportDialogVisible.value = false;
+ reportRows.value = [];
+ resetReportForm();
};
// 鎵撳紑璇︽儏寮圭獥
const openDetailDialog = row => {
getCustomer(row.id).then(res => {
- // 濉厖瀹㈡埛鍩烘湰淇℃伅
Object.assign(detailForm, res.data);
-
- // 鑾峰彇娲借皥杩涘害璁板綍
- negotiationRecords.value = res.data.followUpList || [];
-
+ const bindUser = userList.value.find(item => item.userId === res.data.bindUserId);
+ detailForm.bindUserName = bindUser ? bindUser.nickName : "";
+ detailReports.value = [];
detailDialogVisible.value = true;
+ listCustomerFinancialReport({ customerId: row.id }).then(reportRes => {
+ detailReports.value = reportRes.data || [];
+ });
});
};
@@ -1328,201 +1009,19 @@
detailDialogVisible.value = false;
};
- // 淇敼娲借皥璁板綍
- const editNegotiationRecord = (row, index) => {
- // 灏嗗綋鍓嶈褰曟暟鎹~鍏呭埌琛ㄥ崟
- Object.assign(negotiationForm, {
- customerName: row.customerName,
- customerId: row.customerId,
- followUpMethod: row.followUpMethod,
- followUpLevel: row.followUpLevel,
- followUpTime: row.followUpTime,
- followerUserName: row.followerUserName,
- content: row.content,
- id: row.id, // 璁板綍ID鐢ㄤ簬鏇存柊
- editIndex: index, // 璁板綍绱㈠紩鐢ㄤ簬鏈湴鏇存柊
- });
- negotiationDialogVisible.value = true;
- };
-
- // 鍒犻櫎娲借皥璁板綍
- const deleteNegotiationRecord = (row, index) => {
- ElMessageBox.confirm("纭畾瑕佸垹闄よ繖鏉℃唇璋堣褰曞悧锛�", "鍒犻櫎鎻愮ず", {
- confirmButtonText: "纭畾",
- cancelButtonText: "鍙栨秷",
- type: "warning",
- })
- .then(() => {
- // 杩欓噷鍙互璋冪敤鍒犻櫎鎺ュ彛
- // 瀹為檯椤圭洰涓渶瑕佹牴鎹悗绔帴鍙h繘琛岃皟鏁�
- // 绀轰緥锛歞eleteCustomerFollow(row.id).then(() => {
- // negotiationRecords.value.splice(index, 1);
- // proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
- // });
- delCustomerFollow(row.id).then(() => {
- // 鍒犻櫎鎴愬姛鍚庢洿鏂版湰鍦版暟鎹�
- getCustomer(row.customerId).then(res => {
- // 鏇存柊鏈湴鏁版嵁
- negotiationRecords.value = res.data.followUpList || [];
- });
- proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
- });
- // 鏈湴鍒犻櫎锛堟ā鎷燂級
- negotiationRecords.value.splice(index, 1);
- proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
- })
- .catch(() => {
- proxy.$modal.msg("宸插彇娑堝垹闄�");
- });
- };
-
- // 鎵撳紑闄勪欢寮圭獥
- const openAttachmentDialog = row => {
- currentFollowRecord.value = row;
- // 杞崲涓虹鍚圗lement Plus fileList鏍煎紡鐨勬暟缁�
- currentAttachmentList.value = (row.fileList || []).map((file, index) => ({
- name: file.fileName,
- url: file.fileUrl,
- size: file.fileSize,
- id: file.id,
- uid: file.id || index,
- status: "success",
- }));
-
- attachmentDialogVisible.value = true;
- };
-
- // 鍏抽棴闄勪欢寮圭獥
- const closeAttachmentDialog = () => {
- attachmentDialogVisible.value = false;
- currentFollowRecord.value = {};
- currentAttachmentList.value = [];
- };
-
- // 闄勪欢涓婁紶鎴愬姛
- const handleAttachmentSuccess = (response, file, fileList) => {
- if (response.code === 200) {
- proxy.$modal.msgSuccess("涓婁紶鎴愬姛");
- // 鏇存柊褰撳墠璁板綍鐨勯檮浠跺垪琛�
- currentAttachmentList.value = fileList.map(item => ({
- name: item.name,
- size: item.size,
- url: item.response?.data?.url || item.url,
- id: item.response?.data?.id,
- uid: item.uid,
- status: "success",
- }));
- // 鏇存柊鍘熻褰曚腑鐨刦iles瀛楁
- if (currentFollowRecord.value) {
- currentFollowRecord.value.files = [...currentAttachmentList.value];
- }
- } else {
- proxy.$modal.msgError(response.msg || "涓婁紶澶辫触");
- }
- };
-
- // 闄勪欢涓婁紶澶辫触
- const handleAttachmentError = (error, file, fileList) => {
- console.error("涓婁紶澶辫触:", error);
- proxy.$modal.msgError("涓婁紶澶辫触");
- };
-
- // 闄勪欢绉婚櫎
- const handleAttachmentRemove = (file, fileList) => {
- currentAttachmentList.value = fileList;
- // 鏇存柊鍘熻褰曚腑鐨刦iles瀛楁
- if (currentFollowRecord.value) {
- currentFollowRecord.value.files = [...fileList];
- }
- };
-
- // 闄勪欢涓婁紶鍓嶆牎楠�
- const beforeAttachmentUpload = file => {
- const maxSize = 50 * 1024 * 1024; // 50MB
- if (file.size > maxSize) {
- proxy.$modal.msgError("鏂囦欢澶у皬涓嶈兘瓒呰繃50MB");
- return false;
- }
- return true;
- };
-
- // 鏍煎紡鍖栨枃浠跺ぇ灏�
- const formatFileSize = size => {
- if (size < 1024) {
- return size + " B";
- } else if (size < 1024 * 1024) {
- return (size / 1024).toFixed(2) + " KB";
- } else {
- return (size / (1024 * 1024)).toFixed(2) + " MB";
- }
- };
-
- // 涓嬭浇闄勪欢
- const downloadAttachment = row => {
- if (row.url) {
- // proxy.download(row.url, {}, row.name);
- proxy.$download.byUrl(row.url, row.originalFilename);
- } else {
- proxy.$modal.msgError("涓嬭浇閾炬帴涓嶅瓨鍦�");
- }
- };
-
- // 鍒犻櫎闄勪欢
- const deleteAttachment = (row, index) => {
- ElMessageBox.confirm("纭畾瑕佸垹闄よ繖涓檮浠跺悧锛�", "鍒犻櫎鎻愮ず", {
- confirmButtonText: "纭畾",
- cancelButtonText: "鍙栨秷",
- type: "warning",
- })
- .then(() => {
- // 璋冪敤鍚庣鎺ュ彛鍒犻櫎闄勪欢
- const deleteUrl =
- import.meta.env.VITE_APP_BASE_API +
- "/basic/customer-follow/file/" +
- row.id;
- fetch(deleteUrl, {
- method: "DELETE",
- headers: {
- Authorization: "Bearer " + getToken(),
- "Content-Type": "application/json",
- },
- })
- .then(response => response.json())
- .then(res => {
- if (res.code === 200) {
- // 鍒犻櫎鎴愬姛鍚庢洿鏂版湰鍦版枃浠跺垪琛�
- currentAttachmentList.value.splice(index, 1);
- // 鏇存柊鍘熻褰曚腑鐨刦iles瀛楁
- if (currentFollowRecord.value) {
- currentFollowRecord.value.files = [
- ...currentAttachmentList.value,
- ];
- }
- proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
- } else {
- proxy.$modal.msgError(res.msg || "鍒犻櫎澶辫触");
- }
- })
- .catch(error => {
- console.error("鍒犻櫎闄勪欢澶辫触:", error);
- proxy.$modal.msgError("鍒犻櫎澶辫触");
- });
- })
- .catch(() => {
- proxy.$modal.msg("宸插彇娑堝垹闄�");
- });
- };
-
// 鑾峰彇褰撳墠鏃ユ湡骞舵牸寮忓寲涓� YYYY-MM-DD
function getCurrentDate() {
const today = new Date();
const year = today.getFullYear();
- const month = String(today.getMonth() + 1).padStart(2, "0"); // 鏈堜唤浠�0寮�濮�
+ const month = String(today.getMonth() + 1).padStart(2, "0");
const day = String(today.getDate()).padStart(2, "0");
return `${year}-${month}-${day}`;
}
onMounted(() => {
+ userListNoPage().then(res => {
+ userList.value = res.data;
+ });
getList();
});
</script>
@@ -1533,13 +1032,6 @@
padding: 15px;
background-color: #f9f9f9;
border-radius: 4px;
- }
-
- .section-header {
- display: flex;
- justify-content: space-between;
- align-items: center;
- margin-bottom: 15px;
}
.section-title {
@@ -1574,40 +1066,24 @@
word-break: break-word;
}
- .no-records {
+ .no-record {
text-align: center;
- padding: 30px;
+ padding: 20px;
color: #999;
font-size: 14px;
}
- .attachment-section {
- .upload-area {
- margin-bottom: 20px;
- padding: 20px;
- background-color: #f9f9f9;
- border-radius: 4px;
- border: 1px dashed #d9d9d9;
+ .report-customer {
+ font-size: 14px;
+ color: #606266;
+ margin-bottom: 12px;
+ }
- .el-upload__tip {
- margin-top: 10px;
- color: #909399;
- }
- }
+ .report-form {
+ margin-bottom: 4px;
+ }
- .attachment-list {
- h4 {
- margin: 0 0 10px 0;
- font-size: 14px;
- color: #606266;
- }
- }
-
- .no-attachment {
- text-align: center;
- padding: 40px;
- color: #909399;
- font-size: 14px;
- }
+ .report-actions {
+ margin-top: 10px;
}
</style>
--
Gitblit v1.9.3