Ver código fonte

refactor: 重构操作日志详情样式

dap 6 meses atrás
pai
commit
72ac227ecf

+ 3 - 2
package.json

@@ -43,6 +43,7 @@
     "vue": "3.4.34",
     "vue-cropper": "1.1.1",
     "vue-i18n": "9.10.2",
+    "vue-json-pretty": "^2.4.0",
     "vue-router": "4.3.2",
     "vue-types": "5.1.1",
     "vxe-table": "4.5.22"
@@ -66,10 +67,10 @@
     "eslint": "8.57.0",
     "eslint-config-prettier": "9.1.0",
     "eslint-define-config": "2.1.0",
+    "eslint-plugin-import": "2.29.1",
+    "eslint-plugin-node": "11.1.0",
     "eslint-plugin-prettier": "5.1.3",
     "eslint-plugin-promise": "6.1.1",
-    "eslint-plugin-node": "11.1.0",
-    "eslint-plugin-import": "2.29.1",
     "eslint-plugin-vue": "9.23.0",
     "fast-glob": "3.3.2",
     "postcss": "8.4.36",

+ 6 - 51
src/views/monitor/operlog/index.vue

@@ -123,56 +123,14 @@
       <pagination v-show="total > 0" v-model:page="queryParams.pageNum" v-model:limit="queryParams.pageSize" :total="total" @pagination="getList" />
     </el-card>
     <!-- 操作日志详细 -->
-    <el-dialog v-model="dialog.visible" title="操作日志详细" width="700px" append-to-body>
-      <el-form :model="form" label-width="100px">
-        <el-row>
-          <el-col :span="24">
-            <el-form-item label="登录信息:">{{ form.operName }} / {{ form.deptName }} / {{ form.operIp }} / {{ form.operLocation }}</el-form-item>
-          </el-col>
-          <el-col :span="12">
-            <el-form-item label="请求信息:">{{ form.requestMethod }} {{ form.operUrl }}</el-form-item>
-          </el-col>
-          <el-col :span="12">
-            <el-form-item label="操作模块:">{{ form.title }} / {{ typeFormat(form) }}</el-form-item>
-          </el-col>
-          <el-col :span="24">
-            <el-form-item label="操作方法:">{{ form.method }}</el-form-item>
-          </el-col>
-          <el-col :span="24">
-            <el-form-item label="请求参数:">{{ form.operParam }}</el-form-item>
-          </el-col>
-          <el-col :span="24">
-            <el-form-item label="返回参数:">{{ form.jsonResult }}</el-form-item>
-          </el-col>
-          <el-col :span="6">
-            <el-form-item label="操作状态:">
-              <div v-if="form.status === 0">正常</div>
-              <div v-else-if="form.status === 1">失败</div>
-            </el-form-item>
-          </el-col>
-          <el-col :span="8">
-            <el-form-item label="消耗时间:">{{ form.costTime }}毫秒</el-form-item>
-          </el-col>
-          <el-col :span="10">
-            <el-form-item label="操作时间:">{{ parseTime(form.operTime) }}</el-form-item>
-          </el-col>
-          <el-col :span="24">
-            <el-form-item v-if="form.status === 1" label="异常信息:">{{ form.errorMsg }}</el-form-item>
-          </el-col>
-        </el-row>
-      </el-form>
-      <template #footer>
-        <div class="dialog-footer">
-          <el-button @click="dialog.visible = false">关 闭</el-button>
-        </div>
-      </template>
-    </el-dialog>
+    <OperInfoDialog ref="operInfoDialogRef" />
   </div>
 </template>
 
 <script setup name="Operlog" lang="ts">
 import { list, delOperlog, cleanOperlog } from '@/api/monitor/operlog';
 import { OperLogForm, OperLogQuery, OperLogVO } from '@/api/monitor/operlog/types';
+import OperInfoDialog from './oper-info-dialog.vue';
 
 const { proxy } = getCurrentInstance() as ComponentInternalInstance;
 const { sys_oper_type, sys_common_status } = toRefs<any>(proxy?.useDict('sys_oper_type', 'sys_common_status'));
@@ -189,11 +147,6 @@ const defaultSort = ref<any>({ prop: 'operTime', order: 'descending' });
 const operLogTableRef = ref<ElTableInstance>();
 const queryFormRef = ref<ElFormInstance>();
 
-const dialog = reactive<DialogOption>({
-  visible: false,
-  title: ''
-});
-
 const data = reactive<PageData<OperLogForm, OperLogQuery>>({
   form: {
     operId: undefined,
@@ -267,11 +220,13 @@ const handleSortChange = (column: any) => {
   queryParams.value.isAsc = column.order;
   getList();
 };
+
+const operInfoDialogRef = ref<InstanceType<typeof OperInfoDialog>>();
 /** 详细按钮操作 */
 const handleView = (row: OperLogVO) => {
-  dialog.visible = true;
-  form.value = row;
+  operInfoDialogRef.value.openDialog(row);
 };
+
 /** 删除按钮操作 */
 const handleDelete = async (row?: OperLogVO) => {
   const operIds = row?.operId || ids.value;

+ 111 - 0
src/views/monitor/operlog/oper-info-dialog.vue

@@ -0,0 +1,111 @@
+<template>
+  <el-dialog v-model="open" title="操作日志详细" width="700px" append-to-body close-on-click-modal @closed="info = null">
+    <el-descriptions v-if="info" :column="1" border>
+      <el-descriptions-item label="操作状态">
+        <template #default>
+          <el-tag v-if="info.status === 0" type="success">正常</el-tag>
+          <el-tag v-else-if="info.status === 1" type="danger">失败</el-tag>
+        </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="登录信息">
+        <template #default> {{ info.operName }} / {{ info.deptName }} / {{ info.operIp }} / {{ info.operLocation }} </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="请求信息">
+        <template #default> {{ info.requestMethod }} {{ info.operUrl }} </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="操作模块">
+        <template #default> {{ info.title }} / {{ typeFormat(info) }} </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="操作方法">
+        <template #default>
+          {{ info.method }}
+        </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="请求参数">
+        <template #default>
+          <div class="max-h-300px overflow-y-auto">
+            <VueJsonPretty :data="formatToJsonObject(info.operParam)" />
+          </div>
+        </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="返回参数">
+        <template #default>
+          <div class="max-h-300px overflow-y-auto">
+            <VueJsonPretty :data="formatToJsonObject(info.jsonResult)" />
+          </div>
+        </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="消耗时间">
+        <template #default>
+          <span> {{ info.costTime }}ms </span>
+        </template>
+      </el-descriptions-item>
+      <el-descriptions-item label="操作时间">
+        <template #default> {{ parseTime(info.operTime) }}</template>
+      </el-descriptions-item>
+      <el-descriptions-item v-if="info.status === 1" label="异常信息">
+        <template #default>
+          <span class="text-danger"> {{ info.errorMsg }}</span>
+        </template>
+      </el-descriptions-item>
+    </el-descriptions>
+  </el-dialog>
+</template>
+
+<script setup lang="ts">
+import type { OperLogForm } from '@/api/monitor/operlog/types';
+import VueJsonPretty from 'vue-json-pretty';
+import 'vue-json-pretty/lib/styles.css';
+
+const open = ref(false);
+const info = ref<OperLogForm | null>(null);
+function openDialog(row: OperLogForm) {
+  info.value = row;
+  open.value = true;
+}
+
+function closeDialog() {
+  open.value = false;
+}
+
+defineExpose({
+  openDialog,
+  closeDialog
+});
+
+/**
+ * json转为对象
+ * @param data 原始数据
+ */
+function formatToJsonObject(data: string) {
+  try {
+    return JSON.parse(data);
+  } catch (error) {
+    return data;
+  }
+}
+
+/**
+ * 字典信息
+ */
+const { proxy } = getCurrentInstance() as ComponentInternalInstance;
+const { sys_oper_type } = toRefs<any>(proxy?.useDict('sys_oper_type'));
+const typeFormat = (row: OperLogForm) => {
+  return proxy?.selectDictLabel(sys_oper_type.value, row.businessType);
+};
+</script>
+
+<style scoped>
+/**
+label宽度固定
+*/
+:deep(.el-descriptions__label) {
+  min-width: 100px;
+}
+/**
+文字超过 换行显示
+*/
+:deep(.el-descriptions__content) {
+  max-width: 300px;
+}
+</style>