From 1f4656bc4c1a5586fcd28d5ba8d760d8e508335d Mon Sep 17 00:00:00 2001 From: Cursor Agent Date: Thu, 23 Apr 2026 15:08:02 +0000 Subject: [PATCH] feat(ui): guardrails/pii_components to shadcn - antd Typography/Select/Button/Checkbox/Tooltip/Tag + @ant-design Close/EyeInvisible/Stop/Filter \u2192 shadcn Badge/Button/Checkbox/ Select/Tooltip + lucide Ban/EyeOff/Filter/Info/X. - CategoryFilter keeps antd Select mode='multiple' \u2014 shadcn Select doesn't support multiple. Blue category badge in PiiEntityList preserved as categorical (file added to .eslintrc.json overrides). - Quick Action buttons use destructive/primary outline variants for Mask/Block/Unselect respectively. Gates: TS \u2713 | Build \u2713. Co-authored-by: yuneng-jiang --- ui/litellm-dashboard/.eslintrc.json | 1 + .../components/guardrails/pii_components.tsx | 224 +++++++++++------- 2 files changed, 133 insertions(+), 92 deletions(-) diff --git a/ui/litellm-dashboard/.eslintrc.json b/ui/litellm-dashboard/.eslintrc.json index 61f76577b83..1a28d1a650e 100644 --- a/ui/litellm-dashboard/.eslintrc.json +++ b/ui/litellm-dashboard/.eslintrc.json @@ -70,6 +70,7 @@ "src/components/mcp_tools/mcp_server_cost_config.tsx", "src/components/view_logs/GuardrailViewer/CompliancePanel.tsx", "src/components/view_logs/LogDetailsDrawer/DrawerHeader.tsx", + "src/components/guardrails/pii_components.tsx", "src/components/prompts/prompt_editor_view/PromptEditorHeader.tsx", "src/components/prompts/prompt_editor_view/VersionHistorySidePanel.tsx", "src/app/(dashboard)/teams/components/TeamsTable/ModelsCell.tsx", diff --git a/ui/litellm-dashboard/src/components/guardrails/pii_components.tsx b/ui/litellm-dashboard/src/components/guardrails/pii_components.tsx index 3365e866aa9..bb2f29fe547 100644 --- a/ui/litellm-dashboard/src/components/guardrails/pii_components.tsx +++ b/ui/litellm-dashboard/src/components/guardrails/pii_components.tsx @@ -1,12 +1,27 @@ import React from "react"; -import { Typography, Select, Button, Checkbox, Tooltip, Tag } from "antd"; -import { CloseOutlined, EyeInvisibleOutlined, StopOutlined, FilterOutlined } from "@ant-design/icons"; +import { Badge } from "@/components/ui/badge"; +import { Button } from "@/components/ui/button"; +import { Checkbox } from "@/components/ui/checkbox"; +import { + Select, + SelectContent, + SelectItem, + SelectTrigger, + SelectValue, +} from "@/components/ui/select"; +import { + Tooltip, + TooltipContent, + TooltipProvider, + TooltipTrigger, +} from "@/components/ui/tooltip"; +import { cn } from "@/lib/utils"; +import { Ban, Eye, EyeOff, Filter, Info, X } from "lucide-react"; +import { Select as AntSelect } from "antd"; import { PiiEntityCategory } from "./types"; -const { Text } = Typography; -const { Option } = Select; +const { Option } = AntSelect; -// Helper functions export const formatEntityName = (name: string) => { return name.replace(/_/g, " "); }; @@ -14,29 +29,35 @@ export const formatEntityName = (name: string) => { export const getActionIcon = (action: string) => { switch (action) { case "MASK": - return ; + return ; case "BLOCK": - return ; + return ; default: return null; } }; -// CategoryFilter component +// CategoryFilter export interface CategoryFilterProps { categories: PiiEntityCategory[]; selectedCategories: string[]; onChange: (categories: string[]) => void; } -export const CategoryFilter: React.FC = ({ categories, selectedCategories, onChange }) => { +export const CategoryFilter: React.FC = ({ + categories, + selectedCategories, + onChange, +}) => { return (
- - Filter by category + + + Filter by category +
- +
); }; -// QuickActions component +// QuickActions export interface QuickActionsProps { onSelectAll: (action: string) => void; onUnselectAll: () => void; hasSelectedEntities: boolean; } -export const QuickActions: React.FC = ({ onSelectAll, onUnselectAll, hasSelectedEntities }) => { +export const QuickActions: React.FC = ({ + onSelectAll, + onUnselectAll, + hasSelectedEntities, +}) => { return ( -
+
- + Quick Actions - - -
ⓘ
-
+ + + + + + + + Apply action to all PII types at once + + +
); }; -// PiiEntityList component +// PiiEntityList export interface PiiEntityListProps { entities: string[]; selectedEntities: string[]; @@ -138,62 +161,79 @@ export const PiiEntityList: React.FC = ({ entityToCategoryMap, }) => { return ( -
-
- - PII Type - - - Action - +
+
+ PII Type + Action
{entities.length === 0 ? ( -
No PII types match your filter criteria
+
+ No PII types match your filter criteria +
) : ( - entities.map((entity) => ( -
-
- onEntitySelect(entity)} - className="mr-3" - /> - - {formatEntityName(entity)} - - {entityToCategoryMap.get(entity) && ( - - {entityToCategoryMap.get(entity)} - + entities.map((entity) => { + const isSelected = selectedEntities.includes(entity); + return ( +
+ +
+ +
-
- -
-
- )) + ); + }) )}