From 55690b8a91083f81158b1619bafe6f248f93265f Mon Sep 17 00:00:00 2001
From: gongchunyi <deslre0381@gmail.com>
Date: 星期四, 05 三月 2026 16:22:39 +0800
Subject: [PATCH] fix: 批量删除危险物料管控记录时却只能删除一个

---
 src/views/customerService/afterSalesHandling/index.vue |  487 +++++++++++++++++++++++++++++++++++++++++------------
 1 files changed, 376 insertions(+), 111 deletions(-)

diff --git a/src/views/customerService/afterSalesHandling/index.vue b/src/views/customerService/afterSalesHandling/index.vue
index 4994365..d95e327 100644
--- a/src/views/customerService/afterSalesHandling/index.vue
+++ b/src/views/customerService/afterSalesHandling/index.vue
@@ -1,32 +1,94 @@
 <template>
 	<div class="app-container">
-		<div class="search_form">
-			<div>
-				<span class="search_title">鍙嶉鏃ユ湡锛�</span>
-				<el-date-picker
-					v-model="searchForm.feedbackDate"
-					value-format="YYYY-MM-DD"
-					format="YYYY-MM-DD"
-					type="date"
-					placeholder="璇烽�夋嫨"
-					clearable
-					@change="handleQuery"
-				/>
-				<span class="search_title ml10">澶勭悊鏃ユ湡锛�</span>
-				<el-date-picker
-					v-model="searchForm.disDate"
-					value-format="YYYY-MM-DD"
-					format="YYYY-MM-DD"
-					type="date"
-					placeholder="璇烽�夋嫨"
-					clearable
-					@change="handleQuery"
-				/>
-				<el-button type="primary" @click="handleQuery" style="margin-left: 10px"
-				>鎼滅储</el-button
-				>
-			</div>
-		</div>
+		<div class="search-wrapper">
+      <el-form
+          :model="searchForm"
+          class="demo-form-inline"
+      >
+        <el-row :gutter="20">
+          <el-col :span="4">
+            <el-form-item>
+              <el-input
+                  v-model="searchForm.afterSalesServiceNo"
+                  placeholder="璇疯緭鍏ュ伐鍗曠紪鍙�"
+                  clearable
+              />
+            </el-form-item>
+          </el-col>
+          <el-col :span="4">
+            <el-form-item>
+              <el-select
+                  v-model="searchForm.status"
+                  placeholder="璇烽�夋嫨宸ュ崟鐘舵��"
+                  clearable
+              >
+                <el-option
+                    v-for="dict in workOrderStatusOptions"
+                    :key="dict.value"
+                    :label="dict.label"
+                    :value="dict.value"
+                />
+              </el-select>
+            </el-form-item>
+          </el-col>
+          <el-col :span="4">
+            <el-form-item>
+              <el-select
+                  v-model="searchForm.urgency"
+                  placeholder="璇烽�夋嫨绱ф�ョ▼搴�"
+                  clearable
+              >
+                <el-option
+                    v-for="dict in degreeOfUrgencyOptions"
+                    :key="dict.value"
+                    :label="dict.label"
+                    :value="dict.value"
+                />
+              </el-select>
+            </el-form-item>
+          </el-col>
+           <el-col :span="4">
+            <el-form-item>
+              <el-select
+                  v-model="searchForm.serviceType"
+                  placeholder="璇烽�夋嫨鍞悗绫诲瀷"
+                  clearable
+              >
+                <el-option
+                    v-for="dict in classificationOptions"
+                    :key="dict.value"
+                    :label="dict.label"
+                    :value="dict.value"
+                />
+              </el-select>
+            </el-form-item>
+          </el-col>
+            <el-col :span="4">
+              <el-form-item>
+                <el-input
+                    v-model="searchForm.orderNo"
+                    placeholder="璇疯緭鍏ラ攢鍞崟鍙�"
+                    clearable
+                />
+              </el-form-item>
+            </el-col>
+          
+          
+
+          <!-- 鎸夐挳 -->
+          <el-col :span="4">
+            <el-form-item>
+              <el-button type="primary" @click="handleQuery">
+                鎼滅储
+              </el-button>
+              <el-button @click="handleReset">
+                閲嶇疆
+              </el-button>
+            </el-form-item>
+          </el-col>
+        </el-row>
+      </el-form>
+    </div>
 		<div class="table_list">
 			<PIMTable
 				rowKey="id"
@@ -40,15 +102,30 @@
 			></PIMTable>
 		</div>
 		<form-dia ref="formDia" @close="handleQuery"></form-dia>
+		<FileListDialog
+			ref="fileListRef"
+			v-model="fileListDialogVisible"
+			title="鍞悗闄勪欢"
+			:show-upload-button="true"
+			:show-delete-button="true"
+			:upload-method="handleFileUpload"
+			:delete-method="handleFileDelete"
+		/>
 	</div>
 </template>
 
 <script setup>
-import {Search} from "@element-plus/icons-vue";
-import {onMounted, ref} from "vue";
+import { onMounted, ref, reactive, toRefs, getCurrentInstance, nextTick } from "vue";
 import FormDia from "@/views/customerService/afterSalesHandling/components/formDia.vue";
-import {ElMessageBox} from "element-plus";
-import {afterSalesServiceDelete, afterSalesServiceListPage} from "@/api/customerService/index.js";
+import FileListDialog from "@/components/Dialog/FileListDialog.vue";
+import { ElMessageBox } from "element-plus";
+import request from "@/utils/request";
+import { getToken } from "@/utils/auth";
+import {
+	afterSalesServiceListPage,
+	afterSalesServiceFileListPage,
+	afterSalesServiceFileDel,
+} from "@/api/customerService/index.js";
 import useUserStore from "@/store/modules/user.js";
 const { proxy } = getCurrentInstance();
 const userStore = useUserStore()
@@ -60,75 +137,113 @@
 	},
 });
 const { searchForm } = toRefs(data);
+/* 
+post_sale_waiting_list 鏂板鐨勫敭鍚庡垎绫�
+degree_of_urgency 鏂板鐨勭揣鎬ョ▼搴�
+work_order_status 涓婚〉鐨勫伐鍗曠姸鎬�
+*/
+const { post_sale_waiting_list, degree_of_urgency, work_order_status } = proxy.useDict(
+  "post_sale_waiting_list",
+  "degree_of_urgency",
+  "work_order_status",
+);
+
+const classificationOptions = computed(() => post_sale_waiting_list?.value || []);
+const degreeOfUrgencyOptions = computed(() => degree_of_urgency?.value || []);
+const workOrderStatusOptions = computed(() => work_order_status?.value || []);
 
 const tableColumn = ref([
 	{
-		label: "澶勭悊鐘舵��",
-		prop: "status",
-		dataType: "tag",
-		formatData: (params) => {
-			if (params == 1) {
-				return "寰呭鐞�";
-			} else if (params == 2) {
-				return "宸插鐞�";
-			} else {
-				return null;
-			}
-		},
-		formatType: (params) => {
-			if (params == 1) {
-				return "danger";
-			} else if (params == 2) {
-				return "success";
-			} else {
-				return null;
-			}
-		},
-	},
-	{
-		label: "鍙嶉鏃ユ湡",
-		prop: "feedbackDate",
-		width: 150,
-	},
-	{
-		label: "鐧昏浜�",
-		prop: "checkNickName",
-	},
-	{
-		label: "瀹㈡埛鍚嶇О",
-		prop: "customerName",
-		width: 200,
-	},
-	{
-		label: "闂鎻忚堪",
-		prop: "proDesc",
-		width:300
-	},
-	{
-		label: "鍏宠仈閮ㄩ棬",
-		prop: "deptName",
-		width: 200,
-	},
-	{
-		label: "澶勭悊浜�",
-		prop: "disposeNickName",
-	},
-	{
-		label: "澶勭悊缁撴灉",
-		prop: "disRes",
-		width: 200,
-	},
-	{
-		label: "澶勭悊鏃ユ湡",
-		prop: "disDate",
-		width: 150,
-	},
+    label: "宸ュ崟缂栧彿",
+    prop:"afterSalesServiceNo",
+    width: 150,
+    align: "center"
+  },
+  {
+    label: "閿�鍞崟鍙�",
+    prop:"salesContractNo",
+    width: 150,
+    align: "center"
+  },
+  {
+    label: "澶勭悊鐘舵��",
+    prop: "status",
+    dataType: "tag",
+    
+    formatData: (params) => {
+      if (params === 1) {
+        return "寰呭鐞�";
+      } else if (params === 2) {
+        return "宸插鐞�";
+      } else {
+        return null;
+      }
+    },
+    formatType: (params) => {
+      if (params === 1) {
+        return "danger";
+      } else if (params === 2) {
+        return "success";
+      } else {
+        return null;
+      }
+    },
+    align: "center"
+  },
+  {
+    label: "鍙嶉鏃ユ湡",
+    prop: "feedbackDate",
+    width: 150,
+    align: "center"
+  },
+  {
+    label: "鐧昏浜�",
+    prop: "checkNickName",
+    align: "center"
+  },
+  {
+    label: "绱ф�ョ▼搴�",
+    prop: "urgency",
+    // 鏍规嵁degreeOfUrgencyOptions瀛楀吀鍘昏嚜鍔ㄥ尮閰�
+    formatData: (params) => {
+      if (params) {
+        const item = degreeOfUrgencyOptions.value.find(item => item.value === params);
+        return item?.label || params;
+      }
+      return null;
+    },
+    align: "center"
+  },
+  {
+    label: "鍞悗绫诲瀷",
+    prop: "serviceType",
+    // 鏍规嵁classificationOptions瀛楀吀鍘昏嚜鍔ㄥ尮閰�
+    formatData: (params) => {
+      if (params) {
+        const item = classificationOptions.value.find(item => item.value === params);
+        return item?.label || params;
+      }
+      return null;
+    },
+    align: "center"
+  },
+  {
+    label: "闂鎻忚堪",
+    prop: "disRes",
+    width:300,
+  },
+  {
+    label: "鍏宠仈閮ㄩ棬",
+    prop: "deptName",
+    width: 200,
+    align: "center"
+  },
 	{
 		dataType: "action",
 		label: "鎿嶄綔",
 		align: "center",
 		fixed: 'right',
-		width: 120,
+		width: 240,
 		operation: [
 			{
 				name: "澶勭悊",
@@ -145,6 +260,14 @@
 				type: "text",
 				clickFun: (row) => {
 					openForm("view", row);
+				},
+			},
+			// TODO 涓哄啓鎶ュ憡娣诲姞鐨�
+			{
+				name: "闄勪欢",
+				type: "text",
+				clickFun: (row) => {
+					openFilesFormDia(row);
 				},
 			},
 		],
@@ -164,6 +287,156 @@
 	selectedRows.value = selection;
 };
 const formDia = ref()
+const fileListRef = ref(null)
+const fileListDialogVisible = ref(false)
+const currentFileRow = ref(null)
+
+// 閲嶇疆
+const handleReset = () => {
+  Object.keys(searchForm.value).forEach(key => {
+    searchForm.value[key] = ""
+  })
+}
+
+// 鎵撳紑闄勪欢寮规
+const openFilesFormDia = async (row) => {
+	currentFileRow.value = row
+	try {
+		const res = await afterSalesServiceFileListPage({
+			afterSalesServiceId: row.id,
+			current: 1,
+			size: 100,
+		})
+		if (res.code === 200 && fileListRef.value) {
+			const fileList = (res.data?.records || []).map((item) => ({
+				name: item.name || item.fileName,
+				url: item.url || item.fileUrl,
+				id: item.id,
+				...item,
+			}))
+			fileListRef.value.open(fileList)
+			fileListDialogVisible.value = true
+		} else {
+			fileListRef.value?.open([])
+			fileListDialogVisible.value = true
+		}
+	} catch (error) {
+		proxy.$modal.msgError("鑾峰彇闄勪欢鍒楄〃澶辫触")
+		fileListRef.value?.open([])
+		fileListDialogVisible.value = true
+	}
+}
+
+// 涓婁紶闄勪欢
+const handleFileUpload = async () => {
+	if (!currentFileRow.value) {
+		proxy.$modal.msgWarning("璇峰厛閫夋嫨鏁版嵁")
+		return
+	}
+	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 {
+				const formData = new FormData()
+				formData.append("file", file)
+				formData.append("id", currentFileRow.value.id)
+				const uploadRes = await request({
+					url: "/afterSalesService/file/upload",
+					method: "post",
+					data: formData,
+					headers: {
+						"Content-Type": "multipart/form-data",
+						Authorization: `Bearer ${getToken()}`,
+					},
+				})
+				if (uploadRes.code === 200) {
+					proxy.$modal.msgSuccess("鏂囦欢涓婁紶鎴愬姛")
+					// 閲嶆柊鑾峰彇鏂囦欢鍒楄〃
+					const listRes = await afterSalesServiceFileListPage({
+						afterSalesServiceId: currentFileRow.value.id,
+						current: 1,
+						size: 100,
+					})
+					if (listRes.code === 200 && fileListRef.value) {
+						const fileList = (listRes.data?.records || []).map((item) => ({
+							name: item.fileName,
+							url: item.fileUrl,
+							id: item.id,
+							...item,
+						}))
+						fileListRef.value.setList(fileList)
+					}
+					resolve({ name: file.name, url: "", id: null })
+				} else {
+					proxy.$modal.msgError(uploadRes.msg || "鏂囦欢涓婁紶澶辫触")
+					resolve(null)
+				}
+			} catch (err) {
+				proxy.$modal.msgError("鏂囦欢涓婁紶澶辫触")
+				resolve(null)
+			} finally {
+				document.body.removeChild(input)
+			}
+		}
+		document.body.appendChild(input)
+		input.click()
+	})
+}
+
+// 鍒犻櫎闄勪欢
+const handleFileDelete = async (row) => {
+	try {
+		// 娣诲姞纭瀵硅瘽妗�
+		const confirmResult = await ElMessageBox.confirm(
+			'纭畾瑕佸垹闄よ繖涓檮浠跺悧锛�',
+			'鍒犻櫎纭',
+			{
+				confirmButtonText: '纭畾',
+				cancelButtonText: '鍙栨秷',
+				type: 'warning'
+			}
+		)
+
+		if (confirmResult === 'confirm') {
+			const res = await afterSalesServiceFileDel(row.id)
+			if (res.code === 200) {
+				proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛")
+				if (currentFileRow.value && fileListRef.value) {
+					const listRes = await afterSalesServiceFileListPage({
+						afterSalesServiceId: currentFileRow.value.id,
+						current: 1,
+						size: 100,
+					})
+					if (listRes.code === 200) {
+						const fileList = (listRes.data?.records || []).map((item) => ({
+							name: item.fileName,
+							url: item.fileUrl,
+							id: item.id,
+							...item,
+						}))
+						fileListRef.value.setList(fileList)
+					}
+				}
+			} else {
+				proxy.$modal.msgError(res.msg || "鍒犻櫎澶辫触")
+				return false
+			}
+		}
+	} catch (error) {
+		// 濡傛灉鐢ㄦ埛鍙栨秷鍒犻櫎锛屼笉鏄剧ず閿欒淇℃伅
+		if (error !== 'cancel') {
+			proxy.$modal.msgError("鍒犻櫎澶辫触")
+		}
+		return false
+	}
+}
 
 // 鏌ヨ鍒楄〃
 /** 鎼滅储鎸夐挳鎿嶄綔 */
@@ -192,39 +465,31 @@
 	})
 };
 
-const handleDelete = () => {
-	let ids = [];
-	if (selectedRows.value.length > 0) {
-		ids = selectedRows.value.map((item) => item.id);
-	} else {
-		proxy.$modal.msgWarning("璇烽�夋嫨鏁版嵁");
-		return;
-	}
-	ElMessageBox.confirm("閫変腑鐨勫唴瀹瑰皢琚垹闄わ紝鏄惁纭鍒犻櫎锛�", "鍒犻櫎鎻愮ず", {
+// 瀵煎嚭
+const handleOut = () => {
+	ElMessageBox.confirm("閫変腑鐨勫唴瀹瑰皢琚鍑猴紝鏄惁纭瀵煎嚭锛�", "瀵煎嚭", {
 		confirmButtonText: "纭",
 		cancelButtonText: "鍙栨秷",
 		type: "warning",
 	})
 		.then(() => {
-			tableLoading.value = true;
-			afterSalesServiceDelete(ids)
-				.then((res) => {
-					proxy.$modal.msgSuccess("鍒犻櫎鎴愬姛");
-					getList();
-				})
-				.finally(() => {
-					tableLoading.value = false;
-				});
+			proxy.download("/afterSalesService/exportTwo", {}, "鍞悗澶勭悊.xlsx");
 		})
 		.catch(() => {
 			proxy.$modal.msg("宸插彇娑�");
 		});
 };
+
 onMounted(() => {
 	getList();
 });
 </script>
 
 <style scoped>
-
+.search-wrapper {
+  background: white;
+  padding: 1rem 1rem 0 1rem;
+  border: 8px;
+  border-radius: 16px;
+}
 </style>
\ No newline at end of file

--
Gitblit v1.9.3