diff --git a/ui/litellm-dashboard/src/components/logging_settings_view.tsx b/ui/litellm-dashboard/src/components/logging_settings_view.tsx new file mode 100644 index 00000000000..48344972c88 --- /dev/null +++ b/ui/litellm-dashboard/src/components/logging_settings_view.tsx @@ -0,0 +1,138 @@ +import React from "react"; +import { Text, Badge } from "@tremor/react"; +import { CogIcon } from "@heroicons/react/outline"; +import { callbackInfo, callback_map } from "./callback_info_helpers"; + +interface LoggingConfig { + callback_name: string; + callback_type: string; + callback_vars: Record; +} + +interface LoggingSettingsViewProps { + loggingConfigs?: LoggingConfig[]; + variant?: "card" | "inline"; + className?: string; +} + +export function LoggingSettingsView({ + loggingConfigs = [], + variant = "card", + className = "" +}: LoggingSettingsViewProps) { + const getLoggingDisplayName = (callbackName: string) => { + // Find the display name for the callback + const callbackDisplayName = Object.entries(callback_map).find( + ([_, value]) => value === callbackName + )?.[0]; + return callbackDisplayName || callbackName; + }; + + const getEventTypeColor = (eventType: string) => { + switch (eventType) { + case "success": + return "green"; + case "failure": + return "red"; + case "success_and_failure": + return "blue"; + default: + return "gray"; + } + }; + + const getEventTypeLabel = (eventType: string) => { + switch (eventType) { + case "success": + return "Success Only"; + case "failure": + return "Failure Only"; + case "success_and_failure": + return "Success & Failure"; + default: + return eventType; + } + }; + + const content = ( +
+
+ + Logging Integrations + + {loggingConfigs.length} + +
+ + {loggingConfigs.length > 0 ? ( +
+ {loggingConfigs.map((config, index) => { + const displayName = getLoggingDisplayName(config.callback_name); + const logoUrl = callbackInfo[displayName]?.logo; + + return ( +
+
+ {logoUrl ? ( + {displayName} + ) : ( + + )} +
+ {displayName} + + {Object.keys(config.callback_vars).length} parameters configured + +
+
+ + {getEventTypeLabel(config.callback_type)} + +
+ ); + })} +
+ ) : ( +
+ + No logging integrations configured +
+ )} +
+ ); + + if (variant === "card") { + return ( +
+
+
+ Logging Settings + + Active logging integrations for this team + +
+
+ {content} +
+ ); + } + + return ( +
+ Logging Settings + {content} +
+ ); +} + +export default LoggingSettingsView; \ No newline at end of file diff --git a/ui/litellm-dashboard/src/components/team/EditLoggingSettings.tsx b/ui/litellm-dashboard/src/components/team/EditLoggingSettings.tsx new file mode 100644 index 00000000000..13bc8595146 --- /dev/null +++ b/ui/litellm-dashboard/src/components/team/EditLoggingSettings.tsx @@ -0,0 +1,17 @@ +import React from 'react'; +import LoggingSettings from './LoggingSettings'; + +interface EditLoggingSettingsProps { + value: any[]; + onChange: (value: any[]) => void; +} + +/** + * Wrapper component around LoggingSettings used for editing + * a team's logging integrations. + */ +const EditLoggingSettings: React.FC = ({ value, onChange }) => { + return ; +}; + +export default EditLoggingSettings; diff --git a/ui/litellm-dashboard/src/components/team/team_info.tsx b/ui/litellm-dashboard/src/components/team/team_info.tsx index 16d38f247e8..05f179fa567 100644 --- a/ui/litellm-dashboard/src/components/team/team_info.tsx +++ b/ui/litellm-dashboard/src/components/team/team_info.tsx @@ -38,6 +38,8 @@ import VectorStoreSelector from "../vector_store_management/VectorStoreSelector" import MCPServerSelector from "../mcp_server_management/MCPServerSelector"; import PremiumVectorStoreSelector from "../common_components/PremiumVectorStoreSelector"; import { formatNumberWithCommas } from "@/utils/dataUtils"; +import EditLoggingSettings from "./EditLoggingSettings"; +import LoggingSettingsView from "../logging_settings_view"; export interface TeamMembership { user_id: string; @@ -252,7 +254,8 @@ const TeamInfoView: React.FC = ({ budget_duration: values.budget_duration, metadata: { ...parsedMetadata, - guardrails: values.guardrails || [] + guardrails: values.guardrails || [], + logging: values.logging_settings || [] }, organization_id: values.organization_id, }; @@ -366,6 +369,11 @@ const TeamInfoView: React.FC = ({ variant="card" accessToken={accessToken} /> + + @@ -419,7 +427,10 @@ const TeamInfoView: React.FC = ({ max_budget: info.max_budget, budget_duration: info.budget_duration, guardrails: info.metadata?.guardrails || [], - metadata: info.metadata ? JSON.stringify(info.metadata, null, 2) : "", + metadata: info.metadata + ? JSON.stringify((({ logging, ...rest }) => rest)(info.metadata), null, 2) + : "", + logging_settings: info.metadata?.logging || [], organization_id: info.organization_id, vector_stores: info.object_permission?.vector_stores || [], mcp_servers: info.object_permission?.mcp_servers || [] @@ -525,11 +536,18 @@ const TeamInfoView: React.FC = ({ placeholder="Select MCP servers" /> - + + form.setFieldValue('logging_settings', values)} + /> + + + @@ -606,6 +624,12 @@ const TeamInfoView: React.FC = ({ className="pt-4 border-t border-gray-200" accessToken={accessToken} /> + + )}