// ============================================================ // 操作日志 // ============================================================ import { useState } from 'react' import { useQuery } from '@tanstack/react-query' import { Tag, Select, Typography } from 'antd' import type { ProColumns } from '@ant-design/pro-components' import { ProTable } from '@ant-design/pro-components' import { logService } from '@/services/logs' import type { OperationLog } from '@/types' const { Title } = Typography const actionLabels: Record = { login: '登录', logout: '登出', create_account: '创建账号', update_account: '更新账号', delete_account: '删除账号', create_provider: '创建服务商', update_provider: '更新服务商', delete_provider: '删除服务商', create_model: '创建模型', update_model: '更新模型', delete_model: '删除模型', create_token: '创建密钥', revoke_token: '撤销密钥', update_config: '更新配置', create_prompt: '创建提示词', update_prompt: '更新提示词', archive_prompt: '归档提示词', desktop_audit: '桌面端审计', } const actionColors: Record = { login: 'green', logout: 'default', create_account: 'blue', update_account: 'orange', delete_account: 'red', create_provider: 'blue', update_provider: 'orange', delete_provider: 'red', create_model: 'blue', update_model: 'orange', delete_model: 'red', create_token: 'blue', revoke_token: 'red', update_config: 'orange', create_prompt: 'blue', update_prompt: 'orange', archive_prompt: 'red', desktop_audit: 'default', } const actionOptions = Object.entries(actionLabels).map(([value, label]) => ({ value, label })) export default function Logs() { const [page, setPage] = useState(1) const [actionFilter, setActionFilter] = useState(undefined) const { data, isLoading } = useQuery({ queryKey: ['logs', page, actionFilter], queryFn: ({ signal }) => logService.list({ page, page_size: 20, action: actionFilter }, signal), }) const columns: ProColumns[] = [ { title: '操作类型', dataIndex: 'action', width: 140, render: (_, r) => ( {actionLabels[r.action] || r.action} ), }, { title: '目标类型', dataIndex: 'target_type', width: 100, render: (_, r) => r.target_type || '-' }, { title: '目标 ID', dataIndex: 'target_id', width: 120, render: (_, r) => r.target_id ? {r.target_id.substring(0, 8)}... : '-' }, { title: '详情', dataIndex: 'details', width: 250, ellipsis: true, render: (_, r) => { if (!r.details) return '-' if (typeof r.details === 'string') return r.details return JSON.stringify(r.details) }, }, { title: 'IP 地址', dataIndex: 'ip_address', width: 130, render: (_, r) => {r.ip_address || '-'} }, { title: '时间', dataIndex: 'created_at', width: 180, render: (_, r) => new Date(r.created_at).toLocaleString('zh-CN'), }, ] return (
操作日志