Commit f09a1a4b8eeb1fd1a5266311b2ae0dabf58d4223

Authored by xingyu4j
1 parent 4a692ed2

refactor: operatelog

yudao-ui-admin-vue3/src/api/system/operatelog/index.ts
1 import request from '@/config/axios' 1 import request from '@/config/axios'
2 2
  3 +export type OperateLogVO = {
  4 + id: number
  5 + userNickname: string
  6 + traceId: string
  7 + userId: number
  8 + module: string
  9 + name: string
  10 + type: number
  11 + content: string
  12 + exts: object
  13 + requestMethod: string
  14 + requestUrl: string
  15 + userIp: string
  16 + userAgent: string
  17 + javaMethod: string
  18 + javaMethodArgs: string
  19 + startTime: string
  20 + duration: number
  21 + resultCode: number
  22 + resultMsg: string
  23 + resultData: string
  24 +}
  25 +export interface OperateLogPageReqVO extends BasePage {
  26 + module?: string
  27 + userNickname?: string
  28 + type?: number
  29 + success?: boolean
  30 + startTime?: string[]
  31 +}
  32 +
3 // 查询操作日志列表 33 // 查询操作日志列表
4 -export const getOperateLogPageApi = (params) => { 34 +export const getOperateLogPageApi = (params: OperateLogPageReqVO) => {
5 return request.get({ url: '/system/operate-log/page', params }) 35 return request.get({ url: '/system/operate-log/page', params })
6 } 36 }
7 // 导出操作日志 37 // 导出操作日志
8 -export const exportOperateLogApi = (params) => { 38 +export const exportOperateLogApi = (params: OperateLogPageReqVO) => {
9 return request.download({ url: '/system/operate-log/export', params }) 39 return request.download({ url: '/system/operate-log/export', params })
10 } 40 }
yudao-ui-admin-vue3/src/api/system/operatelog/types.ts deleted
1 -export type OperateLogVO = {  
2 - id: number  
3 - userNickname: string  
4 - traceId: string  
5 - userId: number  
6 - module: string  
7 - name: string  
8 - type: number  
9 - content: string  
10 - exts: object  
11 - requestMethod: string  
12 - requestUrl: string  
13 - userIp: string  
14 - userAgent: string  
15 - javaMethod: string  
16 - javaMethodArgs: string  
17 - startTime: string  
18 - duration: number  
19 - resultCode: number  
20 - resultMsg: string  
21 - resultData: string  
22 -}  
yudao-ui-admin-vue3/src/hooks/web/useVxeCrudSchemas.ts
@@ -20,6 +20,7 @@ export type VxeCrudSchema = { @@ -20,6 +20,7 @@ export type VxeCrudSchema = {
20 primaryType?: VxeColumnPropTypes.Type 20 primaryType?: VxeColumnPropTypes.Type
21 // 是否开启操作栏插槽 21 // 是否开启操作栏插槽
22 action?: boolean 22 action?: boolean
  23 + actionWidth?: string
23 columns: VxeCrudColumns[] 24 columns: VxeCrudColumns[]
24 } 25 }
25 type VxeCrudColumns = Omit<VxeTableColumn, 'children'> & { 26 type VxeCrudColumns = Omit<VxeTableColumn, 'children'> & {
@@ -204,7 +205,7 @@ const filterTableSchema = (crudSchema: VxeCrudSchema): VxeGridPropTypes.Columns @@ -204,7 +205,7 @@ const filterTableSchema = (crudSchema: VxeCrudSchema): VxeGridPropTypes.Columns
204 const tableSchemaItem = { 205 const tableSchemaItem = {
205 title: t('table.action'), 206 title: t('table.action'),
206 field: 'actionbtns', 207 field: 'actionbtns',
207 - width: '240px', 208 + width: crudSchema.actionWidth ? crudSchema.actionWidth : '240px',
208 slots: { 209 slots: {
209 default: 'actionbtns_default' 210 default: 'actionbtns_default'
210 } 211 }
yudao-ui-admin-vue3/src/views/system/dept/index.vue
@@ -10,11 +10,6 @@ import { DeptVO } from &#39;@/api/system/dept/types&#39; @@ -10,11 +10,6 @@ import { DeptVO } from &#39;@/api/system/dept/types&#39;
10 import { useMessage } from '@/hooks/web/useMessage' 10 import { useMessage } from '@/hooks/web/useMessage'
11 import { getListSimpleUsersApi } from '@/api/system/user' 11 import { getListSimpleUsersApi } from '@/api/system/user'
12 const message = useMessage() 12 const message = useMessage()
13 -interface Tree {  
14 - id: number  
15 - name: string  
16 - children?: Tree[]  
17 -}  
18 13
19 const defaultProps = { 14 const defaultProps = {
20 children: 'children', 15 children: 'children',
yudao-ui-admin-vue3/src/views/system/loginlog/loginLog.data.ts
@@ -9,6 +9,7 @@ const crudSchemas = reactive&lt;VxeCrudSchema&gt;({ @@ -9,6 +9,7 @@ const crudSchemas = reactive&lt;VxeCrudSchema&gt;({
9 primaryKey: 'id', 9 primaryKey: 'id',
10 primaryType: 'seq', 10 primaryType: 'seq',
11 action: true, 11 action: true,
  12 + actionWidth: '80px',
12 columns: [ 13 columns: [
13 { 14 {
14 title: '日志类型', 15 title: '日志类型',
yudao-ui-admin-vue3/src/views/system/operatelog/index.vue
1 -<script setup lang="ts">  
2 -import dayjs from 'dayjs'  
3 -import { useTable } from '@/hooks/web/useTable'  
4 -import { allSchemas } from './operatelog.data'  
5 -import { DICT_TYPE } from '@/utils/dict'  
6 -import { useI18n } from '@/hooks/web/useI18n'  
7 -import type { OperateLogVO } from '@/api/system/operatelog/types'  
8 -import * as OperateLogApi from '@/api/system/operatelog'  
9 -import { ref } from 'vue'  
10 -const { t } = useI18n() // 国际化  
11 -// ========== 列表相关 ==========  
12 -const { register, tableObject, methods } = useTable<OperateLogVO>({  
13 - getListApi: OperateLogApi.getOperateLogPageApi,  
14 - exportListApi: OperateLogApi.exportOperateLogApi  
15 -})  
16 -// ========== 详情相关 ==========  
17 -const detailRef = ref() // 详情 Ref  
18 -const dialogVisible = ref(false) // 是否显示弹出层  
19 -const dialogTitle = ref(t('action.detail')) // 弹出层标题  
20 -const { getList, setSearchParams, exportList } = methods  
21 -// 详情  
22 -const handleDetail = (row: OperateLogVO) => {  
23 - // 设置数据  
24 - detailRef.value = row  
25 - dialogVisible.value = true  
26 -}  
27 -getList()  
28 -</script>  
29 <template> 1 <template>
30 <ContentWrap> 2 <ContentWrap>
31 - <Search :schema="allSchemas.searchSchema" @search="setSearchParams" @reset="setSearchParams" />  
32 - </ContentWrap>  
33 - <ContentWrap>  
34 - <!-- 操作工具栏 -->  
35 - <div class="mb-10px">  
36 - <el-button  
37 - type="warning"  
38 - v-hasPermi="['system:operate-log:export']"  
39 - :loading="tableObject.exportLoading"  
40 - @click="exportList('操作日志.xls')"  
41 - >  
42 - <Icon icon="ep:download" class="mr-5px" /> {{ t('action.export') }}  
43 - </el-button>  
44 - </div>  
45 - <Table  
46 - :columns="allSchemas.tableColumns"  
47 - :selection="false"  
48 - :data="tableObject.tableList"  
49 - :loading="tableObject.loading"  
50 - :pagination="{  
51 - total: tableObject.total  
52 - }"  
53 - v-model:pageSize="tableObject.pageSize"  
54 - v-model:currentPage="tableObject.currentPage"  
55 - @register="register"  
56 - >  
57 - <template #type="{ row }">  
58 - <DictTag :type="DICT_TYPE.SYSTEM_OPERATE_TYPE" :value="row.type" /> 3 + <!-- 列表 -->
  4 + <vxe-grid ref="xGrid" v-bind="gridOptions" class="xtable-scrollbar">
  5 + <!-- 操作:新增 -->
  6 + <template #toolbar_buttons>
  7 + <XButton
  8 + type="warning"
  9 + preIcon="ep:download"
  10 + :title="t('action.export')"
  11 + v-hasPermi="['system:operate-log:export']"
  12 + @click="handleExport()"
  13 + />
59 </template> 14 </template>
60 <template #duration="{ row }"> 15 <template #duration="{ row }">
61 <span>{{ row.duration + 'ms' }}</span> 16 <span>{{ row.duration + 'ms' }}</span>
@@ -63,35 +18,68 @@ getList() @@ -63,35 +18,68 @@ getList()
63 <template #resultCode="{ row }"> 18 <template #resultCode="{ row }">
64 <span>{{ row.resultCode === 0 ? '成功' : '失败' }}</span> 19 <span>{{ row.resultCode === 0 ? '成功' : '失败' }}</span>
65 </template> 20 </template>
66 - <template #startTime="{ row }">  
67 - <span>{{ dayjs(row.startTime).format('YYYY-MM-DD HH:mm:ss') }}</span> 21 + <template #actionbtns_default="{ row }">
  22 + <!-- 操作:详情 -->
  23 + <XTextButton preIcon="ep:view" :title="t('action.detail')" @click="handleDetail(row)" />
68 </template> 24 </template>
69 - <template #action="{ row }">  
70 - <el-button link type="primary" @click="handleDetail(row)">  
71 - <Icon icon="ep:view" class="mr-1px" /> {{ t('action.detail') }}  
72 - </el-button>  
73 - </template>  
74 - </Table> 25 + </vxe-grid>
75 </ContentWrap> 26 </ContentWrap>
76 - <Dialog v-model="dialogVisible" :title="dialogTitle">  
77 - <!-- 对话框(详情) -->  
78 - <Descriptions :schema="allSchemas.detailSchema" :data="detailRef">  
79 - <template #resultCode="{ row }">  
80 - <span>{{ row.resultCode === 0 ? '成功' : '失败' }}</span>  
81 - </template>  
82 - <template #type="{ row }">  
83 - <DictTag :type="DICT_TYPE.SYSTEM_OPERATE_TYPE" :value="row.type" />  
84 - </template>  
85 - <template #duration="{ row }">  
86 - <span>{{ row.duration + 'ms' }}</span>  
87 - </template>  
88 - <template #startTime="{ row }">  
89 - <span>{{ dayjs(row.startTime).format('YYYY-MM-DD HH:mm:ss') }}</span>  
90 - </template>  
91 - </Descriptions>  
92 - <!-- 操作按钮 --> 27 + <!-- 弹窗 -->
  28 + <XModal id="postModel" v-model="dialogVisible" :title="dialogTitle">
  29 + <template #default>
  30 + <!-- 对话框(详情) -->
  31 + <Descriptions :schema="allSchemas.detailSchema" :data="detailRef">
  32 + <template #resultCode="{ row }">
  33 + <span>{{ row.resultCode === 0 ? '成功' : '失败' }}</span>
  34 + </template>
  35 + <template #duration="{ row }">
  36 + <span>{{ row.duration + 'ms' }}</span>
  37 + </template>
  38 + </Descriptions>
  39 + </template>
93 <template #footer> 40 <template #footer>
94 - <el-button @click="dialogVisible = false">{{ t('dialog.close') }}</el-button> 41 + <!-- 按钮:关闭 -->
  42 + <XButton :loading="actionLoading" :title="t('dialog.close')" @click="dialogVisible = false" />
95 </template> 43 </template>
96 - </Dialog> 44 + </XModal>
97 </template> 45 </template>
  46 +<script setup lang="ts">
  47 +// 全局相关的 import
  48 +import { ref } from 'vue'
  49 +import { useI18n } from '@/hooks/web/useI18n'
  50 +import { useVxeGrid } from '@/hooks/web/useVxeGrid'
  51 +import { VxeGridInstance } from 'vxe-table'
  52 +// 业务相关的 import
  53 +import * as OperateLogApi from '@/api/system/operatelog'
  54 +import { allSchemas } from './operatelog.data'
  55 +import download from '@/utils/download'
  56 +
  57 +const { t } = useI18n() // 国际化
  58 +// 列表相关的变量
  59 +const xGrid = ref<VxeGridInstance>() // 列表 Grid Ref
  60 +const { gridOptions } = useVxeGrid<OperateLogApi.OperateLogVO>({
  61 + allSchemas: allSchemas,
  62 + getListApi: OperateLogApi.getOperateLogPageApi
  63 +})
  64 +// 弹窗相关的变量
  65 +const dialogVisible = ref(false) // 是否显示弹出层
  66 +const dialogTitle = ref('edit') // 弹出层标题
  67 +const actionLoading = ref(false) // 按钮 Loading
  68 +const detailRef = ref() // 详情 Ref
  69 +// 详情
  70 +const handleDetail = (row: OperateLogApi.OperateLogVO) => {
  71 + // 设置数据
  72 + detailRef.value = row
  73 + dialogVisible.value = true
  74 +}
  75 +
  76 +// 导出操作
  77 +const handleExport = async () => {
  78 + const queryParams = Object.assign(
  79 + {},
  80 + JSON.parse(JSON.stringify(xGrid.value?.getRefMaps().refForm.value.data))
  81 + )
  82 + const res = await OperateLogApi.exportOperateLogApi(queryParams)
  83 + download.excel(res, '岗位列表.xls')
  84 +}
  85 +</script>
yudao-ui-admin-vue3/src/views/system/operatelog/operatelog.data.ts
1 import { reactive } from 'vue' 1 import { reactive } from 'vue'
2 import { DICT_TYPE } from '@/utils/dict' 2 import { DICT_TYPE } from '@/utils/dict'
3 -import { useI18n } from '@/hooks/web/useI18n'  
4 -import { CrudSchema, useCrudSchemas } from '@/hooks/web/useCrudSchemas'  
5 -const { t } = useI18n() // 国际化  
6 -const crudSchemas = reactive<CrudSchema[]>([  
7 - {  
8 - label: t('common.index'),  
9 - field: 'id',  
10 - type: 'index',  
11 - form: {  
12 - show: false  
13 - }  
14 - },  
15 - {  
16 - label: '操作模块',  
17 - field: 'module',  
18 - search: {  
19 - show: true  
20 - }  
21 - },  
22 - {  
23 - label: '操作名',  
24 - field: 'name'  
25 - },  
26 - {  
27 - label: '操作类型',  
28 - field: 'type',  
29 - dictType: DICT_TYPE.SYSTEM_OPERATE_TYPE,  
30 - search: {  
31 - show: true  
32 - }  
33 - },  
34 - {  
35 - label: '请求方法名',  
36 - field: 'requestMethod'  
37 - },  
38 - {  
39 - label: '请求地址',  
40 - field: 'requestUrl'  
41 - },  
42 - {  
43 - label: '操作人员',  
44 - field: 'userNickname',  
45 - search: {  
46 - show: true  
47 - }  
48 - },  
49 - {  
50 - label: '操作明细',  
51 - field: 'content',  
52 - table: {  
53 - show: false  
54 - }  
55 - },  
56 - {  
57 - label: '用户 IP',  
58 - field: 'userIp',  
59 - table: {  
60 - show: false  
61 - }  
62 - },  
63 - {  
64 - label: 'userAgent',  
65 - field: 'userAgent'  
66 - },  
67 - {  
68 - label: '操作结果',  
69 - field: 'resultCode',  
70 - search: {  
71 - show: true,  
72 - component: 'Select',  
73 - componentProps: {  
74 - options: [  
75 - { label: '成功', value: true },  
76 - { label: '失败', value: false }  
77 - ] 3 +import { VxeCrudSchema, useVxeCrudSchemas } from '@/hooks/web/useVxeCrudSchemas'
  4 +
  5 +const crudSchemas = reactive<VxeCrudSchema>({
  6 + primaryKey: 'id',
  7 + primaryType: 'seq',
  8 + action: true,
  9 + actionWidth: '80px',
  10 + columns: [
  11 + {
  12 + title: '操作模块',
  13 + field: 'module',
  14 + isSearch: true
  15 + },
  16 + {
  17 + title: '操作名',
  18 + field: 'name'
  19 + },
  20 + {
  21 + title: '操作类型',
  22 + field: 'type',
  23 + dictType: DICT_TYPE.SYSTEM_OPERATE_TYPE,
  24 + isSearch: true
  25 + },
  26 + {
  27 + title: '请求方法名',
  28 + field: 'requestMethod'
  29 + },
  30 + {
  31 + title: '请求地址',
  32 + field: 'requestUrl'
  33 + },
  34 + {
  35 + title: '操作人员',
  36 + field: 'userNickname',
  37 + isSearch: true
  38 + },
  39 + {
  40 + title: '操作明细',
  41 + field: 'content',
  42 + isTable: false
  43 + },
  44 + {
  45 + title: '用户 IP',
  46 + field: 'userIp',
  47 + isTable: false
  48 + },
  49 + {
  50 + title: 'userAgent',
  51 + field: 'userAgent'
  52 + },
  53 + {
  54 + title: '操作结果',
  55 + field: 'resultCode',
  56 + table: {
  57 + slots: {
  58 + default: 'resultCode'
  59 + }
78 } 60 }
79 - }  
80 - },  
81 - {  
82 - label: '操作日期',  
83 - field: 'startTime',  
84 - form: {  
85 - show: false  
86 }, 61 },
87 - search: {  
88 - show: true,  
89 - component: 'DatePicker',  
90 - componentProps: {  
91 - type: 'daterange',  
92 - valueFormat: 'YYYY-MM-DD HH:mm:ss',  
93 - defaultTime: [new Date(2000, 1, 1, 0, 0, 0), new Date(2000, 2, 1, 23, 59, 59)] 62 + {
  63 + title: '操作日期',
  64 + field: 'startTime',
  65 + formatter: 'formatDate',
  66 + isForm: false,
  67 + search: {
  68 + itemRender: {
  69 + name: 'XDataTimePicker'
  70 + }
94 } 71 }
95 - }  
96 - },  
97 - {  
98 - label: '执行时长',  
99 - field: 'duration'  
100 - },  
101 - {  
102 - label: t('table.action'),  
103 - field: 'action',  
104 - width: '120px',  
105 - form: {  
106 - show: false  
107 }, 72 },
108 - detail: {  
109 - show: false 73 + {
  74 + title: '执行时长',
  75 + field: 'duration',
  76 + table: {
  77 + slots: {
  78 + default: 'duration'
  79 + }
  80 + }
110 } 81 }
111 - }  
112 -])  
113 -export const { allSchemas } = useCrudSchemas(crudSchemas) 82 + ]
  83 +})
  84 +export const { allSchemas } = useVxeCrudSchemas(crudSchemas)
yudao-ui-admin-vue3/src/views/system/user/index.vue
@@ -39,11 +39,6 @@ import { getAccessToken, getTenantId } from &#39;@/utils/auth&#39; @@ -39,11 +39,6 @@ import { getAccessToken, getTenantId } from &#39;@/utils/auth&#39;
39 import { useMessage } from '@/hooks/web/useMessage' 39 import { useMessage } from '@/hooks/web/useMessage'
40 40
41 const message = useMessage() 41 const message = useMessage()
42 -interface Tree {  
43 - id: number  
44 - name: string  
45 - children?: Tree[]  
46 -}  
47 42
48 const defaultProps = { 43 const defaultProps = {
49 children: 'children', 44 children: 'children',