mukaddamzaid commited on
Commit
d83197f
·
1 Parent(s): 0c91a71

feat: enhance StatusIndicator with Tooltip support

Browse files

- Updated StatusIndicator component to utilize Tooltip for displaying additional hover information.
- Introduced hoverInfo prop to provide context for server statuses, including sandbox URLs and error messages.
- Refactored status rendering logic for improved clarity and maintainability.

Files changed (1) hide show
  1. components/mcp-server-manager.tsx +80 -39
components/mcp-server-manager.tsx CHANGED
@@ -37,6 +37,12 @@ import {
37
  AccordionTrigger
38
  } from "./ui/accordion";
39
  import { KeyValuePair, MCPServer, ServerStatus, useMCP } from "@/lib/context/mcp-context";
 
 
 
 
 
 
40
 
41
  // Default template for a new MCP server
42
  const INITIAL_NEW_SERVER: Omit<MCPServer, 'id'> = {
@@ -79,42 +85,67 @@ const maskValue = (value: string): string => {
79
  return value.substring(0, 3) + '•'.repeat(Math.min(10, value.length - 4)) + value.substring(value.length - 1);
80
  };
81
 
82
- const StatusIndicator = ({ status, onClick }: { status?: ServerStatus, onClick?: () => void }) => {
 
 
 
 
 
83
  const isClickable = !!onClick;
 
84
 
85
- const className = `flex-shrink-0 flex items-center gap-1 ${isClickable ? 'cursor-pointer hover:underline' : ''}`;
86
 
87
- switch (status) {
88
- case 'connected':
89
- return (
90
- <div className={className} onClick={onClick}>
91
- <div className="w-2 h-2 rounded-full bg-green-500 animate-pulse" />
92
- <span className="text-xs text-green-500">Connected</span>
93
- </div>
94
- );
95
- case 'connecting':
96
- return (
97
- <div className={className} onClick={onClick}>
98
- <RefreshCw className="w-3 h-3 text-amber-500 animate-spin" />
99
- <span className="text-xs text-amber-500">Connecting</span>
100
- </div>
101
- );
102
- case 'error':
103
- return (
104
- <div className={className} onClick={onClick}>
105
- <AlertTriangle className="w-3 h-3 text-red-500" />
106
- <span className="text-xs text-red-500">Error</span>
107
- </div>
108
- );
109
- case 'disconnected':
110
- default:
111
- return (
112
- <div className={className} onClick={onClick}>
113
- <div className="w-2 h-2 rounded-full bg-gray-400" />
114
- <span className="text-xs text-muted-foreground">Disconnected</span>
115
- </div>
116
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
117
  }
 
 
 
118
  };
119
 
120
  export const MCPServerManager = ({
@@ -466,18 +497,27 @@ export const MCPServerManager = ({
466
 
467
  // UI element to display the correct server URL
468
  const getServerDisplayUrl = (server: MCPServer): string => {
469
- // For stdio servers with active sandbox, show the sandbox URL
470
- if (server.type === 'stdio' && server.sandboxUrl &&
471
- (server.status === 'connected' || server.status === 'connecting')) {
472
- return server.sandboxUrl;
473
- }
474
-
475
- // Otherwise show the configured URL or command
476
  return server.type === 'sse'
477
  ? server.url
478
  : `${server.command} ${server.args?.join(' ')}`;
479
  };
480
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
481
  return (
482
  <Dialog open={open} onOpenChange={onOpenChange}>
483
  <DialogContent className="sm:max-w-[480px] max-h-[85vh] overflow-hidden flex flex-col">
@@ -554,6 +594,7 @@ export const MCPServerManager = ({
554
  <StatusIndicator
555
  status={server.status}
556
  onClick={() => server.errorMessage && toast.error(server.errorMessage)}
 
557
  />
558
 
559
  {/* Server actions */}
 
37
  AccordionTrigger
38
  } from "./ui/accordion";
39
  import { KeyValuePair, MCPServer, ServerStatus, useMCP } from "@/lib/context/mcp-context";
40
+ import {
41
+ Tooltip,
42
+ TooltipContent,
43
+ TooltipProvider,
44
+ TooltipTrigger,
45
+ } from "./ui/tooltip";
46
 
47
  // Default template for a new MCP server
48
  const INITIAL_NEW_SERVER: Omit<MCPServer, 'id'> = {
 
85
  return value.substring(0, 3) + '•'.repeat(Math.min(10, value.length - 4)) + value.substring(value.length - 1);
86
  };
87
 
88
+ // Update the StatusIndicator to use Tooltip component
89
+ const StatusIndicator = ({ status, onClick, hoverInfo }: {
90
+ status?: ServerStatus,
91
+ onClick?: () => void,
92
+ hoverInfo?: string
93
+ }) => {
94
  const isClickable = !!onClick;
95
+ const hasHoverInfo = !!hoverInfo;
96
 
97
+ const className = `flex-shrink-0 flex items-center gap-1 ${isClickable ? 'cursor-pointer' : ''}`;
98
 
99
+ const statusIndicator = (status: ServerStatus | undefined) => {
100
+ switch (status) {
101
+ case 'connected':
102
+ return (
103
+ <div className={className} onClick={onClick}>
104
+ <div className="w-2 h-2 rounded-full bg-green-500 animate-pulse" />
105
+ <span className="text-xs text-green-500 hover:underline">Connected</span>
106
+ </div>
107
+ );
108
+ case 'connecting':
109
+ return (
110
+ <div className={className} onClick={onClick}>
111
+ <RefreshCw className="w-3 h-3 text-amber-500 animate-spin" />
112
+ <span className="text-xs text-amber-500">Connecting</span>
113
+ </div>
114
+ );
115
+ case 'error':
116
+ return (
117
+ <div className={className} onClick={onClick}>
118
+ <AlertTriangle className="w-3 h-3 text-red-500" />
119
+ <span className="text-xs text-red-500 hover:underline">Error</span>
120
+ </div>
121
+ );
122
+ case 'disconnected':
123
+ default:
124
+ return (
125
+ <div className={className} onClick={onClick}>
126
+ <div className="w-2 h-2 rounded-full bg-gray-400" />
127
+ <span className="text-xs text-muted-foreground">Disconnected</span>
128
+ </div>
129
+ );
130
+ }
131
+ };
132
+
133
+ // Use Tooltip if we have hover info
134
+ if (hasHoverInfo) {
135
+ return (
136
+ <Tooltip>
137
+ <TooltipTrigger asChild>
138
+ {statusIndicator(status)}
139
+ </TooltipTrigger>
140
+ <TooltipContent side="top" align="center" className="max-w-[300px] break-all text-wrap">
141
+ {hoverInfo}
142
+ </TooltipContent>
143
+ </Tooltip>
144
+ );
145
  }
146
+
147
+ // Otherwise just return the status indicator
148
+ return statusIndicator(status);
149
  };
150
 
151
  export const MCPServerManager = ({
 
497
 
498
  // UI element to display the correct server URL
499
  const getServerDisplayUrl = (server: MCPServer): string => {
500
+ // Always show the configured URL or command, not the sandbox URL
 
 
 
 
 
 
501
  return server.type === 'sse'
502
  ? server.url
503
  : `${server.command} ${server.args?.join(' ')}`;
504
  };
505
 
506
+ // Update the hover info function to return richer content
507
+ const getServerStatusHoverInfo = (server: MCPServer): string | undefined => {
508
+ // For connected stdio servers, show the sandbox URL as hover info
509
+ if (server.type === 'stdio' && server.status === 'connected' && server.sandboxUrl) {
510
+ return `Running at: ${server.sandboxUrl}`;
511
+ }
512
+
513
+ // For error status, show the error message
514
+ if (server.status === 'error' && server.errorMessage) {
515
+ return `Error: ${server.errorMessage}`;
516
+ }
517
+
518
+ return undefined;
519
+ };
520
+
521
  return (
522
  <Dialog open={open} onOpenChange={onOpenChange}>
523
  <DialogContent className="sm:max-w-[480px] max-h-[85vh] overflow-hidden flex flex-col">
 
594
  <StatusIndicator
595
  status={server.status}
596
  onClick={() => server.errorMessage && toast.error(server.errorMessage)}
597
+ hoverInfo={getServerStatusHoverInfo(server)}
598
  />
599
 
600
  {/* Server actions */}