wupengfei
2025-09-29 eb0b661cb59ce88085e5f2a17d5ce42ac8739a0f
feat: 日志
2个文件已添加
4个文件已修改
497 ■■■■■ 已修改文件
.eslintrc-auto-import.json 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
auto-imports.d.ts 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/constants/logs.ts 27 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/TraceIdLogManage/ConsoleLogs.vue 221 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/TraceIdLogManage/DbAuditLogs.vue 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/TraceIdLogManage/SmsLogs.vue 236 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
.eslintrc-auto-import.json
@@ -28,6 +28,7 @@
    "EnumClientTypeText": true,
    "EnumCodeUrlScene": true,
    "EnumConsoleLogAccess": true,
    "EnumConsoleLogAccessText": true,
    "EnumContractTemplateStatus": true,
    "EnumContractTemplateStatusText": true,
    "EnumContractTemplateStatusTextForEnterpriseFilter": true,
@@ -55,6 +56,7 @@
    "EnumEnterpriseWalletTransactionType": true,
    "EnumGetEnterpriseEmployeesQuerySignContractStatus": true,
    "EnumLogLevel": true,
    "EnumLogLevelText": true,
    "EnumMenuType": true,
    "EnumMenuVisitLevel": true,
    "EnumOcrAccess": true,
@@ -81,8 +83,10 @@
    "EnumSettlementCycleText": true,
    "EnumSmsAccess": true,
    "EnumSmsAccessText": true,
    "EnumSmsAccessTextUseInLogs": true,
    "EnumSmsAccessTextUseInSms": true,
    "EnumSmsStatus": true,
    "EnumSmsStatusText": true,
    "EnumTaskCheckReceiveStatus": true,
    "EnumTaskCheckReceiveStatusText": true,
    "EnumTaskRecommendStatus": true,
auto-imports.d.ts
@@ -30,6 +30,7 @@
  const EnumClientTypeText: typeof import('./src/constants/apiEnumText')['EnumClientTypeText']
  const EnumCodeUrlScene: typeof import('./src/constants/apiEnum')['EnumCodeUrlScene']
  const EnumConsoleLogAccess: typeof import('./src/constants/apiEnum')['EnumConsoleLogAccess']
  const EnumConsoleLogAccessText: typeof import('./src/constants/logs')['EnumConsoleLogAccessText']
  const EnumContractTemplateStatus: typeof import('./src/constants/apiEnum')['EnumContractTemplateStatus']
  const EnumContractTemplateStatusText: typeof import('./src/constants/electronSign')['EnumContractTemplateStatusText']
  const EnumContractTemplateStatusTextForEnterpriseFilter: typeof import('./src/constants/electronSign')['EnumContractTemplateStatusTextForEnterpriseFilter']
@@ -58,6 +59,7 @@
  const EnumEnterpriseWalletTransactionType: typeof import('./src/constants/apiEnum')['EnumEnterpriseWalletTransactionType']
  const EnumGetEnterpriseEmployeesQuerySignContractStatus: typeof import('./src/constants/apiEnum')['EnumGetEnterpriseEmployeesQuerySignContractStatus']
  const EnumLogLevel: typeof import('./src/constants/apiEnum')['EnumLogLevel']
  const EnumLogLevelText: typeof import('./src/constants/logs')['EnumLogLevelText']
  const EnumMenuType: typeof import('./src/constants/apiEnum')['EnumMenuType']
  const EnumMenuVisitLevel: typeof import('./src/constants/apiEnum')['EnumMenuVisitLevel']
  const EnumOcrAccess: typeof import('./src/constants/apiEnum')['EnumOcrAccess']
@@ -85,8 +87,10 @@
  const EnumSettlementCycleText: typeof import('./src/constants/task')['EnumSettlementCycleText']
  const EnumSmsAccess: typeof import('./src/constants/apiEnum')['EnumSmsAccess']
  const EnumSmsAccessText: typeof import('./src/constants/enterprise')['EnumSmsAccessText']
  const EnumSmsAccessTextUseInLogs: typeof import('./src/constants/logs')['EnumSmsAccessTextUseInLogs']
  const EnumSmsAccessTextUseInSms: typeof import('./src/constants/enterprise')['EnumSmsAccessTextUseInSms']
  const EnumSmsStatus: typeof import('./src/constants/apiEnum')['EnumSmsStatus']
  const EnumSmsStatusText: typeof import('./src/constants/logs')['EnumSmsStatusText']
  const EnumTaskCheckReceiveStatus: typeof import('./src/constants/apiEnum')['EnumTaskCheckReceiveStatus']
  const EnumTaskCheckReceiveStatusText: typeof import('./src/constants/task')['EnumTaskCheckReceiveStatusText']
  const EnumTaskRecommendStatus: typeof import('./src/constants/apiEnum')['EnumTaskRecommendStatus']
@@ -345,6 +349,7 @@
    readonly EnumClientTypeText: UnwrapRef<typeof import('./src/constants/apiEnumText')['EnumClientTypeText']>
    readonly EnumCodeUrlScene: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumCodeUrlScene']>
    readonly EnumConsoleLogAccess: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumConsoleLogAccess']>
    readonly EnumConsoleLogAccessText: UnwrapRef<typeof import('./src/constants/logs')['EnumConsoleLogAccessText']>
    readonly EnumContractTemplateStatus: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumContractTemplateStatus']>
    readonly EnumContractTemplateStatusText: UnwrapRef<typeof import('./src/constants/electronSign')['EnumContractTemplateStatusText']>
    readonly EnumContractTemplateStatusTextForEnterpriseFilter: UnwrapRef<typeof import('./src/constants/electronSign')['EnumContractTemplateStatusTextForEnterpriseFilter']>
@@ -372,6 +377,7 @@
    readonly EnumEnterpriseWalletTransactionType: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumEnterpriseWalletTransactionType']>
    readonly EnumGetEnterpriseEmployeesQuerySignContractStatus: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumGetEnterpriseEmployeesQuerySignContractStatus']>
    readonly EnumLogLevel: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumLogLevel']>
    readonly EnumLogLevelText: UnwrapRef<typeof import('./src/constants/logs')['EnumLogLevelText']>
    readonly EnumMenuType: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumMenuType']>
    readonly EnumMenuVisitLevel: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumMenuVisitLevel']>
    readonly EnumOcrAccess: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumOcrAccess']>
@@ -398,8 +404,10 @@
    readonly EnumSettlementCycleText: UnwrapRef<typeof import('./src/constants/task')['EnumSettlementCycleText']>
    readonly EnumSmsAccess: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumSmsAccess']>
    readonly EnumSmsAccessText: UnwrapRef<typeof import('./src/constants/enterprise')['EnumSmsAccessText']>
    readonly EnumSmsAccessTextUseInLogs: UnwrapRef<typeof import('./src/constants/logs')['EnumSmsAccessTextUseInLogs']>
    readonly EnumSmsAccessTextUseInSms: UnwrapRef<typeof import('./src/constants/enterprise')['EnumSmsAccessTextUseInSms']>
    readonly EnumSmsStatus: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumSmsStatus']>
    readonly EnumSmsStatusText: UnwrapRef<typeof import('./src/constants/logs')['EnumSmsStatusText']>
    readonly EnumTaskCheckReceiveStatus: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumTaskCheckReceiveStatus']>
    readonly EnumTaskCheckReceiveStatusText: UnwrapRef<typeof import('./src/constants/task')['EnumTaskCheckReceiveStatusText']>
    readonly EnumTaskRecommendStatus: UnwrapRef<typeof import('./src/constants/apiEnum')['EnumTaskRecommendStatus']>
src/constants/logs.ts
@@ -5,3 +5,30 @@
  [EnumResourceMethod.Put]: '修改',
  [EnumResourceMethod.Delete]: '删除',
};
export const EnumConsoleLogAccessText = {
  [EnumConsoleLogAccess.Back]: '后端',
  [EnumConsoleLogAccess.Front]: '前端',
};
export const EnumSmsAccessTextUseInLogs = {
  [EnumSmsAccess.None]: '无',
  [EnumSmsAccess.AliyunSms]: '阿里云短信',
  [EnumSmsAccess.ChengLiYe]: '诚立业',
};
export const EnumSmsStatusText = {
  [EnumSmsStatus.Wait]: '待发送',
  [EnumSmsStatus.InProcess]: '发送中',
  [EnumSmsStatus.Success]: '发送成功',
  [EnumSmsStatus.Fail]: '发送失败',
};
export const EnumLogLevelText = {
  [EnumLogLevel.Trace]: '跟踪',
  [EnumLogLevel.Debug]: '调试',
  [EnumLogLevel.Information]: '信息',
  [EnumLogLevel.Warning]: '警告',
  [EnumLogLevel.Error]: '错误',
  [EnumLogLevel.Critical]: '严重',
};
src/views/TraceIdLogManage/ConsoleLogs.vue
New file
@@ -0,0 +1,221 @@
<template>
  <LoadingLayout :loading="state.loading">
    <AppContainer>
      <ProTableQueryFilterBar @on-reset="reset">
        <template #query>
          <QueryFilterItem tip-content="通道">
            <FieldRadio
              v-model="extraParamState.access"
              :value-enum="EnumConsoleLogAccessText"
              buttonStyle
              showAllBtn
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem tip-content="等级">
            <FieldRadio
              v-model="extraParamState.level"
              :value-enum="EnumLogLevelText"
              buttonStyle
              showAllBtn
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem tip-content="创建时间">
            <FieldDatePicker
              v-model="extraParamState.createdTime"
              type="daterange"
              range-separator="~"
              start-placeholder="开始时间"
              end-placeholder="结束时间"
              clearable
              @change="getList()"
            ></FieldDatePicker>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.createdUser"
              style="width: 260px"
              placeholder="操作人createdUser"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.traceId"
              style="width: 260px"
              placeholder="跟踪Id(traceId)"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.content"
              style="width: 260px"
              placeholder="内容content"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.url"
              style="width: 260px"
              placeholder="链接地址url"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.request"
              style="width: 260px"
              placeholder="传参request"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.ext"
              style="width: 260px"
              placeholder="扩展ext"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
        </template>
      </ProTableQueryFilterBar>
      <ProTableV2 v-bind="proTableProps" :columns="column" :operationBtns="operationBtns">
        <template #createdUser="{ row }">
          <el-button
            v-if="row.createdUser"
            type="primary"
            link
            @click="
              handleAdd({ json: { createdUser: JSON.parse(JSON.stringify(row.createdUser)) } })
            "
            >查看</el-button
          >
        </template>
      </ProTableV2>
      <JsonViewerDialog v-bind="dialogProps" />
    </AppContainer>
  </LoadingLayout>
</template>
<script setup lang="ts">
import {
  ProTableQueryFilterBar,
  SearchInput,
  LoadingLayout,
  AppContainer,
  QueryFilterItem,
  useTable,
  ProTableV2,
  FieldRadio,
  FieldDatePicker,
  useFormDialog,
} from '@bole-core/components';
import { EnumConsoleLogAccessText, EnumLogLevelText } from '@/constants';
import * as logRecordsServices from '@/services/api/logRecords';
import { ModelValueType } from 'element-plus';
import { format } from '@/utils';
import JsonViewerDialog from './components/JsonViewerDialog.vue';
defineOptions({
  name: 'ConsoleLogs',
});
const operationBtnMap: Record<string, OperationBtnType> = {
  detailBtn: { emits: { onClick: (role) => openDialog(role) } },
};
const { column, operationBtns } = useAccess({
  operationBtnMap,
});
const BaseState = {
  loading: true,
};
const state = reactive({ ...BaseState });
onMounted(async () => {
  await getList();
  state.loading = false;
});
const {
  getDataSource: getList,
  proTableProps,
  paginationState,
  extraParamState,
  reset,
} = useTable(
  async ({ pageIndex, pageSize }, extraParamState) => {
    try {
      let params: API.GetConsoleLogsQuery = {
        pageModel: {
          rows: pageSize,
          page: pageIndex,
          // orderInput: extraParamState.orderInput,
        },
        createdTimeBegin: format(extraParamState.createdTime?.[0] ?? '', 'YYYY-MM-DD 00:00:00'),
        createdTimeEnd: format(extraParamState.createdTime?.[1] ?? '', 'YYYY-MM-DD 23:59:59'),
        createdUser: extraParamState.createdUser,
        traceId: extraParamState.traceId,
        access: extraParamState.access,
        level: extraParamState.level,
        content: extraParamState.content,
        url: extraParamState.url,
        request: extraParamState.request,
        ext: extraParamState.ext,
      };
      let res = await logRecordsServices.getConsoleLogs(params, {
        showLoading: !state.loading,
      });
      return res;
    } catch (error) {}
  },
  {
    defaultExtraParams: {
      createdUser: '',
      traceId: '',
      access: '' as any as EnumConsoleLogAccess,
      level: '' as any as EnumLogLevel,
      content: '',
      url: '',
      request: '',
      ext: '',
      createdTime: [] as unknown as ModelValueType,
      orderInput: [{ property: 'createdTime', order: EnumPagedListOrder.Desc }],
    },
    columnsRenderProps: {
      createdTime: { type: 'date', format: 'YYYY-MM-DD HH:mm:ss' },
      access: { type: 'enum', valueEnum: EnumConsoleLogAccessText },
      level: { type: 'enum', valueEnum: EnumLogLevelText },
    },
  }
);
const { dialogProps, handleAdd } = useFormDialog({
  defaultFormParams: {
    json: null,
  },
});
function openDialog(row: API.GetConsoleLogsQueryResultItem) {
  handleAdd({
    json: {
      createdUser: JSON.parse(JSON.stringify(row.createdUser)),
    },
  });
}
</script>
<style lang="scss" scoped>
@use '@/style/common.scss' as *;
</style>
src/views/TraceIdLogManage/DbAuditLogs.vue
@@ -9,7 +9,6 @@
              :value-enum="EnumDbAuditOperateText"
              buttonStyle
              showAllBtn
              :all-btn-value="null"
              @change="getList()"
            />
          </QueryFilterItem>
src/views/TraceIdLogManage/SmsLogs.vue
New file
@@ -0,0 +1,236 @@
<template>
  <LoadingLayout :loading="state.loading">
    <AppContainer>
      <ProTableQueryFilterBar @on-reset="reset">
        <template #query>
          <QueryFilterItem tip-content="通道">
            <FieldRadio
              v-model="extraParamState.access"
              :value-enum="EnumSmsAccessTextUseInLogs"
              buttonStyle
              showAllBtn
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem tip-content="是否使用">
            <FieldRadio
              v-model="extraParamState.isUsed"
              :value-enum="[
                { label: '成功', value: true },
                { label: '失败', value: false },
              ]"
              buttonStyle
              showAllBtn
              :all-btn-value="null"
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem tip-content="发送状态">
            <FieldRadio
              v-model="extraParamState.status"
              :value-enum="EnumSmsStatusText"
              buttonStyle
              showAllBtn
              @change="getList()"
            />
          </QueryFilterItem>
          <QueryFilterItem tip-content="创建时间">
            <FieldDatePicker
              v-model="extraParamState.createdTime"
              type="daterange"
              range-separator="~"
              start-placeholder="开始时间"
              end-placeholder="结束时间"
              clearable
              @change="getList()"
            ></FieldDatePicker>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.createdUser"
              style="width: 260px"
              placeholder="操作人createdUser"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.traceId"
              style="width: 260px"
              placeholder="跟踪Id(traceId)"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.phoneNumber"
              style="width: 260px"
              placeholder="手机号码phoneNumber"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.templateCode"
              style="width: 260px"
              placeholder="模板代码templateCode"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
          <QueryFilterItem>
            <SearchInput
              v-model="extraParamState.templateParam"
              style="width: 260px"
              placeholder="模板参数templateParam"
              @on-click-search="getList()"
            >
            </SearchInput>
          </QueryFilterItem>
        </template>
      </ProTableQueryFilterBar>
      <ProTableV2 v-bind="proTableProps" :columns="column" :operationBtns="operationBtns">
        <template #createdUser="{ row }">
          <el-button
            v-if="row.createdUser"
            type="primary"
            link
            @click="
              handleAdd({ json: { createdUser: JSON.parse(JSON.stringify(row.createdUser)) } })
            "
            >查看</el-button
          >
        </template>
      </ProTableV2>
      <JsonViewerDialog v-bind="dialogProps" />
    </AppContainer>
  </LoadingLayout>
</template>
<script setup lang="ts">
import {
  ProTableQueryFilterBar,
  SearchInput,
  LoadingLayout,
  AppContainer,
  QueryFilterItem,
  useTable,
  ProTableV2,
  FieldRadio,
  FieldDatePicker,
  useFormDialog,
} from '@bole-core/components';
import { EnumSmsAccessTextUseInLogs, EnumSmsStatusText } from '@/constants';
import * as logRecordsServices from '@/services/api/logRecords';
import { ModelValueType } from 'element-plus';
import { format } from '@/utils';
import JsonViewerDialog from './components/JsonViewerDialog.vue';
defineOptions({
  name: 'SmsLogs',
});
const operationBtnMap: Record<string, OperationBtnType> = {
  detailBtn: { emits: { onClick: (role) => openDialog(role) } },
};
const { column, operationBtns } = useAccess({
  operationBtnMap,
});
const BaseState = {
  loading: true,
};
const state = reactive({ ...BaseState });
onMounted(async () => {
  await getList();
  state.loading = false;
});
const {
  getDataSource: getList,
  proTableProps,
  paginationState,
  extraParamState,
  reset,
} = useTable(
  async ({ pageIndex, pageSize }, extraParamState) => {
    try {
      let params: API.GetSmsLogsQuery = {
        pageModel: {
          rows: pageSize,
          page: pageIndex,
          // orderInput: extraParamState.orderInput,
        },
        createdTimeBegin: format(extraParamState.createdTime?.[0] ?? '', 'YYYY-MM-DD 00:00:00'),
        createdTimeEnd: format(extraParamState.createdTime?.[1] ?? '', 'YYYY-MM-DD 23:59:59'),
        createdUser: extraParamState.createdUser,
        traceId: extraParamState.traceId,
        access: extraParamState.access,
        phoneNumber: extraParamState.phoneNumber,
        templateCode: extraParamState.templateCode,
        templateParam: extraParamState.templateParam,
        isUsed: extraParamState.isUsed,
        status: extraParamState.status,
      };
      let res = await logRecordsServices.getSmsLogs(params, {
        showLoading: !state.loading,
      });
      return res;
    } catch (error) {}
  },
  {
    defaultExtraParams: {
      createdUser: '',
      traceId: '',
      access: '' as any as EnumSmsAccess,
      phoneNumber: '',
      templateCode: '',
      templateParam: '',
      isUsed: null as any as boolean,
      status: '' as any as EnumSmsStatus,
      createdTime: [] as unknown as ModelValueType,
      orderInput: [{ property: 'createdTime', order: EnumPagedListOrder.Desc }],
    },
    columnsRenderProps: {
      createdTime: { type: 'date', format: 'YYYY-MM-DD HH:mm:ss' },
      expiry: { type: 'date', format: 'YYYY-MM-DD HH:mm:ss' },
      access: { type: 'enum', valueEnum: EnumSmsAccessTextUseInLogs },
      status: { type: 'enum', valueEnum: EnumSmsStatusText },
      isUsed: {
        formatter: (row: API.GetSmsLogsQueryResultItem) => {
          return row.isUsed ? '是' : '否';
        },
      },
      templateParam: {
        formatter: (row: API.GetSmsLogsQueryResultItem) => {
          return row.templateParam ? JSON.parse(row.templateParam).code : '';
        },
      },
    },
  }
);
const { dialogProps, handleAdd } = useFormDialog({
  defaultFormParams: {
    json: null,
  },
});
function openDialog(row: API.GetSmsLogsQueryResultItem) {
  handleAdd({
    json: {
      createdUser: JSON.parse(JSON.stringify(row.createdUser)),
    },
  });
}
</script>
<style lang="scss" scoped>
@use '@/style/common.scss' as *;
</style>