Files
aiops/frontend/src/components/system/SystemRolesTab.tsx
T
attacker a7e2351ad2 feat: 定时任务编辑入口全栈打通 + 修复ApprovalFlow编译错误 + 完成大文件拆分重构
- CronJobManager: 编辑按钮接通 onClick → openEdit(job),弹出编辑对话框预填数据,
  复用新建/编辑共用 Dialog(editingId 区分模式),标题/按钮文案动态切换,
  保存时根据 editingId 调用 createJob 或 updateJob — 消除占位按钮
- ApprovalFlow: 修复 API 方法名不匹配导致 tsc -b 编译失败
  (getInstances→getProcesses, getMyApprovals→getProcesses({status:'pending'}),
   approveInstance→approveProcess, rejectInstance→rejectProcess)
  + 添加 ApprovalFlowManager 导出别名兼容 App.tsx 导入
- 合并已完成的大文件拆分重构: automation.go→automation_cron/script/playbook,
  ldap.go→ldap_ou/ldap_users, server.go→cloud_accounts/domain/platform/region,
  user.go→user_admin; 前端 Dashboard/K8s/Server/Approval/Monitor 子组件拆分
  // Logan.Li
2026-06-15 01:09:49 +08:00

73 lines
2.9 KiB
TypeScript

import { Card, CardContent, CardHeader, CardTitle, CardDescription } from '@/components/ui/card';
import { Button } from '@/components/ui/button';
import { Badge } from '@/components/ui/badge';
import { Plus, Shield, Edit, Eye } from 'lucide-react';
import { roles } from '@/mocks/data';
import type { Role } from '@/types';
interface SystemRolesTabProps {
selectedRole: Role | null;
setSelectedRole: (role: Role | null) => void;
}
export function SystemRolesTab({ selectedRole, setSelectedRole }: SystemRolesTabProps) {
return (
<>
<div className="flex items-center justify-end">
<Button className="bg-blue-600 hover:bg-blue-700 text-white">
<Plus className="h-4 w-4 mr-2" />
新建角色
</Button>
</div>
<div className="grid grid-cols-1 lg:grid-cols-2 gap-4">
{roles.map((role) => (
<Card key={role.id} className="bg-slate-900 border-slate-800">
<CardHeader className="pb-2">
<div className="flex items-start justify-between">
<div className="flex items-center gap-3">
<div className="w-10 h-10 rounded-lg bg-purple-500/10 flex items-center justify-center">
<Shield className="h-5 w-5 text-purple-400" />
</div>
<div>
<CardTitle className="text-base text-slate-100">{role.name}</CardTitle>
<CardDescription className="text-slate-500">{role.code}</CardDescription>
</div>
</div>
<div className="flex items-center gap-1">
<Button
variant="ghost"
size="icon"
className="h-8 w-8 text-slate-400 hover:text-slate-100"
onClick={() => setSelectedRole(role)}
>
<Eye className="h-4 w-4" />
</Button>
<Button variant="ghost" size="icon" className="h-8 w-8 text-slate-400 hover:text-slate-100">
<Edit className="h-4 w-4" />
</Button>
</div>
</div>
</CardHeader>
<CardContent>
<p className="text-sm text-slate-400 mb-3">{role.description}</p>
<div className="flex flex-wrap gap-1">
{role.permissions.slice(0, 5).map((permission) => (
<Badge key={permission} variant="outline" className="border-slate-700 text-slate-400 text-xs">
{permission}
</Badge>
))}
{role.permissions.length > 5 && (
<Badge variant="outline" className="border-slate-700 text-slate-400 text-xs">
+{role.permissions.length - 5}
</Badge>
)}
</div>
</CardContent>
</Card>
))}
</div>
</>
);
}