import dayjs from 'dayjs'; export type LogTabKey = 'login-log' | 'operate-log' | 'api-access-log' | 'api-error-log'; export interface LogTabOption { name: LogTabKey; label: string; description: string; queryPermission: string; exportPermission: string; } export interface LogDetailField { label: string; key?: string; span?: number; type?: 'text' | 'datetime' | 'dict' | 'multiline'; dictCode?: string; formatter?: (detail: Record) => string; } export interface LogDetailSection { title: string; fields: LogDetailField[]; } export const LogPermission = { LoginQuery: 'system:login-log:query', LoginExport: 'system:login-log:export', OperateQuery: 'system:operate-log:query', OperateExport: 'system:operate-log:export', ApiAccessQuery: 'system:api-access-log:query', ApiAccessExport: 'system:api-access-log:export', ApiErrorQuery: 'system:api-error-log:query', ApiErrorExport: 'system:api-error-log:export' } as const; export const LOG_TABS: LogTabOption[] = [ { name: 'login-log', label: '登录日志', description: '查看系统登录行为、登录结果与登录时间。', queryPermission: LogPermission.LoginQuery, exportPermission: LogPermission.LoginExport }, { name: 'operate-log', label: '操作日志', description: '查看系统操作轨迹、请求地址与业务编号。', queryPermission: LogPermission.OperateQuery, exportPermission: LogPermission.OperateExport }, { name: 'api-access-log', label: 'API访问日志', description: '查看接口访问结果、执行时长与请求链路。', queryPermission: LogPermission.ApiAccessQuery, exportPermission: LogPermission.ApiAccessExport }, { name: 'api-error-log', label: 'API错误日志', description: '查看接口异常、处理状态与错误上下文。', queryPermission: LogPermission.ApiErrorQuery, exportPermission: LogPermission.ApiErrorExport } ]; export function formatDateTime(value?: string | null) { if (!value) return '--'; const target = dayjs(value); return target.isValid() ? target.format('YYYY-MM-DD HH:mm:ss') : value; } export function formatText(value: unknown) { if (value === null || value === undefined || value === '') return '--'; return String(value); } export function formatDuration(value: unknown) { if (value === null || value === undefined || value === '') return '--'; const duration = Number(value); return Number.isFinite(duration) ? `${duration} ms` : String(value); } export function formatMultilineText(value: unknown) { if (value === null || value === undefined || value === '') return '--'; const text = String(value); const normalized = text.trim(); if (!normalized) return '--'; if ( (normalized.startsWith('{') && normalized.endsWith('}')) || (normalized.startsWith('[') && normalized.endsWith(']')) ) { try { return JSON.stringify(JSON.parse(normalized), null, 2); } catch { return text; } } return text; } export function downloadBlob(blob: Blob, fileName: string) { const url = URL.createObjectURL(blob); const link = document.createElement('a'); link.href = url; link.download = fileName; link.click(); URL.revokeObjectURL(url); } export function getLogExportFileName(label: string) { return `${label}_${dayjs().format('YYYY-MM-DD')}.xls`; }