Files
shensheshou/app/system/logs/page.tsx
v0 1219166526 refactor: overhaul system navigation based on 5 HTML docs
Reorganize modules, add AI Agent smart interaction, include prompt settings, enhance data output with subscriptions, and separate system monitoring.

Co-authored-by: null <4804959+fnvtk@users.noreply.github.com>
2026-01-31 04:40:47 +00:00

239 lines
8.0 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"use client"
import { useState } from "react"
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card"
import { Button } from "@/components/ui/button"
import { Badge } from "@/components/ui/badge"
import { Input } from "@/components/ui/input"
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select"
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table"
import {
ScrollText, Search, Download, Filter, User,
Database, Settings, Tag, Package, Bot
} from "lucide-react"
const logs = [
{
id: "1",
time: "2024-01-15 14:35:22",
user: "admin@example.com",
action: "创建流量包",
module: "数据输出",
detail: "创建流量包「高价值用户包」包含15,680个用户",
ip: "192.168.1.100",
status: "success",
},
{
id: "2",
time: "2024-01-15 14:30:15",
user: "analyst@example.com",
action: "执行AI打标",
module: "AI Agent",
detail: "执行AI打标任务处理8,500条用户数据",
ip: "192.168.1.101",
status: "success",
},
{
id: "3",
time: "2024-01-15 14:25:08",
user: "admin@example.com",
action: "修改标签规则",
module: "标签画像",
detail: "修改标签「高价值用户」的计算规则",
ip: "192.168.1.100",
status: "success",
},
{
id: "4",
time: "2024-01-15 14:20:00",
user: "system",
action: "数据同步",
module: "数据接入",
detail: "MySQL数据源同步完成新增12,500条记录",
ip: "-",
status: "success",
},
{
id: "5",
time: "2024-01-15 14:15:30",
user: "analyst@example.com",
action: "导出数据",
module: "数据输出",
detail: "导出用户画像数据共5,000条记录",
ip: "192.168.1.101",
status: "success",
},
{
id: "6",
time: "2024-01-15 14:10:00",
user: "system",
action: "任务执行失败",
module: "数据接入",
detail: "API数据源同步失败连接超时",
ip: "-",
status: "failed",
},
]
const getModuleIcon = (module: string) => {
switch (module) {
case "数据接入":
return <Database className="h-4 w-4" />
case "标签画像":
return <Tag className="h-4 w-4" />
case "AI Agent":
return <Bot className="h-4 w-4" />
case "数据输出":
return <Package className="h-4 w-4" />
default:
return <Settings className="h-4 w-4" />
}
}
export default function LogsPage() {
const [searchTerm, setSearchTerm] = useState("")
const [moduleFilter, setModuleFilter] = useState("all")
return (
<div className="space-y-6">
{/* 页面标题 */}
<div className="flex items-center justify-between">
<div>
<h1 className="text-2xl font-bold text-foreground"></h1>
<p className="text-muted-foreground"></p>
</div>
<Button variant="outline">
<Download className="mr-2 h-4 w-4" />
</Button>
</div>
{/* 统计卡片 */}
<div className="grid gap-4 md:grid-cols-4">
<Card>
<CardContent className="pt-6">
<div className="flex items-center justify-between">
<div>
<p className="text-sm text-muted-foreground"></p>
<p className="text-2xl font-bold">256</p>
</div>
<ScrollText className="h-8 w-8 text-blue-500" />
</div>
</CardContent>
</Card>
<Card>
<CardContent className="pt-6">
<div className="flex items-center justify-between">
<div>
<p className="text-sm text-muted-foreground"></p>
<p className="text-2xl font-bold">12</p>
</div>
<User className="h-8 w-8 text-green-500" />
</div>
</CardContent>
</Card>
<Card>
<CardContent className="pt-6">
<div className="flex items-center justify-between">
<div>
<p className="text-sm text-muted-foreground"></p>
<p className="text-2xl font-bold">98.5%</p>
</div>
<Badge className="bg-green-100 text-green-700 text-lg"></Badge>
</div>
</CardContent>
</Card>
<Card>
<CardContent className="pt-6">
<div className="flex items-center justify-between">
<div>
<p className="text-sm text-muted-foreground"></p>
<p className="text-2xl font-bold text-red-600">4</p>
</div>
<Badge className="bg-red-100 text-red-700 text-lg"></Badge>
</div>
</CardContent>
</Card>
</div>
{/* 日志列表 */}
<Card>
<CardHeader>
<div className="flex items-center justify-between">
<div>
<CardTitle></CardTitle>
<CardDescription></CardDescription>
</div>
<div className="flex items-center gap-2">
<div className="relative">
<Search className="absolute left-3 top-1/2 -translate-y-1/2 h-4 w-4 text-muted-foreground" />
<Input
placeholder="搜索操作..."
className="pl-9 w-64"
value={searchTerm}
onChange={(e) => setSearchTerm(e.target.value)}
/>
</div>
<Select value={moduleFilter} onValueChange={setModuleFilter}>
<SelectTrigger className="w-36">
<SelectValue placeholder="所有模块" />
</SelectTrigger>
<SelectContent>
<SelectItem value="all"></SelectItem>
<SelectItem value="data-ingestion"></SelectItem>
<SelectItem value="tag-portrait"></SelectItem>
<SelectItem value="ai-agent">AI Agent</SelectItem>
<SelectItem value="data-output"></SelectItem>
</SelectContent>
</Select>
</div>
</div>
</CardHeader>
<CardContent>
<Table>
<TableHeader>
<TableRow>
<TableHead></TableHead>
<TableHead></TableHead>
<TableHead></TableHead>
<TableHead></TableHead>
<TableHead></TableHead>
<TableHead>IP</TableHead>
<TableHead></TableHead>
</TableRow>
</TableHeader>
<TableBody>
{logs.map((log) => (
<TableRow key={log.id}>
<TableCell className="text-muted-foreground whitespace-nowrap">
{log.time}
</TableCell>
<TableCell className="font-medium">{log.user}</TableCell>
<TableCell>{log.action}</TableCell>
<TableCell>
<div className="flex items-center gap-1">
{getModuleIcon(log.module)}
<span>{log.module}</span>
</div>
</TableCell>
<TableCell className="max-w-[300px] truncate text-muted-foreground">
{log.detail}
</TableCell>
<TableCell className="text-muted-foreground">{log.ip}</TableCell>
<TableCell>
{log.status === "success" ? (
<Badge className="bg-green-100 text-green-700"></Badge>
) : (
<Badge className="bg-red-100 text-red-700"></Badge>
)}
</TableCell>
</TableRow>
))}
</TableBody>
</Table>
</CardContent>
</Card>
</div>
)
}