@samanhappy/mcphub 1.0.27 → 1.0.28

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (60) hide show
  1. package/dist/controllers/oauthCallbackController.js +0 -1
  2. package/dist/controllers/oauthCallbackController.js.map +1 -1
  3. package/dist/controllers/serverController.js +13 -1
  4. package/dist/controllers/serverController.js.map +1 -1
  5. package/dist/services/mcpOAuthProvider.js +11 -1
  6. package/dist/services/mcpOAuthProvider.js.map +1 -1
  7. package/dist/services/mcpService.js +189 -13
  8. package/dist/services/mcpService.js.map +1 -1
  9. package/dist/utils/jsonSchemaValidator.js +26 -0
  10. package/dist/utils/jsonSchemaValidator.js.map +1 -0
  11. package/dist/utils/serverConfigPersistence.js +7 -0
  12. package/dist/utils/serverConfigPersistence.js.map +1 -1
  13. package/frontend/dist/assets/{ActivityPage-Ci3V0MRG.js → ActivityPage-D0SFqsRe.js} +2 -2
  14. package/frontend/dist/assets/{ActivityPage-Ci3V0MRG.js.map → ActivityPage-D0SFqsRe.js.map} +1 -1
  15. package/frontend/dist/assets/{Dashboard-CugghcDJ.js → Dashboard-DzWkQnht.js} +2 -2
  16. package/frontend/dist/assets/{Dashboard-CugghcDJ.js.map → Dashboard-DzWkQnht.js.map} +1 -1
  17. package/frontend/dist/assets/{EndpointCopy-BXZo8Cty.js → EndpointCopy-Bqjt3lGe.js} +2 -2
  18. package/frontend/dist/assets/{EndpointCopy-BXZo8Cty.js.map → EndpointCopy-Bqjt3lGe.js.map} +1 -1
  19. package/frontend/dist/assets/{GroupsPage-W6RjpC0i.js → GroupsPage-DsmZMSK0.js} +2 -2
  20. package/frontend/dist/assets/{GroupsPage-W6RjpC0i.js.map → GroupsPage-DsmZMSK0.js.map} +1 -1
  21. package/frontend/dist/assets/{LoginPage-CeK6PaNa.js → LoginPage-_Gr1ere-.js} +2 -2
  22. package/frontend/dist/assets/{LoginPage-CeK6PaNa.js.map → LoginPage-_Gr1ere-.js.map} +1 -1
  23. package/frontend/dist/assets/{LogsPage--YJi3jrU.js → LogsPage-D2vByutC.js} +2 -2
  24. package/frontend/dist/assets/{LogsPage--YJi3jrU.js.map → LogsPage-D2vByutC.js.map} +1 -1
  25. package/frontend/dist/assets/{MarketPage-CM_ywdX2.js → MarketPage-BhyrxwBv.js} +2 -2
  26. package/frontend/dist/assets/{MarketPage-CM_ywdX2.js.map → MarketPage-BhyrxwBv.js.map} +1 -1
  27. package/frontend/dist/assets/{PromptsPage-Bt7UumtQ.js → PromptsPage-BLn95Icp.js} +2 -2
  28. package/frontend/dist/assets/{PromptsPage-Bt7UumtQ.js.map → PromptsPage-BLn95Icp.js.map} +1 -1
  29. package/frontend/dist/assets/{ResourcesPage-DhB3ycyY.js → ResourcesPage-B27GVOO6.js} +2 -2
  30. package/frontend/dist/assets/{ResourcesPage-DhB3ycyY.js.map → ResourcesPage-B27GVOO6.js.map} +1 -1
  31. package/frontend/dist/assets/ServersPage-BuoWpLAq.js +39 -0
  32. package/frontend/dist/assets/ServersPage-BuoWpLAq.js.map +1 -0
  33. package/frontend/dist/assets/{SettingsPage-DfCWu2KX.js → SettingsPage-BzCwUvx7.js} +2 -2
  34. package/frontend/dist/assets/{SettingsPage-DfCWu2KX.js.map → SettingsPage-BzCwUvx7.js.map} +1 -1
  35. package/frontend/dist/assets/{StatusDot-HBipO3HS.js → StatusDot-BUWJw3dA.js} +2 -2
  36. package/frontend/dist/assets/{StatusDot-HBipO3HS.js.map → StatusDot-BUWJw3dA.js.map} +1 -1
  37. package/frontend/dist/assets/{ToggleGroup-pYyiJRvx.js → ToggleGroup-BPAIOm5B.js} +2 -2
  38. package/frontend/dist/assets/{ToggleGroup-pYyiJRvx.js.map → ToggleGroup-BPAIOm5B.js.map} +1 -1
  39. package/frontend/dist/assets/{UsersPage-BNoq4Qio.js → UsersPage-SZrL0bKd.js} +2 -2
  40. package/frontend/dist/assets/{UsersPage-BNoq4Qio.js.map → UsersPage-SZrL0bKd.js.map} +1 -1
  41. package/frontend/dist/assets/{contextCost-DcQ1PVMm.js → contextCost-BxT09q-Y.js} +2 -2
  42. package/frontend/dist/assets/{contextCost-DcQ1PVMm.js.map → contextCost-BxT09q-Y.js.map} +1 -1
  43. package/frontend/dist/assets/index-Bz_euXvO.js +3 -0
  44. package/frontend/dist/assets/{index-CZJVfOO6.js.map → index-Bz_euXvO.js.map} +1 -1
  45. package/frontend/dist/assets/index-DEAy4k6z.css +1 -0
  46. package/frontend/dist/assets/{resourceService-CJciejgX.js → resourceService-CWKSpa0p.js} +2 -2
  47. package/frontend/dist/assets/{resourceService-CJciejgX.js.map → resourceService-CWKSpa0p.js.map} +1 -1
  48. package/frontend/dist/assets/useSettingsData-0sbahDtL.js +2 -0
  49. package/frontend/dist/assets/{useSettingsData-hgvZTFTk.js.map → useSettingsData-0sbahDtL.js.map} +1 -1
  50. package/frontend/dist/assets/variableDetection-DfkBZ0gv.js +16 -0
  51. package/frontend/dist/assets/variableDetection-DfkBZ0gv.js.map +1 -0
  52. package/frontend/dist/index.html +2 -2
  53. package/package.json +2 -2
  54. package/frontend/dist/assets/ServersPage-BFwvEzGn.js +0 -37
  55. package/frontend/dist/assets/ServersPage-BFwvEzGn.js.map +0 -1
  56. package/frontend/dist/assets/index-BfEBXfi0.css +0 -1
  57. package/frontend/dist/assets/index-CZJVfOO6.js +0 -3
  58. package/frontend/dist/assets/useSettingsData-hgvZTFTk.js +0 -2
  59. package/frontend/dist/assets/variableDetection-DPNQ6jqO.js +0 -16
  60. package/frontend/dist/assets/variableDetection-DPNQ6jqO.js.map +0 -1
@@ -0,0 +1 @@
1
+ {"version":3,"file":"variableDetection-DfkBZ0gv.js","sources":["../../src/utils/serverFormPayload.ts","../../src/components/ServerForm.tsx","../../src/utils/variableDetection.ts"],"sourcesContent":["import type { EnvVar, ServerConfig, ServerFormData } from '../types';\n\ntype ServerType = NonNullable<ServerConfig['type']>;\n\ninterface BuildServerPayloadInput {\n formData: ServerFormData;\n serverType: ServerType;\n envVars: EnvVar[];\n headerVars: EnvVar[];\n}\n\nconst buildKeyValueRecord = (vars: EnvVar[]): Record<string, string> => {\n const record: Record<string, string> = {};\n\n vars.forEach(({ key, value }) => {\n const trimmedKey = key.trim();\n if (trimmedKey) {\n record[trimmedKey] = value;\n }\n });\n\n return record;\n};\n\nconst parseCommaSeparatedList = (value?: string): string[] => {\n if (!value) {\n return [];\n }\n\n return value\n .split(',')\n .map((item) => item.trim())\n .filter((item) => item.length > 0);\n};\n\nconst buildOptions = (options?: ServerFormData['options']) => {\n const nextOptions: NonNullable<ServerFormData['options']> = {};\n\n if (options?.timeout && options.timeout !== 60000) {\n nextOptions.timeout = options.timeout;\n }\n\n if (typeof options?.resetTimeoutOnProgress === 'boolean') {\n nextOptions.resetTimeoutOnProgress = options.resetTimeoutOnProgress;\n }\n\n if (options?.maxTotalTimeout) {\n nextOptions.maxTotalTimeout = options.maxTotalTimeout;\n }\n\n return nextOptions;\n};\n\nconst buildOAuthConfig = (\n oauth?: ServerFormData['oauth'],\n): Partial<NonNullable<ServerConfig['oauth']>> => {\n if (!oauth) {\n return {};\n }\n\n const nextOAuth: Partial<NonNullable<ServerConfig['oauth']>> = {};\n const clientId = oauth.clientId?.trim();\n const clientSecret = oauth.clientSecret?.trim();\n const scopes = oauth.scopes?.trim();\n const accessToken = oauth.accessToken?.trim();\n const refreshToken = oauth.refreshToken?.trim();\n const authorizationEndpoint = oauth.authorizationEndpoint?.trim();\n const tokenEndpoint = oauth.tokenEndpoint?.trim();\n const resource = oauth.resource?.trim();\n\n if (clientId) nextOAuth.clientId = clientId;\n if (clientSecret) nextOAuth.clientSecret = clientSecret;\n if (scopes) {\n const parsedScopes = scopes\n .split(/[\\s,]+/)\n .map((scope) => scope.trim())\n .filter((scope) => scope.length > 0);\n\n if (parsedScopes.length > 0) {\n nextOAuth.scopes = parsedScopes;\n }\n }\n if (accessToken) nextOAuth.accessToken = accessToken;\n if (refreshToken) nextOAuth.refreshToken = refreshToken;\n if (authorizationEndpoint) nextOAuth.authorizationEndpoint = authorizationEndpoint;\n if (tokenEndpoint) nextOAuth.tokenEndpoint = tokenEndpoint;\n if (resource) nextOAuth.resource = resource;\n\n return nextOAuth;\n};\n\nconst buildOpenApiConfig = (formData: ServerFormData): NonNullable<ServerConfig['openapi']> => {\n const openapi: NonNullable<ServerConfig['openapi']> = {\n version: formData.openapi?.version || '3.1.0',\n passthroughHeaders: parseCommaSeparatedList(formData.openapi?.passthroughHeaders),\n };\n const oauth2TokenUrl = formData.openapi?.oauth2TokenUrl?.trim();\n const oauth2ClientId = formData.openapi?.oauth2ClientId?.trim();\n const oauth2ClientSecret = formData.openapi?.oauth2ClientSecret?.trim();\n const oauth2Token = formData.openapi?.oauth2Token?.trim();\n\n if (formData.openapi?.inputMode === 'url') {\n openapi.url = formData.openapi?.url || '';\n } else if (formData.openapi?.inputMode === 'schema' && formData.openapi?.schema) {\n try {\n openapi.schema = JSON.parse(formData.openapi.schema);\n } catch {\n throw new Error('Invalid JSON schema format');\n }\n }\n\n if (formData.openapi?.securityType && formData.openapi.securityType !== 'none') {\n openapi.security = {\n type: formData.openapi.securityType,\n ...(formData.openapi.securityType === 'apiKey' && {\n apiKey: {\n name: formData.openapi.apiKeyName || '',\n in: formData.openapi.apiKeyIn || 'header',\n value: formData.openapi.apiKeyValue || '',\n },\n }),\n ...(formData.openapi.securityType === 'http' && {\n http: {\n scheme: formData.openapi.httpScheme || 'bearer',\n credentials: formData.openapi.httpCredentials || '',\n },\n }),\n ...(formData.openapi.securityType === 'oauth2' && {\n oauth2: {\n ...(oauth2TokenUrl && {\n tokenUrl: oauth2TokenUrl,\n }),\n ...(oauth2ClientId && {\n clientId: oauth2ClientId,\n }),\n ...(oauth2ClientSecret && {\n clientSecret: oauth2ClientSecret,\n }),\n ...(oauth2Token && {\n token: oauth2Token,\n }),\n },\n }),\n ...(formData.openapi.securityType === 'openIdConnect' && {\n openIdConnect: {\n url: formData.openapi.openIdConnectUrl || '',\n token: formData.openapi.openIdConnectToken || '',\n },\n }),\n };\n }\n\n return openapi;\n};\n\nexport const buildServerPayload = ({\n formData,\n serverType,\n envVars,\n headerVars,\n}: BuildServerPayloadInput) => {\n const env = buildKeyValueRecord(envVars);\n const headers = buildKeyValueRecord(headerVars);\n const options = buildOptions(formData.options);\n const description = formData.description?.trim() || '';\n\n const config: Partial<ServerConfig> = {\n type: serverType,\n description,\n options,\n visibility: formData.visibility ?? 'private',\n perSessionClient: formData.perSessionClient === true ? true : undefined,\n startOnDemand: formData.startOnDemand === true ? true : undefined,\n idleTimeoutMs: formData.startOnDemand === true ? (formData.idleTimeoutMs ?? 300000) : undefined,\n };\n\n if (serverType === 'openapi') {\n config.headers = headers;\n config.openapi = buildOpenApiConfig(formData);\n } else if (serverType === 'sse' || serverType === 'streamable-http') {\n const keepAliveEnabled = formData.keepAlive?.enabled === true;\n\n config.url = formData.url.trim();\n config.env = env;\n config.headers = headers;\n config.passthroughHeaders = parseCommaSeparatedList(formData.passthroughHeaders);\n config.oauth = buildOAuthConfig(formData.oauth);\n config.enableKeepAlive = keepAliveEnabled;\n config.keepAliveInterval = keepAliveEnabled ? formData.keepAlive?.interval || 60000 : undefined;\n } else {\n config.command = formData.command.trim();\n config.args = formData.args;\n config.env = env;\n }\n\n return {\n name: formData.name.trim(),\n config,\n };\n};\n","import { useState } from 'react';\nimport { useTranslation } from 'react-i18next';\nimport { X } from 'lucide-react';\nimport { Server, EnvVar, ServerFormData } from '@/types';\nimport { buildServerPayload } from '../utils/serverFormPayload';\n\ninterface ServerFormProps {\n onSubmit: (payload: any) => void;\n onCancel: () => void;\n initialData?: Server | null;\n modalTitle: string;\n formError?: string | null;\n}\n\nconst ServerForm = ({\n onSubmit,\n onCancel,\n initialData = null,\n modalTitle,\n formError = null,\n}: ServerFormProps) => {\n const { t } = useTranslation();\n\n // Determine the initial server type from the initialData\n const getInitialServerType = () => {\n if (!initialData || !initialData.config) return 'stdio';\n\n if (initialData.config.type) {\n return initialData.config.type; // Use explicit type if available\n } else if (initialData.config.url) {\n return 'sse'; // Fallback to SSE if URL exists\n } else {\n return 'stdio'; // Default to stdio\n }\n };\n\n const getInitialServerEnvVars = (data: Server | null): EnvVar[] => {\n if (!data || !data.config || !data.config.env) return [];\n\n return Object.entries(data.config.env).map(([key, value]) => ({\n key,\n value,\n description: '', // You can set a default description if needed\n }));\n };\n\n const getInitialOAuthConfig = (data: Server | null): ServerFormData['oauth'] => {\n const oauth = data?.config?.oauth;\n return {\n clientId: oauth?.clientId || '',\n clientSecret: oauth?.clientSecret || '',\n scopes: oauth?.scopes ? oauth.scopes.join(' ') : '',\n accessToken: oauth?.accessToken || '',\n refreshToken: oauth?.refreshToken || '',\n authorizationEndpoint: oauth?.authorizationEndpoint || '',\n tokenEndpoint: oauth?.tokenEndpoint || '',\n resource: oauth?.resource || '',\n };\n };\n\n const [serverType, setServerType] = useState<'stdio' | 'sse' | 'streamable-http' | 'openapi'>(\n getInitialServerType(),\n );\n\n const [formData, setFormData] = useState<ServerFormData>({\n name: (initialData && initialData.name) || '',\n description: (initialData && initialData.config && initialData.config.description) || '',\n url: (initialData && initialData.config && initialData.config.url) || '',\n command: (initialData && initialData.config && initialData.config.command) || '',\n arguments:\n initialData && initialData.config && initialData.config.args\n ? Array.isArray(initialData.config.args)\n ? initialData.config.args.join(' ')\n : String(initialData.config.args)\n : '',\n args: (initialData && initialData.config && initialData.config.args) || [],\n type: getInitialServerType(), // Initialize the type field\n env: getInitialServerEnvVars(initialData),\n headers: [],\n passthroughHeaders:\n initialData?.config?.passthroughHeaders?.join(', ') || '',\n visibility: (initialData?.config?.visibility ?? 'private') as\n | 'private'\n | 'group'\n | 'public',\n options: {\n timeout:\n (initialData &&\n initialData.config &&\n initialData.config.options &&\n initialData.config.options.timeout) ||\n 60000,\n resetTimeoutOnProgress:\n initialData?.config?.options?.resetTimeoutOnProgress ?? true,\n maxTotalTimeout:\n (initialData &&\n initialData.config &&\n initialData.config.options &&\n initialData.config.options.maxTotalTimeout) ||\n undefined,\n },\n oauth: getInitialOAuthConfig(initialData),\n // KeepAlive configuration initialization\n keepAlive: {\n enabled: initialData?.config?.enableKeepAlive === true,\n interval: initialData?.config?.keepAliveInterval || 60000,\n },\n // Per-session client isolation initialization\n perSessionClient: initialData?.config?.perSessionClient === true,\n // On-demand spawning initialization\n startOnDemand: initialData?.config?.startOnDemand === true,\n idleTimeoutMs: initialData?.config?.idleTimeoutMs ?? 300000,\n // OpenAPI configuration initialization\n openapi:\n initialData && initialData.config && initialData.config.openapi\n ? {\n url: initialData.config.openapi.url || '',\n schema: initialData.config.openapi.schema\n ? JSON.stringify(initialData.config.openapi.schema, null, 2)\n : '',\n inputMode: initialData.config.openapi.url\n ? 'url'\n : initialData.config.openapi.schema\n ? 'schema'\n : 'url',\n version: initialData.config.openapi.version || '3.1.0',\n securityType: initialData.config.openapi.security?.type || 'none',\n // API Key initialization\n apiKeyName: initialData.config.openapi.security?.apiKey?.name || '',\n apiKeyIn: initialData.config.openapi.security?.apiKey?.in || 'header',\n apiKeyValue: initialData.config.openapi.security?.apiKey?.value || '',\n // HTTP auth initialization\n httpScheme: initialData.config.openapi.security?.http?.scheme || 'bearer',\n httpCredentials: initialData.config.openapi.security?.http?.credentials || '',\n // OAuth2 initialization\n oauth2TokenUrl: initialData.config.openapi.security?.oauth2?.tokenUrl || '',\n oauth2ClientId: initialData.config.openapi.security?.oauth2?.clientId || '',\n oauth2ClientSecret: initialData.config.openapi.security?.oauth2?.clientSecret || '',\n oauth2Token: initialData.config.openapi.security?.oauth2?.token || '',\n // OpenID Connect initialization\n openIdConnectUrl: initialData.config.openapi.security?.openIdConnect?.url || '',\n openIdConnectToken: initialData.config.openapi.security?.openIdConnect?.token || '',\n // Passthrough headers initialization\n passthroughHeaders: initialData.config.openapi.passthroughHeaders\n ? initialData.config.openapi.passthroughHeaders.join(', ')\n : '',\n }\n : {\n inputMode: 'url',\n url: '',\n schema: '',\n version: '3.1.0',\n securityType: 'none',\n passthroughHeaders: '',\n },\n });\n\n const [envVars, setEnvVars] = useState<EnvVar[]>(\n initialData && initialData.config && initialData.config.env\n ? Object.entries(initialData.config.env).map(([key, value]) => ({ key, value }))\n : [],\n );\n\n const [headerVars, setHeaderVars] = useState<EnvVar[]>(\n initialData && initialData.config && initialData.config.headers\n ? Object.entries(initialData.config.headers).map(([key, value]) => ({ key, value }))\n : [],\n );\n\n const [isRequestOptionsExpanded, setIsRequestOptionsExpanded] = useState<boolean>(false);\n const [isOAuthSectionExpanded, setIsOAuthSectionExpanded] = useState<boolean>(false);\n const [isKeepAliveSectionExpanded, setIsKeepAliveSectionExpanded] = useState<boolean>(false);\n const [isAdvancedExpanded, setIsAdvancedExpanded] = useState<boolean>(false);\n const [error, setError] = useState<string | null>(null);\n const isEdit = !!initialData;\n\n const handleInputChange = (e: React.ChangeEvent<HTMLInputElement>) => {\n const { name, value } = e.target;\n setFormData({ ...formData, [name]: value });\n };\n\n // Transform space-separated arguments string into array\n const handleArgsChange = (value: string) => {\n const args = value.split(' ').filter((arg) => arg.trim() !== '');\n setFormData({ ...formData, arguments: value, args });\n };\n\n const updateServerType = (type: 'stdio' | 'sse' | 'streamable-http' | 'openapi') => {\n setServerType(type);\n setFormData((prev) => ({ ...prev, type }));\n };\n\n const handleEnvVarChange = (index: number, field: 'key' | 'value', value: string) => {\n const newEnvVars = [...envVars];\n newEnvVars[index][field] = value;\n setEnvVars(newEnvVars);\n };\n\n const addEnvVar = () => {\n setEnvVars([...envVars, { key: '', value: '' }]);\n };\n\n const removeEnvVar = (index: number) => {\n const newEnvVars = [...envVars];\n newEnvVars.splice(index, 1);\n setEnvVars(newEnvVars);\n };\n\n const handleHeaderVarChange = (index: number, field: 'key' | 'value', value: string) => {\n const newHeaderVars = [...headerVars];\n newHeaderVars[index][field] = value;\n setHeaderVars(newHeaderVars);\n };\n\n const addHeaderVar = () => {\n setHeaderVars([...headerVars, { key: '', value: '' }]);\n };\n\n const removeHeaderVar = (index: number) => {\n const newHeaderVars = [...headerVars];\n newHeaderVars.splice(index, 1);\n setHeaderVars(newHeaderVars);\n };\n\n const handleOAuthChange = <K extends keyof NonNullable<ServerFormData['oauth']>>(\n field: K,\n value: string,\n ) => {\n setFormData((prev) => ({\n ...prev,\n oauth: {\n ...(prev.oauth || {}),\n [field]: value,\n },\n }));\n };\n\n // Handle options changes\n const handleOptionsChange = (\n field: 'timeout' | 'resetTimeoutOnProgress' | 'maxTotalTimeout',\n value: number | boolean | undefined,\n ) => {\n setFormData((prev) => ({\n ...prev,\n options: {\n ...prev.options,\n [field]: value,\n },\n }));\n };\n\n // Submit handler for server configuration\n const handleSubmit = async (e: React.FormEvent) => {\n e.preventDefault();\n setError(null);\n\n try {\n const payload = buildServerPayload({\n formData,\n serverType,\n envVars,\n headerVars,\n });\n\n onSubmit(payload);\n } catch (err) {\n setError(`Error: ${err instanceof Error ? err.message : String(err)}`);\n }\n };\n\n return (\n <div className=\"hub-card p-6 w-full max-w-3xl max-h-screen overflow-y-auto\">\n <div className=\"flex justify-between items-center mb-5\">\n <h2 className=\"text-lg font-semibold text-[var(--hub-ink)]\">{modalTitle}</h2>\n <button\n onClick={onCancel}\n className=\"hub-icon-btn\"\n aria-label=\"Close\"\n >\n <X size={16} />\n </button>\n </div>\n\n {(error || formError) && (\n <div className=\"bg-red-50 text-red-700 p-3 rounded mb-4\">{formError || error}</div>\n )}\n\n <form onSubmit={handleSubmit}>\n {/* ─── Section 1: Basic Info ─── */}\n <div className=\"mb-5\">\n <h3 className=\"text-sm font-semibold text-[var(--hub-ink)] mb-3 pb-2 border-b border-gray-200 dark:border-gray-700\">\n {t('server.sectionBasicInfo', 'Basic Info')}\n </h3>\n\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\" htmlFor=\"name\">\n {t('server.name')}\n </label>\n <input\n type=\"text\"\n name=\"name\"\n id=\"name\"\n value={formData.name}\n onChange={handleInputChange}\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"e.g.: time-mcp\"\n required\n />\n </div>\n\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\" htmlFor=\"description\">\n {t('server.description')}\n </label>\n <input\n type=\"text\"\n name=\"description\"\n id=\"description\"\n value={formData.description || ''}\n onChange={handleInputChange}\n className=\"w-full py-2 px-3 form-input\"\n placeholder={t('server.descriptionPlaceholder')}\n />\n </div>\n </div>\n\n {/* ─── Section 2: Connection ─── */}\n <div className=\"mb-5\">\n <h3 className=\"text-sm font-semibold text-[var(--hub-ink)] mb-3 pb-2 border-b border-gray-200 dark:border-gray-700\">\n {t('server.sectionConnection', 'Connection')}\n </h3>\n\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\">{t('server.type')}</label>\n <div className=\"flex flex-wrap gap-x-4 gap-y-2\">\n <div>\n <input\n type=\"radio\"\n id=\"command\"\n name=\"serverType\"\n value=\"command\"\n checked={serverType === 'stdio'}\n onChange={() => updateServerType('stdio')}\n className=\"mr-1\"\n />\n <label htmlFor=\"command\" className=\"text-[var(--hub-ink)]\">{t('server.typeStdio')}</label>\n </div>\n <div>\n <input\n type=\"radio\"\n id=\"url\"\n name=\"serverType\"\n value=\"url\"\n checked={serverType === 'sse'}\n onChange={() => updateServerType('sse')}\n className=\"mr-1\"\n />\n <label htmlFor=\"url\" className=\"text-[var(--hub-ink)]\">{t('server.typeSse')}</label>\n </div>\n <div>\n <input\n type=\"radio\"\n id=\"streamable-http\"\n name=\"serverType\"\n value=\"streamable-http\"\n checked={serverType === 'streamable-http'}\n onChange={() => updateServerType('streamable-http')}\n className=\"mr-1\"\n />\n <label htmlFor=\"streamable-http\" className=\"text-[var(--hub-ink)]\">{t('server.typeStreamableHttp')}</label>\n </div>\n <div>\n <input\n type=\"radio\"\n id=\"openapi\"\n name=\"serverType\"\n value=\"openapi\"\n checked={serverType === 'openapi'}\n onChange={() => updateServerType('openapi')}\n className=\"mr-1\"\n />\n <label htmlFor=\"openapi\" className=\"text-[var(--hub-ink)]\">{t('server.typeOpenapi')}</label>\n </div>\n </div>\n </div>\n\n {/* Connection details — indented to show hierarchy under Server Type */}\n <div className=\"pl-4 border-l-2 border-gray-200 dark:border-gray-700 ml-2\">\n {serverType === 'openapi' ? (\n <>\n {/* Input Mode Selection */}\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\">\n {t('server.openapi.inputMode')}\n </label>\n <div className=\"flex space-x-4\">\n <div>\n <input\n type=\"radio\"\n id=\"input-mode-url\"\n name=\"inputMode\"\n value=\"url\"\n checked={formData.openapi?.inputMode === 'url'}\n onChange={() =>\n setFormData((prev) => ({\n ...prev,\n openapi: { ...prev.openapi!, inputMode: 'url' },\n }))\n }\n className=\"mr-1\"\n />\n <label htmlFor=\"input-mode-url\">{t('server.openapi.inputModeUrl')}</label>\n </div>\n <div>\n <input\n type=\"radio\"\n id=\"input-mode-schema\"\n name=\"inputMode\"\n value=\"schema\"\n checked={formData.openapi?.inputMode === 'schema'}\n onChange={() =>\n setFormData((prev) => ({\n ...prev,\n openapi: { ...prev.openapi!, inputMode: 'schema' },\n }))\n }\n className=\"mr-1\"\n />\n <label htmlFor=\"input-mode-schema\">{t('server.openapi.inputModeSchema')}</label>\n </div>\n </div>\n </div>\n\n {/* URL Input */}\n {formData.openapi?.inputMode === 'url' && (\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\" htmlFor=\"openapi-url\">\n {t('server.openapi.specUrl')}\n </label>\n <input\n type=\"url\"\n name=\"openapi-url\"\n id=\"openapi-url\"\n value={formData.openapi?.url || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: { ...prev.openapi!, url: e.target.value },\n }))\n }\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"e.g.: https://api.example.com/openapi.json\"\n required={serverType === 'openapi' && formData.openapi?.inputMode === 'url'}\n />\n </div>\n )}\n\n {/* Schema Input */}\n {formData.openapi?.inputMode === 'schema' && (\n <div className=\"mb-4\">\n <label\n className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\"\n htmlFor=\"openapi-schema\"\n >\n {t('server.openapi.schema')}\n </label>\n <textarea\n name=\"openapi-schema\"\n id=\"openapi-schema\"\n rows={10}\n value={formData.openapi?.schema || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: { ...prev.openapi!, schema: e.target.value },\n }))\n }\n className=\"w-full py-2 px-3 form-input font-mono text-sm\"\n placeholder={`{\n \"openapi\": \"3.1.0\",\n \"info\": {\n \"title\": \"API\",\n \"version\": \"1.0.0\"\n },\n \"servers\": [\n {\n \"url\": \"https://api.example.com\"\n }\n ],\n \"paths\": {\n ...\n }\n}`}\n required={serverType === 'openapi' && formData.openapi?.inputMode === 'schema'}\n />\n <p className=\"text-xs text-[var(--hub-ink-3)] mt-1\">{t('server.openapi.schemaHelp')}</p>\n </div>\n )}\n\n {/* Security Configuration */}\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\">\n {t('server.openapi.security')}\n </label>\n <select\n value={formData.openapi?.securityType || 'none'}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n securityType: e.target.value as any,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full py-2 px-3 form-input\"\n >\n <option value=\"none\">{t('server.openapi.securityNone')}</option>\n <option value=\"apiKey\">{t('server.openapi.securityApiKey')}</option>\n <option value=\"http\">{t('server.openapi.securityHttp')}</option>\n <option value=\"oauth2\">{t('server.openapi.securityOAuth2')}</option>\n <option value=\"openIdConnect\">{t('server.openapi.securityOpenIdConnect')}</option>\n </select>\n </div>\n\n {/* API Key Configuration */}\n {formData.openapi?.securityType === 'apiKey' && (\n <div className=\"mb-4 p-4 border border-gray-200 dark:border-gray-700 rounded bg-gray-50 dark:bg-gray-800\">\n <h4 className=\"text-sm font-medium mb-3 text-[var(--hub-ink-2)]\">\n {t('server.openapi.apiKeyConfig')}\n </h4>\n <div className=\"grid grid-cols-1 md:grid-cols-3 gap-3\">\n <div>\n <label className=\"block text-xs text-[var(--hub-ink-2)] mb-1\">\n {t('server.openapi.apiKeyName')}\n </label>\n <input\n type=\"text\"\n value={formData.openapi?.apiKeyName || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n apiKeyName: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm form-input focus:outline-none\"\n placeholder=\"Authorization\"\n />\n </div>\n <div>\n <label className=\"block text-xs text-[var(--hub-ink-2)] mb-1\">\n {t('server.openapi.apiKeyIn')}\n </label>\n <select\n value={formData.openapi?.apiKeyIn || 'header'}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n apiKeyIn: e.target.value as any,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n >\n <option value=\"header\">{t('server.openapi.apiKeyInHeader')}</option>\n <option value=\"query\">{t('server.openapi.apiKeyInQuery')}</option>\n <option value=\"cookie\">{t('server.openapi.apiKeyInCookie')}</option>\n </select>\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.openapi.apiKeyValue')}\n </label>\n <input\n type=\"password\"\n value={formData.openapi?.apiKeyValue || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n apiKeyValue: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"your-api-key\"\n />\n </div>\n </div>\n </div>\n )}\n\n {/* HTTP Authentication Configuration */}\n {formData.openapi?.securityType === 'http' && (\n <div className=\"mb-4 p-4 border border-gray-200 dark:border-gray-700 rounded bg-gray-50 dark:bg-gray-800\">\n <h4 className=\"text-sm font-medium mb-3 text-gray-700 dark:text-gray-300\">\n {t('server.openapi.httpAuthConfig')}\n </h4>\n <div className=\"grid grid-cols-1 md:grid-cols-2 gap-3\">\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.openapi.httpScheme')}\n </label>\n <select\n value={formData.openapi?.httpScheme || 'bearer'}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n httpScheme: e.target.value as any,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n >\n <option value=\"basic\">{t('server.openapi.httpSchemeBasic')}</option>\n <option value=\"bearer\">{t('server.openapi.httpSchemeBearer')}</option>\n <option value=\"digest\">{t('server.openapi.httpSchemeDigest')}</option>\n </select>\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.openapi.httpCredentials')}\n </label>\n <input\n type=\"password\"\n value={formData.openapi?.httpCredentials || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n httpCredentials: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder={\n formData.openapi?.httpScheme === 'basic'\n ? 'base64-encoded-credentials'\n : 'bearer-token'\n }\n />\n </div>\n </div>\n </div>\n )}\n\n {/* OAuth2 Configuration */}\n {formData.openapi?.securityType === 'oauth2' && (\n <div className=\"mb-4 p-4 border border-gray-200 dark:border-gray-700 rounded bg-gray-50 dark:bg-gray-800\">\n <h4 className=\"text-sm font-medium mb-3 text-gray-700 dark:text-gray-300\">\n {t('server.openapi.oauth2Config')}\n </h4>\n <div className=\"grid grid-cols-1 gap-3\">\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.oauth.tokenEndpoint')}\n </label>\n <input\n type=\"url\"\n value={formData.openapi?.oauth2TokenUrl || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n oauth2TokenUrl: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"https://example.com/oauth/token\"\n />\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.oauth.clientId')}\n </label>\n <input\n type=\"text\"\n value={formData.openapi?.oauth2ClientId || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n oauth2ClientId: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"client-id\"\n />\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.oauth.clientSecret')}\n </label>\n <input\n type=\"password\"\n value={formData.openapi?.oauth2ClientSecret || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n oauth2ClientSecret: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"client-secret\"\n />\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.openapi.oauth2Token')}\n </label>\n <input\n type=\"password\"\n value={formData.openapi?.oauth2Token || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n oauth2Token: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"access-token\"\n />\n </div>\n </div>\n </div>\n )}\n\n {/* OpenID Connect Configuration */}\n {formData.openapi?.securityType === 'openIdConnect' && (\n <div className=\"mb-4 p-4 border border-gray-200 dark:border-gray-700 rounded bg-gray-50 dark:bg-gray-800\">\n <h4 className=\"text-sm font-medium mb-3 text-gray-700 dark:text-gray-300\">\n {t('server.openapi.openIdConnectConfig')}\n </h4>\n <div className=\"grid grid-cols-1 gap-3\">\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.openapi.openIdConnectUrl')}\n </label>\n <input\n type=\"url\"\n value={formData.openapi?.openIdConnectUrl || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n openIdConnectUrl: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"https://example.com/.well-known/openid_configuration\"\n />\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.openapi.openIdConnectToken')}\n </label>\n <input\n type=\"password\"\n value={formData.openapi?.openIdConnectToken || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n openIdConnectToken: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full border rounded px-2 py-1 text-sm focus:outline-none form-input\"\n placeholder=\"id-token\"\n />\n </div>\n </div>\n </div>\n )}\n\n {/* Passthrough Headers Configuration */}\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-gray-700 dark:text-gray-300\">\n {t('server.openapi.passthroughHeaders')}\n </label>\n <input\n type=\"text\"\n value={formData.openapi?.passthroughHeaders || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n openapi: {\n ...prev.openapi,\n passthroughHeaders: e.target.value,\n url: prev.openapi?.url || '',\n },\n }))\n }\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"Authorization, X-API-Key, X-Custom-Header\"\n />\n <p className=\"text-xs text-gray-500 mt-1\">\n {t('server.openapi.passthroughHeadersHelp')}\n </p>\n </div>\n\n <div className=\"mb-4\">\n <div className=\"flex justify-between items-center mb-2\">\n <label className=\"block text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.headers')}\n </label>\n <button\n type=\"button\"\n onClick={addHeaderVar}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] btn-primary\"\n >\n +\n </button>\n </div>\n {headerVars.map((headerVar, index) => (\n <div key={index} className=\"flex items-center mb-2\">\n <div className=\"flex items-center space-x-2 flex-grow\">\n <input\n type=\"text\"\n value={headerVar.key}\n onChange={(e) => handleHeaderVarChange(index, 'key', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder=\"Authorization\"\n />\n <span className=\"flex items-center\">:</span>\n <input\n type=\"text\"\n value={headerVar.value}\n onChange={(e) => handleHeaderVarChange(index, 'value', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder=\"Bearer token...\"\n />\n </div>\n <button\n type=\"button\"\n onClick={() => removeHeaderVar(index)}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] ml-2 btn-danger\"\n >\n -\n </button>\n </div>\n ))}\n </div>\n </>\n ) : serverType === 'sse' || serverType === 'streamable-http' ? (\n <>\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-gray-700 dark:text-gray-300\" htmlFor=\"url\">\n {t('server.url')}\n </label>\n <input\n type=\"url\"\n name=\"url\"\n id=\"url\"\n value={formData.url}\n onChange={handleInputChange}\n className=\"w-full py-2 px-3 form-input\"\n placeholder={\n serverType === 'streamable-http'\n ? 'e.g.: http://localhost:3000/mcp'\n : 'e.g.: http://localhost:3000/sse'\n }\n required={serverType === 'sse' || serverType === 'streamable-http'}\n />\n </div>\n\n <div className=\"mb-4\">\n <div className=\"flex justify-between items-center mb-2\">\n <label className=\"block text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.headers')}\n </label>\n <button\n type=\"button\"\n onClick={addHeaderVar}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] btn-primary\"\n >\n +\n </button>\n </div>\n {headerVars.map((headerVar, index) => (\n <div key={index} className=\"flex items-center mb-2\">\n <div className=\"flex items-center space-x-2 flex-grow\">\n <input\n type=\"text\"\n value={headerVar.key}\n onChange={(e) => handleHeaderVarChange(index, 'key', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder=\"Authorization\"\n />\n <span className=\"flex items-center\">:</span>\n <input\n type=\"text\"\n value={headerVar.value}\n onChange={(e) => handleHeaderVarChange(index, 'value', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder=\"Bearer token...\"\n />\n </div>\n <button\n type=\"button\"\n onClick={() => removeHeaderVar(index)}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] ml-2 btn-danger\"\n >\n -\n </button>\n </div>\n ))}\n </div>\n\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-gray-700 dark:text-gray-300\">\n {t('server.openapi.passthroughHeaders')}\n </label>\n <input\n type=\"text\"\n value={formData.passthroughHeaders || ''}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n passthroughHeaders: e.target.value,\n }))\n }\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"Authorization, X-Custom-User-Id\"\n />\n <p className=\"text-xs text-gray-500 mt-1\">\n {t('server.openapi.passthroughHeadersHelp')}\n </p>\n </div>\n\n <div className=\"mb-4\">\n <div className=\"flex justify-between items-center mb-2\">\n <label className=\"block text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.envVars')}\n </label>\n <button\n type=\"button\"\n onClick={addEnvVar}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] btn-primary\"\n >\n +\n </button>\n </div>\n {envVars.map((envVar, index) => (\n <div key={index} className=\"flex items-center mb-2\">\n <div className=\"flex items-center space-x-2 flex-grow\">\n <input\n type=\"text\"\n value={envVar.key}\n onChange={(e) => handleEnvVarChange(index, 'key', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder={t('server.key')}\n />\n <span className=\"flex items-center\">:</span>\n <input\n type=\"text\"\n value={envVar.value}\n onChange={(e) => handleEnvVarChange(index, 'value', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder={t('server.value')}\n />\n </div>\n <button\n type=\"button\"\n onClick={() => removeEnvVar(index)}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] ml-2 btn-danger\"\n >\n -\n </button>\n </div>\n ))}\n </div>\n\n <div className=\"mb-4\">\n <div\n className=\"flex items-center justify-between cursor-pointer bg-gray-50 dark:bg-gray-800 hover:bg-gray-100 p-3 rounded border border-gray-200 dark:border-gray-700\"\n onClick={() => setIsOAuthSectionExpanded(!isOAuthSectionExpanded)}\n >\n <label className=\"text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.oauth.sectionTitle')}\n </label>\n <span className=\"text-gray-500 text-sm\">{isOAuthSectionExpanded ? '▼' : '▶'}</span>\n </div>\n\n {isOAuthSectionExpanded && (\n <div className=\"border border-gray-200 dark:border-gray-700 rounded-b p-4 bg-gray-50 dark:bg-gray-800 border-t-0\">\n <p className=\"text-xs text-gray-500 mb-3\">\n {t('server.oauth.sectionDescription')}\n </p>\n <div className=\"grid grid-cols-1 gap-3 md:grid-cols-2\">\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.oauth.clientId')}\n </label>\n <input\n type=\"text\"\n value={formData.oauth?.clientId || ''}\n onChange={(e) => handleOAuthChange('clientId', e.target.value)}\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"client id\"\n autoComplete=\"off\"\n />\n </div>\n <div>\n <label className=\"block text-xs text-gray-600 mb-1\">\n {t('server.oauth.clientSecret')}\n </label>\n <input\n type=\"password\"\n value={formData.oauth?.clientSecret || ''}\n onChange={(e) => handleOAuthChange('clientSecret', e.target.value)}\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"client secret\"\n autoComplete=\"off\"\n />\n </div>\n </div>\n </div>\n )}\n </div>\n </>\n ) : (\n <>\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-gray-700 dark:text-gray-300\" htmlFor=\"command\">\n {t('server.command')}\n </label>\n <input\n type=\"text\"\n name=\"command\"\n id=\"command\"\n value={formData.command}\n onChange={handleInputChange}\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"e.g.: npx\"\n required={serverType === 'stdio'}\n />\n </div>\n <div className=\"mb-4\">\n <label className=\"block text-sm font-medium mb-1.5 text-gray-700 dark:text-gray-300\" htmlFor=\"arguments\">\n {t('server.arguments')}\n </label>\n <input\n type=\"text\"\n name=\"arguments\"\n id=\"arguments\"\n value={formData.arguments}\n onChange={(e) => handleArgsChange(e.target.value)}\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"e.g.: -y time-mcp\"\n />\n </div>\n\n <div className=\"mb-4\">\n <div className=\"flex justify-between items-center mb-2\">\n <label className=\"block text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.envVars')}\n </label>\n <button\n type=\"button\"\n onClick={addEnvVar}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] btn-primary\"\n >\n +\n </button>\n </div>\n {envVars.map((envVar, index) => (\n <div key={index} className=\"flex items-center mb-2\">\n <div className=\"flex items-center space-x-2 flex-grow\">\n <input\n type=\"text\"\n value={envVar.key}\n onChange={(e) => handleEnvVarChange(index, 'key', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder={t('server.key')}\n />\n <span className=\"flex items-center\">:</span>\n <input\n type=\"text\"\n value={envVar.value}\n onChange={(e) => handleEnvVarChange(index, 'value', e.target.value)}\n className=\"w-1/2 py-2 px-3 form-input\"\n placeholder={t('server.value')}\n />\n </div>\n <button\n type=\"button\"\n onClick={() => removeEnvVar(index)}\n className=\"bg-gray-200 hover:bg-gray-300 text-gray-700 font-medium py-1 px-2 rounded text-sm flex items-center justify-center min-w-[30px] min-h-[30px] ml-2 btn-danger\"\n >\n -\n </button>\n </div>\n ))}\n </div>\n </>\n )}\n </div>\n </div>\n\n {/* ─── Section 3: Advanced Options (collapsible) ─── */}\n <div className=\"mb-4\">\n <div\n className=\"flex items-center justify-between cursor-pointer bg-gray-50 dark:bg-gray-800 hover:bg-gray-100 dark:hover:bg-gray-700 p-3 rounded border border-gray-200 dark:border-gray-700\"\n onClick={() => setIsAdvancedExpanded(!isAdvancedExpanded)}\n >\n <h3 className=\"text-sm font-semibold text-[var(--hub-ink)]\">\n {t('server.sectionAdvanced', 'Advanced Options')}\n </h3>\n <span className=\"text-gray-500 text-sm\">{isAdvancedExpanded ? '▼' : '▶'}</span>\n </div>\n\n {isAdvancedExpanded && (\n <div className=\"border border-gray-200 dark:border-gray-700 rounded-b p-4 bg-white dark:bg-gray-900 border-t-0 space-y-4\">\n {/* Visibility */}\n <div>\n <label className=\"block text-sm font-medium mb-1.5 text-[var(--hub-ink-2)]\" htmlFor=\"visibility\">\n {t('server.visibility', 'Visibility')}\n </label>\n <select\n id=\"visibility\"\n name=\"visibility\"\n value={formData.visibility || 'private'}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n visibility: e.target.value as 'private' | 'group' | 'public',\n }))\n }\n className=\"w-full py-2 px-3 form-input\"\n >\n <option value=\"private\">\n {t('server.visibilityPrivate', 'Private — only the owner and admins')}\n </option>\n {formData.visibility === 'group' && (\n <option value=\"group\" disabled>\n {t('server.visibilityGroup', 'Group (reserved — not yet implemented)')}\n </option>\n )}\n <option value=\"public\">\n {t('server.visibilityPublic', 'Public — every authenticated user')}\n </option>\n </select>\n <p className=\"text-xs text-gray-500 mt-1\">\n {t(\n 'server.visibilityDescription',\n \"Controls which non-admin users see this server in tools/list. Admins always see all servers regardless of this setting.\",\n )}\n </p>\n </div>\n\n {/* Request Options Configuration */}\n {serverType !== 'openapi' && (\n <div>\n <div\n className=\"flex items-center justify-between cursor-pointer bg-gray-50 dark:bg-gray-800 hover:bg-gray-100 p-3 rounded border border-gray-200 dark:border-gray-700\"\n onClick={() => setIsRequestOptionsExpanded(!isRequestOptionsExpanded)}\n >\n <label className=\"text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.requestOptions')}\n </label>\n <span className=\"text-gray-500 text-sm\">{isRequestOptionsExpanded ? '▼' : '▶'}</span>\n </div>\n\n {isRequestOptionsExpanded && (\n <div className=\"border border-gray-200 dark:border-gray-700 rounded-b p-4 bg-gray-50 dark:bg-gray-800 border-t-0\">\n <div className=\"grid grid-cols-1 md:grid-cols-2 gap-4\">\n <div>\n <label\n className=\"block text-gray-600 text-sm font-medium mb-1\"\n htmlFor=\"timeout\"\n >\n {t('server.timeout')}\n </label>\n <input\n type=\"number\"\n id=\"timeout\"\n value={formData.options?.timeout || 60000}\n onChange={(e) =>\n handleOptionsChange('timeout', parseInt(e.target.value) || 60000)\n }\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"30000\"\n min=\"1000\"\n max=\"300000\"\n />\n <p className=\"text-xs text-gray-500 mt-1\">{t('server.timeoutDescription')}</p>\n </div>\n\n <div>\n <label\n className=\"block text-gray-600 text-sm font-medium mb-1\"\n htmlFor=\"maxTotalTimeout\"\n >\n {t('server.maxTotalTimeout')}\n </label>\n <input\n type=\"number\"\n id=\"maxTotalTimeout\"\n value={formData.options?.maxTotalTimeout || ''}\n onChange={(e) =>\n handleOptionsChange(\n 'maxTotalTimeout',\n e.target.value ? parseInt(e.target.value) : undefined,\n )\n }\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"Optional\"\n min=\"1000\"\n />\n <p className=\"text-xs text-gray-500 mt-1\">\n {t('server.maxTotalTimeoutDescription')}\n </p>\n </div>\n </div>\n\n <div className=\"mt-3\">\n <label className=\"flex items-center\">\n <input\n type=\"checkbox\"\n checked={formData.options?.resetTimeoutOnProgress ?? true}\n onChange={(e) =>\n handleOptionsChange('resetTimeoutOnProgress', e.target.checked)\n }\n className=\"mr-2\"\n />\n <span className=\"text-gray-600 text-sm\">\n {t('server.resetTimeoutOnProgress')}\n </span>\n </label>\n <p className=\"text-xs text-gray-500 mt-1 ml-6\">\n {t('server.resetTimeoutOnProgressDescription')}\n </p>\n </div>\n </div>\n )}\n </div>\n )}\n\n {/* KeepAlive Configuration - only for SSE/Streamable HTTP */}\n {(serverType === 'sse' || serverType === 'streamable-http') && (\n <div>\n <div\n className=\"flex items-center justify-between cursor-pointer bg-gray-50 dark:bg-gray-800 hover:bg-gray-100 p-3 rounded border border-gray-200 dark:border-gray-700\"\n onClick={() => setIsKeepAliveSectionExpanded(!isKeepAliveSectionExpanded)}\n >\n <label className=\"text-sm font-medium text-gray-700 dark:text-gray-300\">\n {t('server.keepAlive', 'Connection Health')}\n </label>\n <span className=\"text-gray-500 text-sm\">\n {isKeepAliveSectionExpanded ? '▼' : '▶'}\n </span>\n </div>\n\n {isKeepAliveSectionExpanded && (\n <div className=\"border border-gray-200 dark:border-gray-700 rounded-b p-4 bg-gray-50 dark:bg-gray-800 border-t-0\">\n <div className=\"flex items-center mb-3\">\n <input\n type=\"checkbox\"\n id=\"enableKeepAlive\"\n checked={formData.keepAlive?.enabled || false}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n keepAlive: {\n ...prev.keepAlive,\n enabled: e.target.checked,\n },\n }))\n }\n className=\"mr-2\"\n />\n <label htmlFor=\"enableKeepAlive\" className=\"text-gray-600 text-sm\">\n {t('server.enableKeepAlive', 'Enable Health Checks and Auto Reconnect')}\n </label>\n </div>\n <p className=\"text-xs text-gray-500 mb-3\">\n {t(\n 'server.keepAliveDescription',\n 'Run periodic health checks and automatically reconnect this remote server when it becomes disconnected.',\n )}\n </p>\n <div>\n <label\n className=\"block text-gray-600 text-sm font-medium mb-1\"\n htmlFor=\"keepAliveInterval\"\n >\n {t('server.keepAliveInterval', 'Check interval (ms)')}\n </label>\n <input\n type=\"number\"\n id=\"keepAliveInterval\"\n value={formData.keepAlive?.interval || 60000}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n keepAlive: {\n ...prev.keepAlive,\n interval: parseInt(e.target.value) || 60000,\n },\n }))\n }\n className=\"w-full py-2 px-3 form-input\"\n placeholder=\"60000\"\n min=\"5000\"\n max=\"300000\"\n />\n <p className=\"text-xs text-gray-500 mt-1\">\n {t(\n 'server.keepAliveIntervalDescription',\n 'Time between health checks and automatic reconnect attempts in milliseconds (default: 60000ms = 1 minute)',\n )}\n </p>\n </div>\n </div>\n )}\n </div>\n )}\n\n {/* Per-session client isolation - applies to any server type except openapi */}\n {serverType !== 'openapi' && (\n <div>\n <div className=\"flex items-center mb-1\">\n <input\n type=\"checkbox\"\n id=\"perSessionClient\"\n checked={formData.perSessionClient || false}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n perSessionClient: e.target.checked,\n }))\n }\n className=\"mr-2\"\n />\n <label htmlFor=\"perSessionClient\" className=\"text-gray-700 dark:text-gray-300 text-sm font-medium\">\n {t('server.perSessionClient', 'Per-Session Client Isolation')}\n </label>\n </div>\n <p className=\"text-xs text-gray-500 ml-6\">\n {t(\n 'server.perSessionClientDescription',\n 'Create a dedicated upstream connection per session instead of sharing one across all sessions. Enable for stateful servers like Playwright. Increases upstream connections with concurrent sessions.',\n )}\n </p>\n </div>\n )}\n\n {/* On-demand spawning - stdio only */}\n {serverType === 'stdio' && (\n <div>\n <div className=\"flex items-center mb-1\">\n <input\n type=\"checkbox\"\n id=\"startOnDemand\"\n checked={formData.startOnDemand || false}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n startOnDemand: e.target.checked,\n }))\n }\n className=\"mr-2\"\n />\n <label htmlFor=\"startOnDemand\" className=\"text-gray-700 dark:text-gray-300 text-sm font-medium\">\n {t('server.startOnDemand', 'Start On Demand')}\n </label>\n </div>\n <p className=\"text-xs text-gray-500 ml-6\">\n {t(\n 'server.startOnDemandDescription',\n 'Skip startup connect and spawn this server only when a tool call arrives. The process is shut down automatically after the idle timeout, then restarted on the next call. Reduces persistent memory usage for rarely-used servers.',\n )}\n </p>\n {formData.startOnDemand && (\n <div className=\"ml-6 mt-2\">\n <label htmlFor=\"idleTimeoutMs\" className=\"block text-xs text-gray-600 dark:text-gray-400 mb-1\">\n {t('server.idleTimeoutMs', 'Idle shutdown timeout (ms)')}\n </label>\n <input\n type=\"number\"\n id=\"idleTimeoutMs\"\n min={10000}\n step={1000}\n value={formData.idleTimeoutMs ?? 300000}\n onChange={(e) =>\n setFormData((prev) => ({\n ...prev,\n idleTimeoutMs: Number(e.target.value),\n }))\n }\n className=\"hub-input w-40 text-sm\"\n />\n <p className=\"text-xs text-gray-500 mt-1\">\n {t(\n 'server.idleTimeoutMsDescription',\n 'Shut down the process after this many milliseconds with no tool calls. Default: 300000 (5 minutes).',\n )}\n </p>\n </div>\n )}\n </div>\n )}\n </div>\n )}\n </div>\n\n <div className=\"flex justify-end mt-6\">\n <button\n type=\"button\"\n onClick={onCancel}\n className=\"hub-btn mr-2\"\n >\n {t('server.cancel')}\n </button>\n <button\n type=\"submit\"\n className=\"hub-btn primary\"\n >\n {isEdit ? t('server.save') : t('server.add')}\n </button>\n </div>\n </form>\n </div>\n );\n};\n\nexport default ServerForm;\n","// Utility function to detect ${} variables in server configurations\nexport const detectVariables = (payload: any): string[] => {\n const variables = new Set<string>();\n const variableRegex = /\\$\\{([^}]+)\\}/g;\n\n const checkString = (str: string) => {\n let match;\n while ((match = variableRegex.exec(str)) !== null) {\n variables.add(match[1]);\n }\n };\n\n const checkObject = (obj: any, path: string = '') => {\n if (typeof obj === 'string') {\n checkString(obj);\n } else if (Array.isArray(obj)) {\n obj.forEach((item, index) => checkObject(item, `${path}[${index}]`));\n } else if (obj && typeof obj === 'object') {\n Object.entries(obj).forEach(([key, value]) => {\n checkObject(value, path ? `${path}.${key}` : key);\n });\n }\n };\n\n checkObject(payload);\n return Array.from(variables);\n};\n"],"names":["buildKeyValueRecord","vars","record","key","value","trimmedKey","parseCommaSeparatedList","item","buildOptions","options","nextOptions","buildOAuthConfig","oauth","nextOAuth","clientId","_a","clientSecret","_b","scopes","_c","accessToken","_d","refreshToken","_e","authorizationEndpoint","_f","tokenEndpoint","_g","resource","_h","parsedScopes","scope","buildOpenApiConfig","formData","openapi","oauth2TokenUrl","oauth2ClientId","oauth2ClientSecret","oauth2Token","_j","_i","_k","_l","_m","_n","_o","buildServerPayload","serverType","envVars","headerVars","env","headers","description","config","keepAliveEnabled","ServerForm","onSubmit","onCancel","initialData","modalTitle","formError","useTranslation","getInitialServerType","getInitialServerEnvVars","data","getInitialOAuthConfig","setServerType","useState","setFormData","_q","_p","_s","_r","_u","_t","_w","_v","_y","_x","_A","_z","_C","_B","_E","_D","_G","_F","setEnvVars","setHeaderVars","isRequestOptionsExpanded","setIsRequestOptionsExpanded","isOAuthSectionExpanded","setIsOAuthSectionExpanded","isKeepAliveSectionExpanded","setIsKeepAliveSectionExpanded","isAdvancedExpanded","setIsAdvancedExpanded","error","setError","isEdit","handleInputChange","e","name","handleArgsChange","args","arg","updateServerType","type","prev","handleEnvVarChange","index","field","newEnvVars","addEnvVar","removeEnvVar","handleHeaderVarChange","newHeaderVars","addHeaderVar","removeHeaderVar","handleOAuthChange","handleOptionsChange","handleSubmit","payload","err","jsxs","jsx","X","Fragment","_H","_I","_J","_K","_L","_M","_N","_O","_P","_Q","_R","_S","_T","_U","_V","_W","_X","_Y","_Z","__","_$","_aa","_ba","_ca","_da","_ea","headerVar","envVar","_fa","_ga","_ha","_ia","_ja","_ka","_la","detectVariables","variables","variableRegex","checkString","str","match","checkObject","obj","path"],"mappings":"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"}
@@ -9,11 +9,11 @@
9
9
  <link rel="preconnect" href="https://fonts.googleapis.com">
10
10
  <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
11
11
  <link href="https://fonts.googleapis.com/css2?family=Inter:wght@300;400;500;600;700&display=swap" rel="stylesheet">
12
- <script type="module" crossorigin src="./assets/index-CZJVfOO6.js"></script>
12
+ <script type="module" crossorigin src="./assets/index-Bz_euXvO.js"></script>
13
13
  <link rel="modulepreload" crossorigin href="./assets/framework-vendor-I9Y6AgD5.js">
14
14
  <link rel="modulepreload" crossorigin href="./assets/i18n-vendor-y9bLzIeh.js">
15
15
  <link rel="modulepreload" crossorigin href="./assets/icons-vendor-hw0ScL8G.js">
16
- <link rel="stylesheet" crossorigin href="./assets/index-BfEBXfi0.css">
16
+ <link rel="stylesheet" crossorigin href="./assets/index-DEAy4k6z.css">
17
17
  </head>
18
18
 
19
19
  <body class="bg-gray-100">
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@samanhappy/mcphub",
3
- "version": "1.0.27",
3
+ "version": "1.0.28",
4
4
  "description": "A hub server for mcp servers",
5
5
  "main": "dist/index.js",
6
6
  "type": "module",
@@ -47,7 +47,7 @@
47
47
  "express-rate-limit": "^8.3.0",
48
48
  "express-validator": "^7.3.1",
49
49
  "gpt-tokenizer": "^3.4.0",
50
- "hono": "4.12.27",
50
+ "hono": "4.12.34",
51
51
  "i18next": "^25.5.0",
52
52
  "i18next-fs-backend": "^2.6.0",
53
53
  "ipaddr.js": "^2.4.0",
@@ -1,37 +0,0 @@
1
- const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./resourceService-CJciejgX.js","./index-CZJVfOO6.js","./framework-vendor-I9Y6AgD5.js","./i18n-vendor-y9bLzIeh.js","./icons-vendor-hw0ScL8G.js","./index-BfEBXfi0.css"])))=>i.map(i=>d[i]);
2
- import{r as d,j as e,d as Ds}from"./framework-vendor-I9Y6AgD5.js";import{e as le,f as ts,h as ve,i as Pe,u as Ps,_ as ge,j as zs,k as Ts,l as $s}from"./index-CZJVfOO6.js";import{f as ie,u as Fs,a as Is}from"./contextCost-DcQ1PVMm.js";import{S as Rs}from"./StatusDot-HBipO3HS.js";import{u as ze}from"./useSettingsData-hgvZTFTk.js";import{S as Ne}from"./ToggleGroup-pYyiJRvx.js";import{u as te}from"./i18n-vendor-y9bLzIeh.js";import{n as rs,o as ns,l as we,p as Os,C as xe,q as ye,r as Te,s as as,t as os,u as $e,m as ke,W as _s,g as As,F as Ms,X as Ee,E as Vs,v as Js,R as je,w as Us,L as Bs,T as Ls,P as Ws,x as qs,y as Hs,z as Ks}from"./icons-vendor-hw0ScL8G.js";import{g as Gs}from"./toolDescription-Dw3sa28K.js";import{D as Xs}from"./DeleteDialog-DNe-zTEl.js";import{C as De}from"./ConfirmDialog-CYfXEuyU.js";import{S as is,d as Ys}from"./variableDetection-DPNQ6jqO.js";import{P as Zs}from"./Pagination-DLSuQ8hw.js";const ls=async(s,n)=>{try{const t=n?`/tools/${encodeURIComponent(n)}/${encodeURIComponent(s.toolName)}`:"/tools/call",a=await le(t,s.arguments,{headers:{Authorization:`Bearer ${localStorage.getItem("mcphub_token")}`}});return a.success===!1?{success:!1,error:a.message||"Tool call failed"}:{success:!0,content:(a==null?void 0:a.content)||[]}}catch(t){return console.error("Error calling tool",{toolName:s.toolName,server:n,error:t}),{success:!1,error:t instanceof Error?t.message:"Unknown error occurred"}}},Qs=async(s,n,t)=>{try{const a=await le(`/servers/${encodeURIComponent(s)}/tools/${encodeURIComponent(n)}/toggle`,{enabled:t},{headers:{Authorization:`Bearer ${localStorage.getItem("mcphub_token")}`}});return{success:a.success,error:a.success?void 0:a.message}}catch(a){return console.error("Error toggling tool",{serverName:s,toolName:n,enabled:t,error:a}),{success:!1,error:a instanceof Error?a.message:"Unknown error occurred"}}},cs=async(s,n,t)=>{try{const a=await ve(`/servers/${encodeURIComponent(s)}/tools/${encodeURIComponent(n)}/description`,{description:t},{headers:{Authorization:`Bearer ${localStorage.getItem("mcphub_token")}`}});return{success:a.success,error:a.success?void 0:a.message}}catch(a){return console.error("Error updating tool description",{serverName:s,toolName:n,error:a}),{success:!1,error:a instanceof Error?a.message:"Unknown error occurred"}}},ds=async(s,n)=>{var t;try{const a=await ts(`/servers/${encodeURIComponent(s)}/tools/${encodeURIComponent(n)}/description`,{headers:{Authorization:`Bearer ${localStorage.getItem("mcphub_token")}`}});return{success:a.success,error:a.success?void 0:a.message,description:(t=a.data)==null?void 0:t.description}}catch(a){return console.error("Error resetting tool description",{serverName:s,toolName:n,error:a}),{success:!1,error:a instanceof Error?a.message:"Unknown error occurred"}}},et=Object.freeze(Object.defineProperty({__proto__:null,callTool:ls,resetToolDescription:ds,toggleTool:Qs,updateToolDescription:cs},Symbol.toStringTag,{value:"Module"})),us=({schema:s,onSubmit:n,onCancel:t,loading:a=!1,storageKey:x,title:f})=>{const{t:o}=te(),[j,S]=d.useState({}),[D,r]=d.useState({}),[m,z]=d.useState(!1),[g,F]=d.useState(""),[N,E]=d.useState(""),C=d.useMemo(()=>(u=>{const v=l=>{if(typeof l=="object"&&l!==null){const p=l;return{type:p.type||"string",description:p.description,enum:p.enum,default:p.default,properties:p.properties?Object.fromEntries(Object.entries(p.properties).map(([c,y])=>[c,v(y)])):void 0,required:p.required,items:p.items?v(p.items):void 0}}return{type:"string"}};return{type:u.type,properties:u.properties?Object.fromEntries(Object.entries(u.properties).map(([l,p])=>[l,v(p)])):void 0,required:u.required}})(s),[s]);d.useEffect(()=>{const h=(v,l="")=>{const p={};return v.type==="object"&&v.properties&&Object.entries(v.properties).forEach(([c,y])=>{const $=l?`${l}.${c}`:c;y.default!==void 0?p[c]=y.default:y.type==="string"?p[c]="":y.type==="number"||y.type==="integer"?p[c]=0:y.type==="boolean"?p[c]=!1:y.type==="array"?p[c]=[]:y.type==="object"&&(y.properties?p[c]=h(y,$):p[c]={})}),p};let u=h(C);if(x)try{const v=localStorage.getItem(x);if(v){const l=JSON.parse(v);u={...u,...l}}}catch(v){console.warn("Failed to load saved form data:",v)}S(u)},[C,x]),d.useEffect(()=>{m&&Object.keys(j).length>0&&(F(JSON.stringify(j,null,2)),E(""))},[m,j]);const O=h=>{F(h),E("");try{const u=JSON.parse(h);if(S(u),x)try{localStorage.setItem(x,JSON.stringify(u))}catch(v){console.warn("Failed to save form data to localStorage:",v)}}catch{E(o("tool.invalidJsonFormat"))}},M=()=>{F(JSON.stringify(j,null,2)),E(""),z(!0)},W=()=>{if(g.trim())try{const h=JSON.parse(g);S(h),E(""),z(!1)}catch{E(o("tool.fixJsonBeforeSwitching"));return}else z(!1)},R=(h,u)=>{S(v=>{const l={...v},p=h.split(".");let c=l;for(let y=0;y<p.length-1;y++)c[p[y]]||(c[p[y]]={}),c=c[p[y]];if(c[p[p.length-1]]=u,x)try{localStorage.setItem(x,JSON.stringify(l))}catch(y){console.warn("Failed to save form data to localStorage:",y)}return l}),D[h]&&r(v=>{const l={...v};return delete l[h],l})},B=()=>{const h={},u=(v,l,p="")=>{v.type==="object"&&v.properties&&Object.entries(v.properties).forEach(([c,y])=>{var _;const $=p?`${p}.${c}`:c,I=l==null?void 0:l[c];if((_=v.required)!=null&&_.includes(c)&&(I==null||I===""||Array.isArray(I)&&I.length===0)){h[$]=`${c} is required`;return}I!=null&&I!==""&&(y.type==="string"&&typeof I!="string"?h[$]=`${c} must be a string`:y.type==="number"&&typeof I!="number"?h[$]=`${c} must be a number`:y.type==="integer"&&(!Number.isInteger(I)||typeof I!="number")?h[$]=`${c} must be an integer`:y.type==="boolean"&&typeof I!="boolean"?h[$]=`${c} must be a boolean`:y.type==="array"&&Array.isArray(I)?y.items&&I.forEach((L,Q)=>{var A;((A=y.items)==null?void 0:A.type)==="object"&&y.items.properties&&u(y.items,L,`${$}.${Q}`)}):y.type==="object"&&typeof I=="object"&&u(y,I,$))})};return u(C,j),r(h),Object.keys(h).length===0},T=h=>{h.preventDefault(),B()&&n(j)},K=(h,u)=>u.split(".").reduce((v,l)=>v==null?void 0:v[l],h),q=(h,u,v,l)=>{const p=v==null?void 0:v[h];return u.type==="string"?u.enum?e.jsxs("select",{value:p||"",onChange:c=>l(c.target.value),className:"w-full border rounded-md px-2 py-1 text-sm border-gray-300 focus:outline-none focus:ring-1 focus:ring-blue-500",children:[e.jsx("option",{value:"",children:o("tool.selectOption")}),u.enum.map((c,y)=>e.jsx("option",{value:c,children:c},y))]}):e.jsx("input",{type:"text",value:p||"",onChange:c=>l(c.target.value),className:"w-full border rounded-md px-2 py-1 text-sm border-gray-300 focus:outline-none focus:ring-1 focus:ring-blue-500 form-input",placeholder:u.description||o("tool.enterKey",{key:h})}):u.type==="number"||u.type==="integer"?e.jsx("input",{type:"number",step:u.type==="integer"?"1":"any",value:p??"",onChange:c=>{const y=c.target.value===""?"":u.type==="integer"?parseInt(c.target.value):parseFloat(c.target.value);l(y)},className:"w-full border rounded-md px-2 py-1 text-sm border-gray-300 focus:outline-none focus:ring-1 focus:ring-blue-500 form-input"}):u.type==="boolean"?e.jsx("input",{type:"checkbox",checked:p||!1,onChange:c=>l(c.target.checked),className:"h-4 w-4 text-blue-600 focus:ring-blue-500 border-gray-300 rounded"}):e.jsx("input",{type:"text",value:p||"",onChange:c=>l(c.target.value),className:"w-full border rounded-md px-2 py-1 text-sm border-gray-300 focus:outline-none focus:ring-1 focus:ring-blue-500 form-input",placeholder:u.description||o("tool.enterKey",{key:h})})},X=(h,u,v="")=>{var y,$,I,_,L,Q,A,k,U,ee,oe,P,H,ce;const l=v?`${v}.${h}`:h,p=K(j,l),c=D[l];if(u.type==="array"){const V=K(j,l)||[];return e.jsxs("div",{className:"mb-6",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?($=(y=K(C,v))==null?void 0:y.required)==null?void 0:$.includes(h):(I=C.required)==null?void 0:I.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsxs("div",{className:"border border-gray-200 dark:border-gray-700 rounded-md p-3 bg-gray-50 dark:bg-gray-800",children:[V.map((Z,se)=>{var he,ae,G;return e.jsxs("div",{className:"mb-3 p-3 bg-white dark:bg-gray-800 border border-gray-200 dark:border-gray-700 rounded-md",children:[e.jsxs("div",{className:"flex justify-between items-center mb-2",children:[e.jsx("span",{className:"text-sm font-medium text-gray-600",children:o("tool.item",{index:se+1})}),e.jsx("button",{type:"button",onClick:()=>{const Y=[...V];Y.splice(se,1),R(l,Y)},className:"text-status-red hover:text-red-700 text-sm",children:o("common.remove")})]}),((he=u.items)==null?void 0:he.type)==="string"&&u.items.enum?e.jsxs("select",{value:Z||"",onChange:Y=>{const re=[...V];re[se]=Y.target.value,R(l,re)},className:"w-full border rounded-md px-3 py-2 border-gray-300 focus:outline-none focus:ring-2 focus:ring-blue-500",children:[e.jsx("option",{value:"",children:o("tool.selectOption")}),u.items.enum.map((Y,re)=>e.jsx("option",{value:Y,children:Y},re))]}):((ae=u.items)==null?void 0:ae.type)==="object"&&u.items.properties?e.jsx("div",{className:"space-y-3",children:Object.entries(u.items.properties).map(([Y,re])=>{var be,fe;return e.jsxs("div",{children:[e.jsxs("label",{className:"block text-xs font-medium text-gray-600 mb-1",children:[Y,((fe=(be=u.items)==null?void 0:be.required)==null?void 0:fe.includes(Y))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]}),q(Y,re,Z,Ce=>{const pe=[...V];pe[se]={...pe[se],[Y]:Ce},R(l,pe)})]},Y)})}):e.jsx("input",{type:"text",value:Z||"",onChange:Y=>{const re=[...V];re[se]=Y.target.value,R(l,re)},className:"w-full border rounded-md px-3 py-2 border-gray-300 focus:outline-none focus:ring-2 focus:ring-blue-500 form-input",placeholder:o("tool.enterValue",{type:((G=u.items)==null?void 0:G.type)||"value"})})]},se)}),e.jsx("button",{type:"button",onClick:()=>{var se;const Z=((se=u.items)==null?void 0:se.type)==="object"?{}:"";R(l,[...V,Z])},className:"w-full mt-2 px-3 py-2 text-sm text-blue-600 border border-blue-300 rounded-md hover:bg-blue-50",children:o("tool.addItem",{key:h})})]}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l)}return u.type==="object"?u.properties?e.jsxs("div",{className:"mb-6",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?(L=(_=K(C,v))==null?void 0:_.required)==null?void 0:L.includes(h):(Q=C.required)==null?void 0:Q.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsx("div",{className:"border border-gray-200 dark:border-gray-700 rounded-md p-4 bg-gray-50 dark:bg-gray-800",children:Object.entries(u.properties).map(([V,Z])=>X(V,Z,l))}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l):e.jsxs("div",{className:"mb-4",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?(k=(A=K(C,v))==null?void 0:A.required)==null?void 0:k.includes(h):(U=C.required)==null?void 0:U.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"}),e.jsx("span",{className:"text-xs text-gray-500 ml-1",children:"(JSON object)"})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsx("textarea",{value:typeof p=="object"?JSON.stringify(p,null,2):p||"{}",onChange:V=>{try{const Z=JSON.parse(V.target.value);R(l,Z)}catch{R(l,V.target.value)}},placeholder:`{
3
- "key": "value"
4
- }`,className:`w-full border rounded-md px-3 py-2 font-mono text-sm ${c?"border-red-500":"border-gray-300"} focus:outline-none focus:ring-2 focus:ring-blue-500`,rows:4}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l):u.type==="string"?u.enum?e.jsxs("div",{className:"mb-4",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?!1:(ee=C.required)==null?void 0:ee.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsxs("select",{value:p||"",onChange:V=>R(l,V.target.value),className:`w-full border rounded-md px-3 py-2 ${c?"border-red-500":"border-gray-300"} focus:outline-none focus:ring-2 focus:ring-blue-500`,children:[e.jsx("option",{value:"",children:o("tool.selectOption")}),u.enum.map((V,Z)=>e.jsx("option",{value:V,children:V},Z))]}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l):e.jsxs("div",{className:"mb-4",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?!1:(oe=C.required)==null?void 0:oe.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsx("input",{type:"text",value:p||"",onChange:V=>R(l,V.target.value),className:`w-full border rounded-md px-3 py-2 ${c?"border-red":"border-gray-200"} focus:outline-none form-input`}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l):u.type==="number"||u.type==="integer"?e.jsxs("div",{className:"mb-4",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?!1:(P=C.required)==null?void 0:P.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsx("input",{type:"number",step:u.type==="integer"?"1":"any",value:p??"",onChange:V=>{const Z=V.target.value===""?"":u.type==="integer"?parseInt(V.target.value):parseFloat(V.target.value);R(l,Z)},className:`w-full border rounded-md px-3 py-2 form-input ${c?"border-red-500":"border-gray-300"} focus:outline-none focus:ring-2 focus:ring-blue-500`}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l):u.type==="boolean"?e.jsxs("div",{className:"mb-4",children:[e.jsxs("div",{className:"flex items-center",children:[e.jsx("input",{type:"checkbox",checked:p||!1,onChange:V=>R(l,V.target.checked),className:"h-4 w-4 text-blue-600 focus:ring-blue-500 border-gray-300 rounded"}),e.jsxs("label",{className:"ml-2 block text-sm text-gray-700",children:[h,(v?!1:(H=C.required)==null?void 0:H.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"})]})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mt-1",children:u.description}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l):e.jsxs("div",{className:"mb-4",children:[e.jsxs("label",{className:"block text-sm font-medium text-gray-700 mb-1",children:[h,(v?!1:(ce=C.required)==null?void 0:ce.includes(h))&&e.jsx("span",{className:"text-status-red ml-1",children:"*"}),e.jsxs("span",{className:"text-xs text-gray-500 ml-1",children:["(",u.type,")"]})]}),u.description&&e.jsx("p",{className:"text-xs text-gray-500 mb-2",children:u.description}),e.jsx("input",{type:"text",value:p||"",onChange:V=>R(l,V.target.value),placeholder:o("tool.enterValue",{type:u.type}),className:`w-full border rounded-md px-3 py-2 ${c?"border-red-500":"border-gray-300"} focus:outline-none focus:ring-2 focus:ring-blue-500 form-input`}),c&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:c})]},l)};return C.properties?e.jsxs("div",{className:"space-y-4",children:[e.jsxs("div",{className:"flex justify-between items-center pb-3",children:[e.jsx("h6",{className:"text-md font-medium text-gray-900",children:f}),e.jsxs("div",{className:"flex space-x-2",children:[e.jsx("button",{type:"button",onClick:W,className:`hub-btn sm ${m?"":"primary"}`,children:o("tool.formMode")}),e.jsx("button",{type:"button",onClick:M,className:`hub-btn sm ${m?"primary":""}`,children:o("tool.jsonMode")})]})]}),m?e.jsxs("div",{className:"space-y-4",children:[e.jsxs("div",{children:[e.jsx("label",{className:"block text-sm font-medium text-gray-700 mb-2",children:o("tool.jsonConfiguration")}),e.jsx("textarea",{value:g,onChange:h=>O(h.target.value),placeholder:`{
5
- "key": "value"
6
- }`,className:`w-full h-64 border rounded-md px-3 py-2 font-mono text-sm resize-y form-input ${N?"border-red-500":"border-gray-300"} focus:outline-none focus:ring-2 focus:ring-blue-500`}),N&&e.jsx("p",{className:"text-status-red text-xs mt-1",children:N})]}),e.jsxs("div",{className:"flex justify-end space-x-2 pt-4",children:[e.jsx("button",{type:"button",onClick:t,className:"hub-btn sm",children:o("tool.cancel")}),e.jsx("button",{onClick:()=>{try{const h=JSON.parse(g);n(h)}catch{E(o("tool.invalidJsonFormat"))}},disabled:a||!!N,className:"hub-btn sm primary",children:o(a?"tool.running":"tool.runTool")})]})]}):e.jsxs("form",{onSubmit:T,className:"space-y-4",children:[Object.entries(C.properties||{}).map(([h,u])=>X(h,u)),e.jsxs("div",{className:"flex justify-end space-x-2 pt-4",children:[e.jsx("button",{type:"button",onClick:t,className:"hub-btn sm",children:o("tool.cancel")}),e.jsx("button",{type:"submit",disabled:a,className:"hub-btn sm primary",children:o(a?"tool.running":"tool.runTool")})]})]})]}):e.jsxs("div",{className:"p-4 bg-gray-50 dark:bg-gray-800 rounded-md",children:[e.jsx("p",{className:"text-sm text-gray-600",children:o("tool.noParameters")}),e.jsxs("div",{className:"flex justify-end space-x-2 mt-4",children:[e.jsx("button",{type:"button",onClick:t,className:"hub-btn",children:o("tool.cancel")}),e.jsx("button",{onClick:()=>n({}),disabled:a,className:"hub-btn primary",children:o(a?"tool.running":"tool.runTool")})]})]})},st=({result:s,onClose:n})=>{const{t}=te(),a=s.content,x=r=>r?r.startsWith("image/")?r:`image/${r}`:"image/png",f=r=>{if(!r)return[];if(Array.isArray(r))return r.flatMap(g=>f(g));if(typeof r!="object")return[];const m=[];r.type==="image"&&r.data&&m.push({data:String(r.data),mimeType:x(r.mimeType||r.mime_type)});const z=r.image_base64||r.imageBase64||r.image_data||r.imageData||r.base64;return z&&m.push({data:String(z),mimeType:x(r.image_mimeType||r.image_mime_type||r.mimeType||r.mime_type)}),r.image&&typeof r.image=="object"&&m.push(...f(r.image)),Array.isArray(r.images)&&m.push(...f(r.images)),Array.isArray(r.content)&&m.push(...f(r.content)),m},o=r=>{const m=[];try{const F=JSON.parse(r);if(m.push(...f(F)),m.length>0)return m}catch{}const z=/data:image\/(png|jpe?g|gif|webp);base64,([A-Za-z0-9+/=]+)/g;let g;for(;(g=z.exec(r))!==null;){const F=`image/${g[1]==="jpg"?"jpeg":g[1]}`;m.push({data:g[2],mimeType:F})}return m},j=r=>{try{const m=JSON.parse(r),z=g=>{if(Array.isArray(g))return g.map(z);if(g&&typeof g=="object"){const F={};for(const[N,E]of Object.entries(g))typeof E=="string"&&N.toLowerCase().includes("base64")?F[N]="[base64 omitted]":F[N]=z(E);return F}return g};return JSON.stringify(z(m),null,2)}catch{return r.replace(/data:image\/(png|jpe?g|gif|webp);base64,[A-Za-z0-9+/=]+/g,"[image data omitted]")}},S=r=>Array.isArray(r)?r.map((m,z)=>e.jsx("div",{className:"mb-3 last:mb-0",children:D(m)},z)):D(r),D=r=>{if(typeof r=="string"){const m=o(r),z=j(r);return e.jsxs("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:[m.length>0&&e.jsx("div",{className:"mb-3 space-y-3",children:m.map((g,F)=>e.jsx("img",{src:`data:${g.mimeType||"image/png"};base64,${g.data}`,alt:t("tool.toolResult"),className:"max-w-full h-auto rounded-md"},F))}),e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:z})]})}if(typeof r=="object"&&r!==null){if(r.type==="text"&&r.text){const m=o(r.text),z=j(r.text);return e.jsxs("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:[m.length>0&&e.jsx("div",{className:"mb-3 space-y-3",children:m.map((g,F)=>e.jsx("img",{src:`data:${g.mimeType||"image/png"};base64,${g.data}`,alt:t("tool.toolResult"),className:"max-w-full h-auto rounded-md"},F))}),e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:z})]})}if(r.type==="image"&&r.data)return e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("img",{src:`data:${r.mimeType||"image/png"};base64,${r.data}`,alt:t("tool.toolResult"),className:"max-w-full h-auto rounded-md"})});try{const m=typeof r=="string"?JSON.parse(r):r;return e.jsxs("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:[e.jsx("div",{className:"text-xs text-gray-500 mb-2",children:t("tool.jsonResponse")}),e.jsx("pre",{className:"text-sm text-gray-800 overflow-auto",children:JSON.stringify(m,null,2)})]})}catch{return e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:String(r)})})}}return e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:String(r)})})};return e.jsxs("div",{className:"border border-gray-300 rounded-lg bg-white dark:bg-gray-800 shadow-sm",children:[e.jsx("div",{className:"border-b border-gray-300 px-4 py-3 bg-gray-50 dark:bg-gray-800 rounded-t-lg",children:e.jsxs("div",{className:"flex items-center justify-between",children:[e.jsxs("div",{className:"flex items-center space-x-2",children:[s.success?e.jsx(rs,{size:20,className:"text-status-green"}):e.jsx(ns,{size:20,className:"text-status-red"}),e.jsx("div",{children:e.jsxs("h4",{className:"text-sm font-medium text-gray-900",children:[t("tool.execution")," ",s.success?t("tool.successful"):t("tool.failed")]})})]}),e.jsx("button",{onClick:n,className:"text-gray-400 hover:text-gray-600 text-sm",children:"✕"})]})}),e.jsx("div",{className:"p-4",children:s.success?e.jsx("div",{children:s.content&&s.content.length>0?e.jsxs("div",{children:[e.jsx("div",{className:"text-sm text-gray-600 mb-3",children:t("tool.result")}),S(s.content)]}):e.jsx("div",{className:"text-sm text-gray-500 italic",children:t("tool.noContent")})}):e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-center space-x-2 mb-3",children:[e.jsx(we,{size:16,className:"text-red-500"}),e.jsx("span",{className:"text-sm font-medium text-red-700",children:t("tool.error")})]}),a&&a.length>0?e.jsxs("div",{children:[e.jsx("div",{className:"text-sm text-gray-600 mb-3",children:t("tool.errorDetails")}),S(a)]}):e.jsx("div",{className:"bg-red-50 border border-red-300 rounded-md p-3",children:e.jsx("pre",{className:"text-sm text-red-800 whitespace-pre-wrap",children:s.error||s.message||t("tool.unknownError")})})]})})]})},me=({title:s,onClick:n,disabled:t=!1,loading:a=!1})=>e.jsx("button",{type:"button",className:"ml-2 p-1 text-amber-600 hover:text-amber-700 cursor-pointer transition-colors disabled:opacity-60 disabled:cursor-not-allowed",onClick:n,disabled:t,title:s,"aria-label":s,children:e.jsx(Os,{size:14,className:a?"animate-spin":""})});function tt(s){return s==null?!0:typeof s=="string"?s.trim()==="":Array.isArray(s)?s.length===0:typeof s=="object"?Object.keys(s).length===0:!1}const rt=({tool:s,server:n,readOnly:t=!1,onToggle:a,onDescriptionUpdate:x,cost:f})=>{const{t:o}=te(),{showToast:j}=Pe(),{nameSeparator:S}=ze(),[D,r]=d.useState(!1),[m,z]=d.useState(!1),[g,F]=d.useState(!1),[N,E]=d.useState(null),[C,O]=d.useState(!1),[M,W]=d.useState(!1),[R,B]=d.useState(s.description||""),T=d.useRef(null),K=d.useRef(null),[q,X]=d.useState(0),[h,u]=d.useState(!1);d.useEffect(()=>{C&&T.current&&(T.current.focus(),q>0&&(T.current.style.width=`${q+20}px`))},[C,q]),d.useEffect(()=>{!C&&K.current&&X(K.current.offsetWidth)},[C,R]),d.useEffect(()=>{B(s.description||"")},[s.description]);const v=s.name.replace(n+S,""),l=Gs(s,o("tool.noDescription")),p=l.hasDescriptionOverride?o("tool.defaultDescriptionTooltip",{description:l.defaultDescription}):void 0,c=d.useCallback(()=>`mcphub_tool_form_${n?`${n}_`:""}${s.name}`,[s.name,n]),y=d.useCallback(()=>{localStorage.removeItem(c())},[c]),$=P=>{!t&&a&&a(s.name,P)},I=()=>{t||O(!0)},_=async()=>{if(!t)try{const P=await cs(n,s.name,R);P.success?(O(!1),x&&x(s.name,R)):(B(s.description||""),console.error("Failed to update tool description:",P.error))}catch(P){console.error("Error updating tool description:",P),B(s.description||""),O(!1)}},L=P=>{B(P.target.value)},Q=async()=>{if(!t){W(!0);try{const P=await ds(n,s.name);if(P.success){const H=P.description||"";B(H),O(!1),x==null||x(s.name,H,{restored:!0})}else j(P.error||o("tool.restoreDefaultFailed"),"error")}catch(P){console.error("Error resetting tool description:",P),j(o("tool.restoreDefaultFailed"),"error")}finally{W(!1)}}},A=P=>{P.key==="Enter"?_():P.key==="Escape"&&(B(s.description||""),O(!1))},k=async P=>{P.stopPropagation();try{if(navigator.clipboard&&window.isSecureContext)await navigator.clipboard.writeText(s.name),u(!0),j(o("common.copySuccess"),"success"),setTimeout(()=>u(!1),2e3);else{const H=document.createElement("textarea");H.value=s.name,H.style.position="fixed",H.style.left="-9999px",document.body.appendChild(H),H.focus(),H.select();try{document.execCommand("copy"),u(!0),j(o("common.copySuccess"),"success"),setTimeout(()=>u(!1),2e3)}catch(ce){j(o("common.copyFailed"),"error"),console.error("Copy to clipboard failed:",ce)}document.body.removeChild(H)}}catch(H){j(o("common.copyFailed"),"error"),console.error("Copy to clipboard failed:",H)}},U=async P=>{F(!0);try{P=Object.fromEntries(Object.entries(P).filter(([ce,V])=>!tt(V)));const H=await ls({toolName:s.name,arguments:P},n);E(H)}catch(H){E({success:!1,error:H instanceof Error?H.message:"Unknown error occurred"})}finally{F(!1)}},ee=()=>{z(!1),y(),E(null)},oe=()=>{E(null)};return e.jsxs("div",{className:"hub-card overflow-hidden",style:{marginBottom:8},children:[e.jsxs("div",{className:"flex justify-between items-center gap-2 px-3 py-2.5 cursor-pointer hover:bg-[var(--hub-surface-hover)] transition-colors",onClick:P=>{P.stopPropagation(),r(!D)},children:[e.jsxs("div",{className:"flex-1 min-w-0 flex items-center gap-1.5 flex-wrap",children:[e.jsx("span",{className:"hub-mono font-medium",style:{fontSize:13,color:"var(--hub-ink)"},children:v}),e.jsx("button",{className:"hub-icon-btn sm",onClick:k,title:o("common.copy"),children:h?e.jsx(xe,{size:12,style:{color:"var(--hub-ok)"}}):e.jsx(ye,{size:12})}),e.jsx("span",{className:"flex items-center gap-1",style:{fontSize:12,color:"var(--hub-ink-3)"},children:C?e.jsxs(e.Fragment,{children:[e.jsx("input",{ref:T,type:"text",className:"hub-input",style:{height:26,fontSize:12,width:q>0?`${q+20}px`:160,minWidth:80},value:R,onChange:L,onKeyDown:A,onClick:P=>P.stopPropagation()}),e.jsx("button",{className:"hub-icon-btn sm",onClick:P=>{P.stopPropagation(),_()},disabled:M,children:e.jsx(xe,{size:12,style:{color:"var(--hub-ok)"}})}),e.jsx(me,{title:o("tool.restoreDefault"),onClick:P=>{P.stopPropagation(),Q()},disabled:M,loading:M})]}):e.jsxs(e.Fragment,{children:[e.jsx("span",{ref:K,title:p,children:l.currentDescription}),l.hasDescriptionOverride&&e.jsx("span",{className:"inline-flex items-center rounded-full border px-1.5 py-0.5 text-[10px] font-medium",style:{color:"var(--hub-accent)",borderColor:"var(--hub-line)",background:"var(--hub-bg-2)"},title:p,children:o("tool.descriptionModifiedBadge")}),!t&&e.jsxs(e.Fragment,{children:[e.jsx("button",{className:"hub-icon-btn sm",onClick:P=>{P.stopPropagation(),I()},children:e.jsx(Te,{size:12})}),e.jsx(me,{title:o("tool.restoreDefault"),onClick:P=>{P.stopPropagation(),Q()},disabled:M,loading:M})]})]})})]}),e.jsxs("div",{className:"flex items-center gap-1.5 flex-shrink-0",children:[f!=null&&e.jsxs("span",{className:"hub-mono flex-shrink-0",style:{fontSize:11,color:"var(--hub-ink-3)"},title:o("cost.estimate"),children:["Σ ",ie(f)]}),e.jsx("div",{className:"flex h-[26px] items-center",onClick:P=>P.stopPropagation(),children:e.jsx(Ne,{checked:s.enabled??!0,onCheckedChange:$,disabled:g||t,size:"card","aria-label":`${o(s.enabled??!0?"server.disable":"server.enable")} ${v}`})}),e.jsxs("button",{onClick:P=>{P.stopPropagation(),r(!0),z(!0)},className:"hub-btn sm",style:{color:"var(--hub-accent)"},disabled:g||!s.enabled,children:[g?e.jsx(as,{size:12,className:"animate-spin"}):e.jsx(os,{size:12}),e.jsx("span",{children:o(g?"tool.running":"tool.run")})]}),e.jsx("button",{className:"hub-icon-btn sm",children:D?e.jsx($e,{size:14}):e.jsx(ke,{size:14})})]})]}),D&&e.jsxs("div",{style:{borderTop:"1px solid var(--hub-line-2)",padding:"10px 12px",display:"flex",flexDirection:"column",gap:10},children:[l.hasDescriptionOverride&&l.defaultDescription&&e.jsxs("div",{style:{background:"var(--hub-bg-2)",borderRadius:7,padding:"8px 12px",border:"1px dashed var(--hub-line)",fontSize:11.5,color:"var(--hub-ink-3)"},children:[e.jsx("span",{className:"hub-sect",style:{marginRight:6},children:o("tool.defaultDescriptionLabel")}),e.jsx("span",{className:"whitespace-pre-wrap break-words",children:l.defaultDescription})]}),!m&&e.jsxs("div",{style:{background:"var(--hub-bg-2)",borderRadius:7,padding:"8px 12px",border:"1px solid var(--hub-line)"},children:[e.jsx("div",{className:"hub-sect",style:{marginBottom:6},children:o("tool.inputSchema")}),e.jsx("pre",{className:"hub-mono overflow-auto",style:{fontSize:11.5,color:"var(--hub-ink-2)",margin:0},children:JSON.stringify(s.inputSchema,null,2)})]}),m&&e.jsxs("div",{style:{border:"1px solid var(--hub-line)",borderRadius:8,padding:14},children:[e.jsx(us,{schema:s.inputSchema||{type:"object"},onSubmit:U,onCancel:ee,loading:g,storageKey:c(),title:o("tool.runToolWithName",{name:v})}),N&&e.jsx("div",{style:{marginTop:12},children:e.jsx(st,{result:N,onClose:oe})})]})]})]})},nt=async(s,n)=>{try{const t=n?`/prompts/call/${n}`:"/prompts/call",a=await le(t,{promptName:s.promptName,arguments:s.arguments});return a.success?{success:!0,data:a.data}:{success:!1,error:a.message||"Prompt call failed"}}catch(t){return console.error("Error calling prompt",{promptName:s.promptName,server:n,error:t}),{success:!1,error:t instanceof Error?t.message:"Unknown error occurred"}}},ms=async(s,n)=>{try{const t=await le(`/mcp/${encodeURIComponent(n||"")}/prompts/${encodeURIComponent(s.promptName)}`,{name:s.promptName,arguments:s.arguments});if(!t.success)throw new Error(`Failed to get prompt: ${t.message||"Unknown error"}`);return{success:!0,data:t.data}}catch(t){return console.error("Error getting prompt",{promptName:s.promptName,server:n,error:t}),{success:!1,error:t instanceof Error?t.message:"Unknown error occurred"}}},at=async(s,n,t)=>{try{const a=await le(`/servers/${encodeURIComponent(s)}/prompts/${encodeURIComponent(n)}/toggle`,{enabled:t});return{success:a.success,error:a.success?void 0:a.message}}catch(a){return console.error("Error toggling prompt",{serverName:s,promptName:n,enabled:t,error:a}),{success:!1,error:a instanceof Error?a.message:"Unknown error occurred"}}},ps=async(s,n,t)=>{try{const a=await ve(`/servers/${encodeURIComponent(s)}/prompts/${encodeURIComponent(n)}/description`,{description:t},{headers:{Authorization:`Bearer ${localStorage.getItem("mcphub_token")}`}});return{success:a.success,error:a.success?void 0:a.message}}catch(a){return console.error("Error updating prompt description",{serverName:s,promptName:n,error:a}),{success:!1,error:a instanceof Error?a.message:"Unknown error occurred"}}},xs=async(s,n)=>{var t;try{const a=await ts(`/servers/${encodeURIComponent(s)}/prompts/${encodeURIComponent(n)}/description`,{headers:{Authorization:`Bearer ${localStorage.getItem("mcphub_token")}`}});return{success:a.success,error:a.success?void 0:a.message,description:(t=a.data)==null?void 0:t.description}}catch(a){return console.error("Error resetting prompt description",{serverName:s,promptName:n,error:a}),{success:!1,error:a instanceof Error?a.message:"Unknown error occurred"}}},ot=Object.freeze(Object.defineProperty({__proto__:null,callPrompt:nt,getPrompt:ms,resetPromptDescription:xs,togglePrompt:at,updatePromptDescription:ps},Symbol.toStringTag,{value:"Module"})),Ye=({result:s,onClose:n})=>{const{t}=te(),a=x=>{if(typeof x=="string")return e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:x})});if(typeof x=="object"&&x!==null){if(x.description||x.messages)return e.jsxs("div",{className:"space-y-4",children:[x.description&&e.jsxs("div",{children:[e.jsx("h4",{className:"text-sm font-medium text-gray-900 mb-2",children:t("prompt.description")}),e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("p",{className:"text-sm text-gray-800",children:x.description})})]}),x.messages&&e.jsxs("div",{children:[e.jsx("h4",{className:"text-sm font-medium text-gray-900 mb-2",children:t("prompt.messages")}),e.jsx("div",{className:"space-y-3",children:x.messages.map((f,o)=>e.jsxs("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:[e.jsx("div",{className:"flex items-center mb-2",children:e.jsxs("span",{className:"inline-block w-16 text-xs font-medium text-gray-500",children:[f.role,":"]})}),typeof f.content=="string"?e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:f.content}):typeof f.content=="object"&&f.content.type==="text"?e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:f.content.text}):e.jsx("pre",{className:"text-sm text-gray-800 overflow-auto",children:JSON.stringify(f.content,null,2)})]},o))})]})]});try{const f=typeof x=="string"?JSON.parse(x):x;return e.jsxs("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:[e.jsx("div",{className:"text-xs text-gray-500 mb-2",children:t("prompt.jsonResponse")}),e.jsx("pre",{className:"text-sm text-gray-800 overflow-auto",children:JSON.stringify(f,null,2)})]})}catch{return e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:String(x)})})}}return e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 rounded-md p-3",children:e.jsx("pre",{className:"whitespace-pre-wrap text-sm text-gray-800 font-mono",children:String(x)})})};return e.jsxs("div",{className:"border border-gray-300 rounded-lg bg-white dark:bg-gray-800 shadow-sm",children:[e.jsx("div",{className:"border-b border-gray-300 px-4 py-3 bg-gray-50 dark:bg-gray-800 rounded-t-lg",children:e.jsxs("div",{className:"flex items-center justify-between",children:[e.jsxs("div",{className:"flex items-center space-x-2",children:[s.success?e.jsx(rs,{size:20,className:"text-status-green"}):e.jsx(ns,{size:20,className:"text-status-red"}),e.jsx("div",{children:e.jsxs("h4",{className:"text-sm font-medium text-gray-900",children:[t("prompt.execution")," ",s.success?t("prompt.successful"):t("prompt.failed")]})})]}),e.jsx("button",{onClick:n,className:"text-gray-400 hover:text-gray-600 text-sm",children:"✕"})]})}),e.jsx("div",{className:"p-4",children:s.success?e.jsx("div",{children:s.data?e.jsxs("div",{children:[e.jsx("div",{className:"text-sm text-gray-600 mb-3",children:t("prompt.result")}),a(s.data)]}):e.jsx("div",{className:"text-sm text-gray-500 italic",children:t("prompt.noContent")})}):e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-center space-x-2 mb-3",children:[e.jsx(we,{size:16,className:"text-red-500"}),e.jsx("span",{className:"text-sm font-medium text-red-700",children:t("prompt.error")})]}),e.jsx("div",{className:"bg-red-50 border border-red-300 rounded-md p-3",children:e.jsx("pre",{className:"text-sm text-red-800 whitespace-pre-wrap",children:s.error||s.message||t("prompt.unknownError")})})]})})]})},it=({prompt:s,server:n,readOnly:t=!1,onToggle:a,onDescriptionUpdate:x,cost:f})=>{const{t:o}=te(),{showToast:j}=Pe(),{nameSeparator:S}=ze(),[D,r]=d.useState(!1),[m,z]=d.useState(!1),[g,F]=d.useState(!1),[N,E]=d.useState(null),[C,O]=d.useState(!1),[M,W]=d.useState(!1),[R,B]=d.useState(s.description||""),T=d.useRef(null),K=d.useRef(null),[q,X]=d.useState(0);d.useEffect(()=>{C&&T.current&&(T.current.focus(),q>0&&(T.current.style.width=`${q+20}px`))},[C,q]),d.useEffect(()=>{!C&&K.current&&X(K.current.offsetWidth)},[C,R]),d.useEffect(()=>{B(s.description||"")},[s.description]);const h=d.useCallback(()=>`mcphub_prompt_form_${n?`${n}_`:""}${s.name}`,[s.name,n]),u=d.useCallback(()=>{localStorage.removeItem(h())},[h]),v=k=>{!t&&a&&a(s.name,k)},l=()=>{t||O(!0)},p=async()=>{if(!t){O(!1);try{const k=await ps(n,s.name,R);k.success?x&&x(s.name,R):(j(k.error||o("prompt.descriptionUpdateFailed"),"error"),B(s.description||""))}catch(k){console.error("Error updating prompt description:",k),j(o("prompt.descriptionUpdateFailed"),"error"),B(s.description||"")}}},c=async()=>{if(!t){W(!0);try{const k=await xs(n,s.name);if(k.success){const U=k.description||"";B(U),O(!1),x==null||x(s.name,U,{restored:!0})}else j(k.error||o("prompt.restoreDefaultFailed"),"error")}catch(k){console.error("Error resetting prompt description:",k),j(o("prompt.restoreDefaultFailed"),"error")}finally{W(!1)}}},y=k=>{B(k.target.value)},$=k=>{k.key==="Enter"?p():k.key==="Escape"&&(B(s.description||""),O(!1))},I=async k=>{F(!0);try{const U=await ms({promptName:s.name,arguments:k},n);console.log("GetPrompt result:",U),E({success:U.success,data:U.data,error:U.error})}catch(U){E({success:!1,error:U instanceof Error?U.message:"Unknown error occurred"})}finally{F(!1)}},_=()=>{z(!1),u(),E(null)},L=()=>{E(null)},Q=s.name.replace(n+S,""),A=()=>{if(!s.arguments||s.arguments.length===0)return{type:"object",properties:{},required:[]};const k={},U=[];return s.arguments.forEach(ee=>{k[ee.name]={type:"string",description:ee.description||""},ee.required&&U.push(ee.name)}),{type:"object",properties:k,required:U}};return e.jsxs("div",{className:"hub-card overflow-hidden",style:{marginBottom:8},children:[e.jsxs("div",{className:"flex justify-between items-center gap-2 px-3 py-2.5 cursor-pointer hover:bg-[var(--hub-surface-hover)] transition-colors",onClick:()=>r(!D),children:[e.jsxs("div",{className:"flex-1 min-w-0 flex items-center gap-1.5 flex-wrap",children:[e.jsx("span",{className:"hub-mono font-medium",style:{fontSize:13,color:"var(--hub-ink)"},children:Q}),s.title&&e.jsx("span",{style:{fontSize:12,color:"var(--hub-ink-2)"},children:s.title}),e.jsx("span",{className:"flex items-center gap-1",style:{fontSize:12,color:"var(--hub-ink-3)"},children:C?e.jsxs(e.Fragment,{children:[e.jsx("input",{ref:T,type:"text",className:"hub-input",style:{height:26,fontSize:12,width:q>0?`${q+20}px`:160,minWidth:80},value:R,onChange:y,onKeyDown:$,onClick:k=>k.stopPropagation()}),e.jsx("button",{className:"hub-icon-btn sm",onClick:k=>{k.stopPropagation(),p()},disabled:M,children:e.jsx(xe,{size:12,style:{color:"var(--hub-ok)"}})}),e.jsx(me,{title:o("prompt.restoreDefault"),onClick:k=>{k.stopPropagation(),c()},disabled:M,loading:M})]}):e.jsxs(e.Fragment,{children:[e.jsx("span",{ref:K,children:R||o("tool.noDescription")}),!t&&e.jsxs(e.Fragment,{children:[e.jsx("button",{className:"hub-icon-btn sm",onClick:k=>{k.stopPropagation(),l()},children:e.jsx(Te,{size:12})}),e.jsx(me,{title:o("prompt.restoreDefault"),onClick:k=>{k.stopPropagation(),c()},disabled:M,loading:M})]})]})})]}),e.jsxs("div",{className:"flex items-center gap-1.5 flex-shrink-0",children:[f!=null&&e.jsxs("span",{className:"hub-mono flex-shrink-0",style:{fontSize:11,color:"var(--hub-ink-3)"},title:o("cost.estimate"),children:["Σ ",ie(f)]}),e.jsx("div",{className:"flex h-[26px] items-center",onClick:k=>k.stopPropagation(),children:s.enabled!==void 0&&e.jsx(Ne,{checked:s.enabled,onCheckedChange:v,disabled:g||t,size:"card","aria-label":`${o(s.enabled?"server.disable":"server.enable")} ${Q}`})}),e.jsxs("button",{onClick:k=>{k.stopPropagation(),r(!0),z(!0)},className:"hub-btn sm",style:{color:"var(--hub-accent)"},disabled:g||!s.enabled,children:[g?e.jsx(as,{size:12,className:"animate-spin"}):e.jsx(os,{size:12}),e.jsx("span",{children:o(g?"tool.running":"tool.run")})]}),e.jsx("button",{className:"hub-icon-btn sm",children:D?e.jsx($e,{size:14}):e.jsx(ke,{size:14})})]})]}),D&&e.jsxs("div",{style:{borderTop:"1px solid var(--hub-line-2)",padding:"10px 12px",display:"flex",flexDirection:"column",gap:10},children:[m&&e.jsxs("div",{style:{border:"1px solid var(--hub-line)",borderRadius:8,padding:14},children:[e.jsx(us,{schema:A(),onSubmit:I,onCancel:_,loading:g,storageKey:h(),title:o("prompt.runPromptWithName",{name:Q})}),N&&e.jsx("div",{style:{marginTop:12},children:e.jsx(Ye,{result:N,onClose:L})})]}),!m&&s.arguments&&s.arguments.length>0&&e.jsxs("div",{style:{background:"var(--hub-bg-2)",borderRadius:7,padding:"8px 12px",border:"1px solid var(--hub-line)"},children:[e.jsx("div",{className:"hub-sect",style:{marginBottom:6},children:o("tool.parameters")}),e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:6},children:s.arguments.map((k,U)=>e.jsxs("div",{className:"flex items-start gap-2",children:[e.jsxs("div",{className:"flex-1",children:[e.jsxs("div",{className:"flex items-center gap-1",children:[e.jsx("span",{className:"hub-mono",style:{fontSize:12.5,color:"var(--hub-ink)"},children:k.name}),k.required&&e.jsx("span",{style:{color:"var(--hub-err)",fontSize:12},children:"*"})]}),k.description&&e.jsx("p",{style:{fontSize:12,color:"var(--hub-ink-3)",margin:"2px 0 0"},children:k.description})]}),k.title&&e.jsx("span",{style:{fontSize:11,color:"var(--hub-ink-3)"},children:k.title})]},U))})]}),!m&&N&&e.jsx("div",{children:e.jsx(Ye,{result:N,onClose:L})})]})]})},lt=({resource:s,readOnly:n=!1,onToggle:t,onDescriptionUpdate:a,cost:x})=>{const{t:f}=te(),[o,j]=d.useState(!1),[S,D]=d.useState(!1),[r,m]=d.useState(!1),[z,g]=d.useState(s.description||""),F=d.useRef(null),N=d.useRef(null),[E,C]=d.useState(0);d.useEffect(()=>{S&&F.current&&(F.current.focus(),E>0&&(F.current.style.width=`${E+20}px`))},[S,E]),d.useEffect(()=>{!S&&N.current&&C(N.current.offsetWidth)},[S,z]),d.useEffect(()=>{g(s.description||"")},[s.description]);const O=s.name||s.uri,M=T=>{!n&&t&&t(s.uri,T)},W=async()=>{n||(D(!1),a&&await a(s.uri,z))},R=async()=>{if(!n){m(!0);try{await(a==null?void 0:a(s.uri,"",{restored:!0})),D(!1)}finally{m(!1)}}},B=T=>{T.key==="Enter"?W():T.key==="Escape"&&(g(s.description||""),D(!1))};return e.jsxs("div",{className:"hub-card overflow-hidden",style:{marginBottom:8},children:[e.jsxs("div",{className:"flex justify-between items-center gap-2 px-3 py-2.5 cursor-pointer hover:bg-[var(--hub-surface-hover)] transition-colors",onClick:()=>j(!o),children:[e.jsxs("div",{className:"flex-1 min-w-0",children:[e.jsxs("div",{className:"flex items-center gap-1.5 flex-wrap",children:[e.jsx("span",{className:"hub-mono font-medium truncate",style:{fontSize:13,color:"var(--hub-ink)"},children:O}),e.jsx("span",{className:"hub-mono truncate",style:{fontSize:11.5,color:"var(--hub-ink-3)"},children:s.uri})]}),e.jsx("span",{className:"flex items-center gap-1 mt-0.5",style:{fontSize:12,color:"var(--hub-ink-3)"},children:S?e.jsxs(e.Fragment,{children:[e.jsx("input",{ref:F,type:"text",className:"hub-input",style:{height:26,fontSize:12,width:E>0?`${E+20}px`:160,minWidth:80},value:z,onChange:T=>g(T.target.value),onKeyDown:B,onClick:T=>T.stopPropagation()}),e.jsx("button",{className:"hub-icon-btn sm",onClick:T=>{T.stopPropagation(),W()},disabled:r,children:e.jsx(xe,{size:12,style:{color:"var(--hub-ok)"}})}),e.jsx(me,{title:f("builtinResources.restoreDefault"),onClick:T=>{T.stopPropagation(),R()},disabled:r,loading:r})]}):e.jsxs(e.Fragment,{children:[e.jsx("span",{ref:N,children:z||f("tool.noDescription")}),!n&&e.jsxs(e.Fragment,{children:[e.jsx("button",{className:"hub-icon-btn sm",onClick:T=>{T.stopPropagation(),D(!0)},children:e.jsx(Te,{size:12})}),e.jsx(me,{title:f("builtinResources.restoreDefault"),onClick:T=>{T.stopPropagation(),R()},disabled:r,loading:r})]})]})})]}),e.jsxs("div",{className:"flex items-center gap-1.5 flex-shrink-0",children:[x!=null&&e.jsxs("span",{className:"hub-mono flex-shrink-0",style:{fontSize:11,color:"var(--hub-ink-3)"},title:f("cost.estimate"),children:["Σ ",ie(x)]}),e.jsx("div",{className:"flex h-[26px] items-center",onClick:T=>T.stopPropagation(),children:e.jsx(Ne,{checked:s.enabled!==!1,onCheckedChange:M,disabled:n,size:"card","aria-label":`${f(s.enabled!==!1?"server.disable":"server.enable")} ${O}`})}),e.jsx("button",{className:"hub-icon-btn sm",children:o?e.jsx($e,{size:14}):e.jsx(ke,{size:14})})]})]}),o&&e.jsxs("div",{style:{borderTop:"1px solid var(--hub-line-2)",padding:"8px 12px"},children:[e.jsxs("span",{className:"hub-sect",children:[f("builtinResources.mimeType"),":"]})," ",e.jsx("span",{style:{fontSize:12,color:"var(--hub-ink-2)"},children:s.mimeType||"text/plain"})]})]})},ct=(s,n)=>n?n.isAdmin?!0:!!(s.owner&&s.owner===n.username):!1,dt={private:{shortKey:"server.visibilityPrivateShort",shortFallback:"Private",longKey:"server.visibilityPrivate",longFallback:"Private — only the owner and admins",className:"bg-[var(--hub-bg-2)] text-[var(--hub-ink-2)] border-[var(--hub-line-2)]"},group:{shortKey:"server.visibilityGroupShort",shortFallback:"Group",longKey:"server.visibilityGroup",longFallback:"Group (reserved — not yet implemented)",className:"bg-[oklch(0.97_0.02_85)] text-[oklch(0.45_0.07_85)] border-[oklch(0.88_0.04_85)]"},public:{shortKey:"server.visibilityPublicShort",shortFallback:"Public",longKey:"server.visibilityPublic",longFallback:"Public — every authenticated user",className:"bg-[oklch(0.97_0.03_145)] text-[oklch(0.42_0.12_145)] border-[oklch(0.88_0.04_145)]"}},Fe=s=>s==="public"||s==="group"?s:"private",ut=(s,n)=>{const t=Fe(n),a=dt[t];return{value:t,shortLabel:s(a.shortKey,{defaultValue:a.shortFallback}),longLabel:s(a.longKey,{defaultValue:a.longFallback}),className:a.className}},mt=(s,n)=>{const t=Fe(n),a=[{value:"private",label:s("server.visibilityPrivateShort",{defaultValue:"Private"}),disabled:!1}];return t==="group"&&a.push({value:"group",label:s("server.visibilityGroupShort",{defaultValue:"Group"}),disabled:!0}),a.push({value:"public",label:s("server.visibilityPublicShort",{defaultValue:"Public"}),disabled:!1}),a},Ze=({isLoading:s,children:n,className:t,overlayStyle:a,spinnerSize:x=12})=>e.jsxs("div",{className:t?`relative flex items-center ${t}`:"relative flex items-center","aria-busy":s,children:[e.jsx("div",{className:"flex w-full items-center justify-center",style:{visibility:s?"hidden":"visible",pointerEvents:s?"none":"auto"},children:n}),s&&e.jsx("div",{className:"pointer-events-none absolute inset-0 flex items-center justify-center",style:{background:"var(--hub-surface)",border:"1px solid var(--hub-line-2)",borderRadius:8,...a},children:e.jsx(je,{size:x,className:"animate-spin",style:{color:"var(--hub-ink-3)"}})})]}),Qe=({icon:s})=>e.jsx("span",{className:"hub-server-capability-icon","aria-hidden":"true",children:e.jsx(s,{size:11.5,strokeWidth:1.9,className:"block"})}),es=(s,n)=>n?n==="stdio"?s("server.typeStdio")||"stdio":n==="sse"?s("server.typeSse")||"sse":n==="streamable-http"?s("server.typeStreamableHttp")||"http":n==="openapi"?s("server.typeOpenapi")||"openapi":n:null,pt="text/html;profile=mcp-app",ss=s=>s?!!(s.ui||s["ui/resourceUri"]):!1,xt=s=>{var n,t;return!!((n=s.tools)!=null&&n.some(a=>ss(a._meta))||(t=s.resources)!=null&&t.some(a=>{var x;return((x=a.uri)==null?void 0:x.startsWith("ui://"))||a.mimeType===pt||ss(a._meta)}))},ht=({server:s,cost:n,onRemove:t,onEdit:a,onToggle:x,onVisibilityChange:f,onRefresh:o,onReload:j,onReinstall:S,onOAuthDisconnect:D})=>{var _e,Ae,Me,Ve,Je,Ue,Be,Le,We,qe,He,Ke,Ge,Xe;const{t:r}=te(),{showToast:m}=Pe(),{exportMCPSettings:z,installConfig:g}=ze(),{auth:F}=Ps(),N=((_e=g==null?void 0:g.baseUrl)==null?void 0:_e.replace(/\/+$/,""))||"",[E,C]=d.useState(!1),[O,M]=d.useState(null),[W,R]=d.useState(!1),[B,T]=d.useState(!1),[K,q]=d.useState(!1),[X,h]=d.useState(!1),[u,v]=d.useState(!1),[l,p]=d.useState(!1),[c,y]=d.useState(!1),[$,I]=d.useState(!1),[_,L]=d.useState(!1),[Q,A]=d.useState(!1),[k,U]=d.useState(!1),ee=d.useRef(null),oe=d.useRef(null);d.useEffect(()=>{const i=b=>{ee.current&&!ee.current.contains(b.target)&&L(!1),oe.current&&!oe.current.contains(b.target)&&A(!1)};return document.addEventListener("mousedown",i),()=>document.removeEventListener("mousedown",i)},[]);const P=((Ae=s.tools)==null?void 0:Ae.length)||0,H=((Me=s.tools)==null?void 0:Me.filter(i=>i.enabled!==!1).length)||0,ce=((Ve=s.prompts)==null?void 0:Ve.length)||0,V=((Je=s.prompts)==null?void 0:Je.filter(i=>i.enabled!==!1).length)||0,Z=((Ue=s.resources)==null?void 0:Ue.length)||0,se=((Be=s.resources)==null?void 0:Be.filter(i=>i.enabled!==!1).length)||0,he=xt(s),ae=s.enabled!==!1,G=ct(s,F.user),Y=((Le=s.config)==null?void 0:Le.command)==="npx"||((We=s.config)==null?void 0:We.command)==="uvx",re=!!((qe=s.oauth)!=null&&qe.connected&&D),be=async i=>{if(!(!G||X||!x)){h(!0);try{await x(s,i)}finally{h(!1)}}},fe=async i=>{if(i.stopPropagation(),L(!1),!(!G||l||!j)){p(!0);try{await j(s)?m(r("server.reloadSuccess")||"Server reloaded successfully","success"):m(r("server.reloadError",{serverName:s.name})||"Failed to reload","error")}finally{p(!1)}}},Ce=async()=>{if(L(!1),!(!G||c||!S)){y(!0);try{await S(s)?m(r("server.reinstallSuccess")||"Server reinstall initiated","success"):m(r("server.reinstallError",{serverName:s.name})||"Failed to reinstall","error")}finally{y(!1)}}},pe=async()=>{if(L(!1),!(!G||$||!D)){I(!0);try{await D(s)?m(r("server.disconnectOAuthSuccess")||"Server OAuth disconnected","success"):m(r("server.disconnectOAuthError",{serverName:s.name})||"Failed to disconnect OAuth","error")}finally{I(!1)}}},hs=async i=>{var w;if(i.stopPropagation(),!G||u||!f)return;const b=i.target.value;if(b!==Fe(s.visibility??((w=s.config)==null?void 0:w.visibility))){v(!0);try{await f(s,b)}finally{v(!1)}}},Se=async i=>{try{if(navigator.clipboard&&window.isSecureContext)return await navigator.clipboard.writeText(i),!0}catch{}try{const b=document.createElement("textarea");b.value=i,b.style.position="fixed",b.style.left="-9999px",document.body.appendChild(b),b.focus(),b.select();const w=document.execCommand("copy");return document.body.removeChild(b),w}catch{return!1}},bs=async i=>{if(i.stopPropagation(),!s.error)return;await Se(s.error)?(U(!0),m(r("common.copySuccess")||"Copied","success"),setTimeout(()=>U(!1),1500)):m(r("common.copyFailed")||"Copy failed","error")},fs=async i=>{if(i.stopPropagation(),L(!1),!!G)try{const b=await z(s.name);if(!b||!b.success||!b.data){m((b==null?void 0:b.message)||r("common.copyFailed")||"Copy failed","error");return}const w=JSON.stringify(b.data,null,2),J=await Se(w);m(J?r("common.copySuccess")||"Copied":r("common.copyFailed")||"Copy failed",J?"success":"error")}catch(b){console.error("Error copying server configuration:",b),m(r("common.copyFailed")||"Copy failed","error")}},gs=i=>{var b;if(i.stopPropagation(),(b=s.oauth)!=null&&b.authorizationUrl){const ne=window.screen.width/2-300,de=window.screen.height/2-700/2;window.open(s.oauth.authorizationUrl,"OAuth Authorization",`width=600,height=700,left=${ne},top=${de}`),m(r("status.oauthWindowOpened"),"info")}},ys=async(i,b)=>{try{const{toggleTool:w}=await ge(async()=>{const{toggleTool:ne}=await Promise.resolve().then(()=>et);return{toggleTool:ne}},void 0,import.meta.url),J=await w(s.name,i,b);J.success?(m(r(b?"tool.enableSuccess":"tool.disableSuccess",{name:i}),"success"),o==null||o()):m(J.error||r("tool.toggleFailed"),"error")}catch(w){console.error(w),m(r("tool.toggleFailed"),"error")}},js=async(i,b)=>{try{const{togglePrompt:w}=await ge(async()=>{const{togglePrompt:ne}=await Promise.resolve().then(()=>ot);return{togglePrompt:ne}},void 0,import.meta.url),J=await w(s.name,i,b);J.success?(m(r(b?"tool.enableSuccess":"tool.disableSuccess",{name:i}),"success"),o==null||o()):m(J.error||r("tool.toggleFailed"),"error")}catch(w){console.error(w),m(r("tool.toggleFailed"),"error")}},vs=async(i,b)=>{try{const{toggleResource:w}=await ge(async()=>{const{toggleResource:ne}=await import("./resourceService-CJciejgX.js");return{toggleResource:ne}},__vite__mapDeps([0,1,2,3,4,5]),import.meta.url),J=await w(s.name,i,b);J.success?(m(r(b?"tool.enableSuccess":"tool.disableSuccess",{name:i}),"success"),o==null||o()):m(J.error||r("tool.toggleFailed"),"error")}catch(w){console.error(w),m(r("tool.toggleFailed"),"error")}},Ns=(i,b,w)=>{m(w!=null&&w.restored?r("tool.restoreDefaultSuccess"):r("tool.descriptionUpdateSuccess"),"success"),o==null||o()},ws=(i,b,w)=>{m(w!=null&&w.restored?r("prompt.restoreDefaultSuccess"):r("prompt.descriptionUpdateSuccess"),"success"),o==null||o()},ks=async(i,b,w)=>{try{const{updateResourceDescription:J,resetResourceDescription:ne}=await ge(async()=>{const{updateResourceDescription:Ss,resetResourceDescription:Es}=await import("./resourceService-CJciejgX.js");return{updateResourceDescription:Ss,resetResourceDescription:Es}},__vite__mapDeps([0,1,2,3,4,5]),import.meta.url),de=w!=null&&w.restored?await ne(s.name,i):await J(s.name,i,b);de.success?(m(w!=null&&w.restored?r("builtinResources.restoreDefaultSuccess"):r("builtinResources.descriptionUpdateSuccess"),"success"),o==null||o()):m(de.error||(w!=null&&w.restored?r("builtinResources.restoreDefaultFailed"):r("builtinResources.descriptionUpdateFailed")),"error")}catch(J){console.error(J),m(w!=null&&w.restored?r("builtinResources.restoreDefaultFailed"):r("builtinResources.descriptionUpdateFailed"),"error")}};(()=>{var w;const i=s.config;if(!i)return"";if(i.url)return i.url;const b=[];return i.command&&b.push(i.command),(w=i.args)!=null&&w.length&&b.push(...i.args),b.join(" ")})();const Ie=`${N}/mcp/${s.name}`,Re=(i,b)=>r(i,b),ue=ut(Re,s.visibility??((He=s.config)==null?void 0:He.visibility)),Cs=mt(Re,ue.value),Oe=[{key:"tools",icon:_s,total:P,enabled:H,label:r("server.tools")},{key:"prompts",icon:As,total:ce,enabled:V,label:r("server.prompts")},{key:"resources",icon:Ms,total:Z,enabled:se,label:r("nav.resources")}];return e.jsxs(e.Fragment,{children:[e.jsxs("div",{className:"hub-card overflow-visible",style:{marginBottom:10},children:[e.jsxs("div",{className:"hub-server-card-row cursor-pointer px-4 py-3 transition-colors hover:bg-[var(--hub-surface-hover)]",onClick:()=>C(!E),children:[e.jsxs("div",{className:"flex items-center gap-2.5 min-w-0",children:[e.jsx(ke,{size:12,style:{color:"var(--hub-ink-3)",transform:E?"rotate(90deg)":"none",transition:"transform 0.15s",flexShrink:0}}),e.jsxs("div",{className:"min-w-0",children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("span",{className:"hub-mono truncate",style:{fontSize:13.5,color:ae?"var(--hub-ink)":"var(--hub-ink-3)"},children:s.name}),he&&e.jsx("span",{className:"hub-tag accent flex-shrink-0",title:r("server.mcpApp"),children:"App"}),s.error&&e.jsxs("div",{className:"relative",ref:oe,children:[e.jsx("button",{onClick:i=>{i.stopPropagation(),A(b=>!b)},className:"text-[var(--hub-err)] hover:opacity-80","aria-label":r("server.viewErrorDetails"),children:e.jsx(we,{size:14})}),Q&&e.jsxs("div",{className:"absolute z-20 mt-1.5 hub-card",style:{left:0,top:"100%",width:460,maxHeight:320,overflow:"hidden",boxShadow:"0 8px 24px rgba(0,0,0,0.08)"},onClick:i=>i.stopPropagation(),children:[e.jsxs("div",{className:"flex items-center justify-between px-3 py-2",style:{borderBottom:"1px solid var(--hub-line-2)"},children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("span",{className:"text-[12px] font-medium",style:{color:"var(--hub-err)"},children:r("server.errorDetails")}),e.jsx("button",{onClick:bs,className:"hub-icon-btn sm",title:r("common.copy"),children:k?e.jsx(xe,{size:12,className:"text-[var(--hub-ok)]"}):e.jsx(ye,{size:12})})]}),e.jsx("button",{onClick:()=>A(!1),className:"hub-icon-btn sm","aria-label":r("app.closeButton"),children:e.jsx(Ee,{size:12})})]}),e.jsx("div",{className:"p-3 overflow-auto hub-mono",style:{maxHeight:260,fontSize:12},children:e.jsx("pre",{className:"whitespace-pre-wrap break-words m-0",style:{color:"var(--hub-ink-2)"},children:s.error})})]})]})]}),((Ke=s.config)==null?void 0:Ke.description)&&e.jsx("div",{className:"text-[11.5px] truncate",style:{color:"var(--hub-ink-3)",marginTop:1},title:s.config.description,children:s.config.description})]})]}),e.jsx("div",{className:"hub-server-card-status-cell min-w-0",children:e.jsx(Rs,{status:s.status,enabled:s.enabled,startOnDemand:((Ge=s.config)==null?void 0:Ge.startOnDemand)===!0,onAuthClick:gs,className:"hub-server-card-status"})}),e.jsx("div",{className:"hub-server-card-transport-cell min-w-0",children:(Xe=s.config)!=null&&Xe.type?e.jsx("span",{className:"hub-tag hub-server-card-transport-tag",title:es(r,s.config.type)??void 0,children:es(r,s.config.type)}):e.jsx("span",{style:{color:"var(--hub-ink-3)",fontSize:12},children:"—"})}),e.jsx("div",{className:"hub-server-card-visibility min-w-0",onClick:i=>i.stopPropagation(),children:G&&f?e.jsx(Ze,{isLoading:u,className:"w-full",overlayStyle:{borderRadius:6},children:e.jsx("select",{value:ue.value,onChange:hs,disabled:u,className:"hub-server-card-select w-full rounded-md border px-2 py-1 text-[11.5px] bg-[var(--hub-surface)] text-[var(--hub-ink)]",style:{borderColor:"var(--hub-line-2)"},"aria-label":r("server.visibility","Visibility"),title:ue.longLabel,children:Cs.map(i=>e.jsx("option",{value:i.value,disabled:i.disabled,children:i.label},i.value))})}):e.jsx("span",{className:`hub-server-card-visibility-badge inline-flex items-center rounded-md border px-2 py-0.5 text-[11.5px] ${ue.className}`,title:ue.longLabel,children:ue.shortLabel})}),Oe.map(({key:i,icon:b,total:w,enabled:J,label:ne})=>{const de=w===0;return e.jsxs("span",{className:`hub-server-capability-stat hub-mono hub-num ${de?"is-empty":""}`,title:`${ne}: ${J}/${w}`,children:[e.jsx("span",{className:"text-[var(--hub-ink-3)]",children:e.jsx(Qe,{icon:b})}),e.jsx("span",{className:"hub-server-capability-value",children:de?"0":`${J}/${w}`})]},i)}),n&&n.connected?e.jsxs("span",{className:"hub-server-capability-stat hub-mono hub-num",title:`${r("cost.exposed")} ${n.exposed} / ${r("cost.gross")} ${n.gross} · ${r("cost.estimate")}`,children:[e.jsx("span",{className:"text-[var(--hub-ink-3)]",children:"Σ"}),e.jsxs("span",{className:"hub-server-capability-value",children:[ie(n.exposed),"/",ie(n.gross)]})]}):n?e.jsx("span",{className:"hub-server-capability-stat hub-mono is-empty",title:r("cost.notConnected"),children:e.jsx("span",{className:"hub-server-capability-value",children:"—"})}):null,e.jsx("div",{className:"flex items-center justify-center",onClick:i=>i.stopPropagation(),children:e.jsx(Ze,{isLoading:X,className:"h-[18px] w-[30px]",overlayStyle:{borderRadius:999,background:"var(--hub-bg-2)"},spinnerSize:10,children:e.jsx(Ne,{checked:ae,onCheckedChange:be,disabled:X||!G,size:"compact","aria-label":`${r(ae?"server.disable":"server.enable")} ${s.name}`})})}),e.jsxs("div",{className:"relative",ref:ee,children:[G&&e.jsx("button",{className:"hub-icon-btn",onClick:i=>{i.stopPropagation(),L(b=>!b)},"aria-label":"More",children:e.jsx(Vs,{size:14})}),G&&_&&e.jsxs("div",{className:"absolute right-0 top-full mt-1 z-20 hub-card",style:{minWidth:160,padding:4},onClick:i=>i.stopPropagation(),children:[e.jsxs("button",{onClick:i=>{i.stopPropagation(),L(!1),a(s)},className:"flex items-center gap-2 w-full px-2.5 py-1.5 text-[13px] rounded-md hover:bg-[var(--hub-surface-hover)] text-left",style:{color:"var(--hub-ink)"},children:[e.jsx(Js,{size:13})," ",r("server.edit")]}),e.jsxs("button",{onClick:fs,className:"flex items-center gap-2 w-full px-2.5 py-1.5 text-[13px] rounded-md hover:bg-[var(--hub-surface-hover)] text-left",style:{color:"var(--hub-ink)"},children:[e.jsx(ye,{size:13})," ",r("server.copy")]}),j&&e.jsxs("button",{onClick:fe,disabled:l||X||!ae,className:"flex items-center gap-2 w-full px-2.5 py-1.5 text-[13px] rounded-md hover:bg-[var(--hub-surface-hover)] text-left disabled:opacity-50 disabled:cursor-not-allowed",style:{color:"var(--hub-ink)"},children:[e.jsx(je,{size:13})," ",r("server.reload")]}),S&&Y&&e.jsxs("button",{onClick:i=>{i.stopPropagation(),L(!1),!(!G||c||!ae)&&T(!0)},disabled:c||X||!ae,className:"flex items-center gap-2 w-full px-2.5 py-1.5 text-[13px] rounded-md hover:bg-[var(--hub-surface-hover)] text-left disabled:opacity-50 disabled:cursor-not-allowed",style:{color:"var(--hub-ink)"},children:[e.jsx(Us,{size:13})," ",r("server.reinstall")]}),re&&e.jsxs("button",{onClick:i=>{i.stopPropagation(),L(!1),!(!G||$)&&q(!0)},disabled:$,className:"flex items-center gap-2 w-full px-2.5 py-1.5 text-[13px] rounded-md hover:bg-[var(--hub-surface-hover)] text-left disabled:opacity-50 disabled:cursor-not-allowed",style:{color:"var(--hub-ink)"},children:[e.jsx(Bs,{size:13})," ",r("server.disconnectOAuth")]}),e.jsx("div",{style:{height:1,background:"var(--hub-line-2)",margin:"4px 0"}}),e.jsxs("button",{onClick:i=>{i.stopPropagation(),L(!1),R(!0)},className:"flex items-center gap-2 w-full px-2.5 py-1.5 text-[13px] rounded-md hover:bg-[var(--hub-surface-hover)] text-left",style:{color:"var(--hub-err)"},children:[e.jsx(Ls,{size:13})," ",r("server.delete")]})]})]})]}),E&&e.jsxs("div",{style:{borderTop:"1px solid var(--hub-line-2)",background:"var(--hub-bg-2)",padding:"14px 16px 16px 38px"},children:[e.jsxs("div",{className:"flex items-center gap-1 mb-2 flex-wrap",children:[Oe.map(i=>{const b=O===i.key,w=i.icon;return e.jsxs("button",{onClick:()=>M(b?null:i.key),className:"inline-flex items-center gap-1.5 px-2.5 py-1 rounded-md text-[12px] transition-colors hover:bg-[var(--hub-surface-hover)]",style:{background:b?"var(--hub-surface)":"transparent",border:"1px solid "+(b?"var(--hub-line)":"transparent"),color:b?"var(--hub-ink)":"var(--hub-ink-2)"},children:[e.jsx(Qe,{icon:w}),e.jsx("span",{children:i.label}),e.jsx("span",{className:"hub-mono hub-num",style:{color:"var(--hub-ink-3)",fontSize:11},children:i.total===0?"0":`${i.enabled}/${i.total}`})]},i.key)}),n&&n.connected&&e.jsxs("button",{onClick:()=>M(O==="cost"?null:"cost"),className:"inline-flex items-center gap-1.5 px-2.5 py-1 rounded-md text-[12px] transition-colors hover:bg-[var(--hub-surface-hover)]",style:{background:O==="cost"?"var(--hub-surface)":"transparent",border:"1px solid "+(O==="cost"?"var(--hub-line)":"transparent"),color:O==="cost"?"var(--hub-ink)":"var(--hub-ink-2)"},title:r("cost.estimate"),children:[e.jsx("span",{style:{color:"var(--hub-ink-3)"},children:"Σ"}),e.jsx("span",{children:r("cost.totalFootprint")}),e.jsxs("span",{className:"hub-mono hub-num",style:{color:"var(--hub-ink-3)",fontSize:11},children:[ie(n.exposed),"/",ie(n.gross)]})]}),e.jsx("div",{className:"ml-auto max-w-full flex-shrink-0",children:e.jsxs("div",{className:"hub-endpoint",style:{height:26},children:[e.jsx("div",{className:"hub-endpoint-label",children:"/mcp/"}),e.jsx("div",{className:"hub-endpoint-url",title:Ie,style:{maxWidth:200},children:s.name}),e.jsx("button",{type:"button",className:"hub-endpoint-copy",onClick:async i=>{i.stopPropagation();const b=await Se(Ie);m(b?r("common.copySuccess")||"Copied":r("common.copyFailed")||"Failed",b?"success":"error")},title:r("common.copy"),children:e.jsx(ye,{size:12})})]})})]}),O==="cost"&&(n==null?void 0:n.connected)&&e.jsx("div",{className:"mt-2 space-y-1",children:[...n.items].sort((i,b)=>b.cost-i.cost).map(i=>e.jsxs("div",{className:"flex items-center justify-between hub-mono",style:{fontSize:11.5,color:i.enabled?"var(--hub-ink-2)":"var(--hub-ink-3)"},children:[e.jsx("span",{className:"truncate",children:i.name}),e.jsx("span",{className:"hub-num flex-shrink-0",children:ie(i.cost)})]},`${i.kind}:${i.name}`))}),O==="tools"&&s.tools&&e.jsx("div",{className:"space-y-3 mt-2",children:s.tools.map((i,b)=>{var w;return e.jsx(rt,{server:s.name,tool:i,readOnly:!G,onToggle:ys,onDescriptionUpdate:Ns,cost:(w=n==null?void 0:n.items.find(J=>J.kind==="tool"&&J.name===i.name))==null?void 0:w.cost},b)})}),O==="prompts"&&s.prompts&&e.jsx("div",{className:"space-y-3 mt-2",children:s.prompts.map((i,b)=>{var w;return e.jsx(it,{server:s.name,prompt:i,readOnly:!G,onToggle:js,onDescriptionUpdate:ws,cost:(w=n==null?void 0:n.items.find(J=>J.kind==="prompt"&&J.name===i.name))==null?void 0:w.cost},b)})}),O==="resources"&&s.resources&&e.jsx("div",{className:"mt-2",children:s.resources.length===0?e.jsx("div",{className:"text-sm",style:{color:"var(--hub-ink-3)"},children:r("builtinResources.noResources")}):e.jsx("div",{className:"space-y-3",children:s.resources.map((i,b)=>{var w;return e.jsx(lt,{resource:i,readOnly:!G,onToggle:vs,onDescriptionUpdate:ks,cost:(w=n==null?void 0:n.items.find(J=>J.kind==="resource"&&J.name===i.uri))==null?void 0:w.cost},`${i.uri}-${b}`)})})})]})]}),e.jsx(Xs,{isOpen:W,onClose:()=>R(!1),onConfirm:()=>{t(s.name),R(!1)},serverName:s.name}),e.jsx(De,{isOpen:B,onClose:()=>T(!1),onConfirm:()=>{T(!1),Ce()},title:r("server.reinstall"),message:r("server.reinstallConfirm")||"This will clear the package cache and re-download dependencies. The server will restart.",confirmText:r("server.reinstall"),variant:"warning"}),e.jsx(De,{isOpen:K,onClose:()=>q(!1),onConfirm:()=>{q(!1),pe()},title:r("server.disconnectOAuth"),message:r("server.disconnectOAuthConfirm")||"This will revoke stored OAuth credentials where supported and require authorization again.",confirmText:r("server.disconnectOAuth"),variant:"warning"})]})},bt=({onAdd:s})=>{const{t:n}=te(),[t,a]=d.useState(!1),[x,f]=d.useState(null),[o,j]=d.useState(!1),[S,D]=d.useState(null),[r,m]=d.useState([]),z=()=>{a(!t),f(null),j(!1),D(null)},g=async()=>{S&&(await F(S),j(!1),D(null))},F=async E=>{try{f(null);const C=await le("/servers",E);if(!C.success){C&&C.message?f(C.message):f(n("server.addError"));return}a(!1),s()}catch(C){console.error("Error adding server:",C),navigator.onLine?C instanceof TypeError&&(C.message.includes("NetworkError")||C.message.includes("Failed to fetch"))?f(n("errors.serverConnection")):f(n("errors.serverAdd")):f(n("errors.network"))}},N=async E=>{try{const C=Ys(E);C.length>0?(m(C),D(E),j(!0)):await F(E)}catch(C){console.error("Error processing server submission:",C),f(n("errors.serverAdd"))}};return e.jsxs("div",{children:[e.jsxs("button",{onClick:z,className:"hub-btn primary",children:[e.jsx("svg",{xmlns:"http://www.w3.org/2000/svg",className:"h-3.5 w-3.5",viewBox:"0 0 20 20",fill:"currentColor",children:e.jsx("path",{fillRule:"evenodd",d:"M10 3a1 1 0 011 1v5h5a1 1 0 110 2h-5v5a1 1 0 11-2 0v-5H4a1 1 0 110-2h5V4a1 1 0 011-1z",clipRule:"evenodd"})}),n("server.add")]}),t&&e.jsx("div",{className:"fixed inset-0 bg-black/50 z-50 flex items-center justify-center p-4",children:e.jsx(is,{onSubmit:N,onCancel:z,modalTitle:n("server.addServer"),formError:x})}),o&&e.jsx("div",{className:"fixed inset-0 bg-black/50 z-[60] flex items-center justify-center p-4",children:e.jsxs("div",{className:"hub-card p-6 w-full max-w-md",children:[e.jsx("h3",{className:"text-lg font-semibold text-gray-900 mb-4",children:n("server.confirmVariables")}),e.jsx("p",{className:"text-gray-600 mb-4",children:n("server.variablesDetected")}),e.jsx("div",{className:"bg-yellow-50 border border-yellow-200 rounded p-3 mb-4",children:e.jsxs("div",{className:"flex items-start",children:[e.jsx("div",{className:"flex-shrink-0",children:e.jsx("svg",{className:"h-5 w-5 text-yellow-400",viewBox:"0 0 20 20",fill:"currentColor",children:e.jsx("path",{fillRule:"evenodd",d:"M8.257 3.099c.765-1.36 2.722-1.36 3.486 0l5.58 9.92c.75 1.334-.213 2.98-1.742 2.98H4.42c-1.53 0-2.493-1.646-1.743-2.98l5.58-9.92zM11 13a1 1 0 11-2 0 1 1 0 012 0zm-1-8a1 1 0 00-1 1v3a1 1 0 002 0V6a1 1 0 00-1-1z",clipRule:"evenodd"})})}),e.jsxs("div",{className:"ml-3",children:[e.jsxs("h4",{className:"text-sm font-medium text-yellow-800",children:[n("server.detectedVariables"),":"]}),e.jsx("ul",{className:"mt-1 text-sm text-yellow-700",children:r.map((E,C)=>e.jsxs("li",{className:"font-mono",children:["$",`{${E}}`]},C))})]})]})}),e.jsx("p",{className:"text-gray-600 text-sm mb-6",children:n("server.confirmVariablesMessage")}),e.jsxs("div",{className:"flex justify-end space-x-3",children:[e.jsx("button",{onClick:()=>{j(!1),D(null)},className:"hub-btn",children:n("common.cancel")}),e.jsx("button",{onClick:g,className:"hub-btn primary",children:n("server.confirmAndAdd")})]})]})})]})},ft=({server:s,onEdit:n,onCancel:t})=>{const{t:a}=te(),[x,f]=d.useState(null),o=async j=>{try{f(null);const S=encodeURIComponent(s.name),D=j.name&&j.name!==s.name,r={config:j.config,...D?{newName:j.name}:{}},m=await ve(`/servers/${S}`,r);if(!m.success){m&&m.message?f(m.message):f(a("server.updateError",{serverName:s.name}));return}n()}catch(S){console.error("Error updating server:",S),navigator.onLine?S instanceof TypeError&&(S.message.includes("NetworkError")||S.message.includes("Failed to fetch"))?f(a("errors.serverConnection")):f(a("errors.serverUpdate",{serverName:s.name})):f(a("errors.network"))}};return e.jsx("div",{className:"fixed inset-0 bg-black/50 z-50 flex items-center justify-center p-4",children:e.jsx(is,{onSubmit:o,onCancel:t,initialData:s,modalTitle:a("server.editTitle",{serverName:s.name}),formError:x})})},gt=({onSuccess:s,onCancel:n})=>{const{t}=te(),[a,x]=d.useState(!1),[f,o]=d.useState(!1),[j,S]=d.useState(null),[D,r]=d.useState(null),[m,z]=d.useState(!1),[g,F]=d.useState(null),[N,E]=d.useState(""),[C,O]=d.useState(!1),[M,W]=d.useState(""),R=l=>{l.preventDefault(),x(!0)},B=l=>{l.preventDefault(),x(!1)},T=l=>{l.preventDefault(),x(!1);const p=l.dataTransfer.files;if(p.length>0){const c=p[0];c.name.endsWith(".mcpb")?(r(c),S(null)):S(t("mcpb.invalidFileType"))}},K=l=>{const p=l.target.files;if(p&&p.length>0){const c=p[0];c.name.endsWith(".mcpb")?(r(c),S(null)):S(t("mcpb.invalidFileType"))}},q=async()=>{if(!D){S(t("mcpb.noFileSelected"));return}o(!0),S(null);try{const l=new FormData;l.append("mcpbFile",D);const p=await Ts($s("/mcpb/upload"),{method:"POST",body:l}),c=await p.json();if(!p.ok)throw new Error(c.message||`HTTP error! Status: ${p.status}`);if(c.success&&c.data)F(c.data.manifest),E(c.data.extractDir),z(!0);else throw new Error(c.message||t("mcpb.uploadFailed"))}catch(l){console.error("MCPB upload error:",l),S(l instanceof Error?l.message:t("mcpb.uploadFailed"))}finally{o(!1)}},X=async(l,p=!1)=>{var c;o(!0),S(null);try{const y=v(g,N,l);if(!p){const I=await zs("/servers");if(I.success&&((c=I.data)==null?void 0:c.find(L=>L.name===l))){W(l),O(!0),o(!1);return}}let $;if(p?$=await ve(`/servers/${encodeURIComponent(l)}`,{name:l,config:y}):$=await le("/servers",{name:l,config:y}),$.success)s(y);else throw new Error($.message||t("mcpb.installFailed"))}catch(y){console.error("MCPB install error:",y),S(y instanceof Error?y.message:t("mcpb.installFailed")),o(!1)}},h=()=>{O(!1),M&&X(M,!0)},u=()=>{O(!1),W(""),o(!1)},v=(l,p,c)=>{var I;const y=((I=l.server)==null?void 0:I.mcp_config)||{},$={type:"stdio",command:y.command||"node",args:(y.args||[]).map(_=>_.replace("${__dirname}",p))};return y.env&&Object.keys(y.env).length>0&&($.env={...y.env},Object.keys($.env).forEach(_=>{typeof $.env[_]=="string"&&($.env[_]=$.env[_].replace("${__dirname}",p))})),$};return m&&g?e.jsxs(e.Fragment,{children:[e.jsx(De,{isOpen:C,onClose:u,onConfirm:h,title:t("mcpb.serverExistsTitle"),message:t("mcpb.serverExistsConfirm",{serverName:M}),confirmText:t("mcpb.override"),cancelText:t("common.cancel"),variant:"warning"}),e.jsx("div",{className:`fixed inset-0 bg-black/50 z-50 flex items-center justify-center p-4 ${C?"opacity-50 pointer-events-none":""}`,children:e.jsxs("div",{className:"bg-white dark:bg-gray-800 shadow rounded-lg p-6 w-full max-w-3xl max-h-screen overflow-y-auto",children:[e.jsxs("div",{className:"flex justify-between items-center mb-6",children:[e.jsx("h2",{className:"text-xl font-semibold text-gray-900",children:t("mcpb.installServer")}),e.jsx("button",{onClick:n,className:"text-gray-500 hover:text-gray-700",children:"✕"})]}),j&&e.jsx("div",{className:"mb-4 bg-red-50 border-l-4 border-red-500 p-4 rounded",children:e.jsx("p",{className:"text-red-700",children:j})}),e.jsxs("div",{className:"space-y-6",children:[e.jsxs("div",{className:"bg-gray-50 dark:bg-gray-800 p-4 rounded-lg",children:[e.jsx("h3",{className:"font-medium text-gray-900 mb-2",children:t("mcpb.extensionInfo")}),e.jsxs("div",{className:"space-y-2 text-sm",children:[e.jsxs("div",{children:[e.jsxs("strong",{children:[t("mcpb.name"),":"]})," ",g.display_name||g.name]}),e.jsxs("div",{children:[e.jsxs("strong",{children:[t("mcpb.version"),":"]})," ",g.version]}),e.jsxs("div",{children:[e.jsxs("strong",{children:[t("mcpb.description"),":"]})," ",g.description]}),g.author&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("mcpb.author"),":"]})," ",g.author.name]}),g.tools&&g.tools.length>0&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("mcpb.tools"),":"]}),e.jsx("ul",{className:"list-disc list-inside ml-4",children:g.tools.map((l,p)=>e.jsxs("li",{children:[l.name," - ",l.description]},p))})]})]})]}),e.jsxs("div",{children:[e.jsx("label",{className:"block text-sm font-medium text-gray-700 mb-2",children:t("mcpb.serverName")}),e.jsx("input",{type:"text",id:"serverName",defaultValue:g.name,className:"w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500 form-input",placeholder:t("mcpb.serverNamePlaceholder")})]}),e.jsxs("div",{className:"flex justify-end space-x-4",children:[e.jsx("button",{onClick:n,disabled:f,className:"hub-btn",children:t("common.cancel")}),e.jsx("button",{onClick:()=>{const l=document.getElementById("serverName"),p=(l==null?void 0:l.value.trim())||g.name;X(p)},disabled:f,className:"hub-btn primary",children:f?e.jsxs(e.Fragment,{children:[e.jsxs("svg",{className:"animate-spin h-4 w-4 mr-2",xmlns:"http://www.w3.org/2000/svg",fill:"none",viewBox:"0 0 24 24",children:[e.jsx("circle",{className:"opacity-25",cx:"12",cy:"12",r:"10",stroke:"currentColor",strokeWidth:"4"}),e.jsx("path",{className:"opacity-75",fill:"currentColor",d:"M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"})]}),t("mcpb.installing")]}):t("mcpb.install")})]})]})]})})]}):e.jsx("div",{className:"fixed inset-0 bg-black/50 z-50 flex items-center justify-center p-4",children:e.jsxs("div",{className:"bg-white dark:bg-gray-800 shadow rounded-lg p-6 w-full max-w-lg",children:[e.jsxs("div",{className:"flex justify-between items-center mb-6",children:[e.jsx("h2",{className:"text-xl font-semibold text-gray-900",children:t("mcpb.uploadTitle")}),e.jsx("button",{onClick:n,className:"text-gray-500 hover:text-gray-700",children:"✕"})]}),j&&e.jsx("div",{className:"mb-4 bg-red-50 border-l-4 border-red-500 p-4 rounded",children:e.jsx("p",{className:"text-red-700",children:j})}),e.jsxs("div",{className:`relative border-2 border-dashed rounded-lg p-8 text-center transition-colors ${a?"border-blue-500 bg-blue-50":D?"border-gray-500 ":"border-gray-300 hover:border-gray-400"}`,onDragOver:R,onDragLeave:B,onDrop:T,children:[D?e.jsxs("div",{className:"space-y-2",children:[e.jsx("svg",{className:"mx-auto h-12 w-12 text-green-200",fill:"none",viewBox:"0 0 24 24",stroke:"currentColor",children:e.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z"})}),e.jsx("p",{className:"text-sm text-gray-900 font-medium",children:D.name}),e.jsxs("p",{className:"text-xs text-gray-500",children:[(D.size/1024/1024).toFixed(2)," MB"]})]}):e.jsxs("div",{className:"space-y-2",children:[e.jsx("svg",{className:"mx-auto h-12 w-12 text-gray-400",fill:"none",viewBox:"0 0 24 24",stroke:"currentColor",children:e.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",strokeWidth:2,d:"M20 7l-8-4-8 4m16 0l-8 4m8-4v10l-8 4m0-10L4 7m8 4v10M4 7v10l8 4"})}),e.jsxs("div",{children:[e.jsx("p",{className:"text-sm text-gray-900",children:t("mcpb.dropFileHere")}),e.jsx("p",{className:"text-xs text-gray-500",children:t("mcpb.orClickToSelect")})]})]}),e.jsx("input",{type:"file",accept:".mcpb",onChange:K,className:"absolute inset-0 w-full h-full opacity-0 cursor-pointer"})]}),e.jsxs("div",{className:"mt-6 flex justify-end space-x-4",children:[e.jsx("button",{onClick:n,disabled:f,className:"hub-btn",children:t("common.cancel")}),e.jsx("button",{onClick:q,disabled:!D||f,className:"hub-btn primary flex items-center",children:f?e.jsxs(e.Fragment,{children:[e.jsxs("svg",{className:"animate-spin h-4 w-4 mr-2",xmlns:"http://www.w3.org/2000/svg",fill:"none",viewBox:"0 0 24 24",children:[e.jsx("circle",{className:"opacity-25",cx:"12",cy:"12",r:"10",stroke:"currentColor",strokeWidth:"4"}),e.jsx("path",{className:"opacity-75",fill:"currentColor",d:"M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"})]}),t("mcpb.uploading")]}):t("mcpb.upload")})]})]})})},yt=s=>Object.entries(s.mcpServers).map(([n,t])=>{const a={};return t.type==="sse"||t.type==="streamable-http"?(a.type=t.type,a.url=t.url,t.headers&&(a.headers=t.headers)):t.type==="openapi"?(a.type="openapi",a.openapi=t.openapi):(a.type="stdio",a.command=t.command,a.args=t.args||[],t.env&&(a.env=t.env),t.options&&(a.options=t.options)),{name:n,config:a}}),jt=({onSuccess:s,onCancel:n})=>{const{t}=te(),[a,x]=d.useState(""),[f,o]=d.useState(null),[j,S]=d.useState(!1),[D,r]=d.useState(null),m=`{
7
- "mcpServers": {
8
- "stdio-server-example": {
9
- "command": "npx",
10
- "args": ["-y", "mcp-server-example"]
11
- },
12
- "sse-server-example": {
13
- "type": "sse",
14
- "url": "http://localhost:3000"
15
- },
16
- "http-server-example": {
17
- "type": "streamable-http",
18
- "url": "http://localhost:3001",
19
- "headers": {
20
- "Content-Type": "application/json",
21
- "Authorization": "Bearer your-token"
22
- }
23
- },
24
- "openapi-server-example": {
25
- "type": "openapi",
26
- "openapi": {
27
- "url": "https://petstore.swagger.io/v2/swagger.json"
28
- }
29
- }
30
- }
31
- }
32
-
33
- Supports: STDIO, SSE, HTTP (streamable-http), OpenAPI
34
- All servers will be imported in a single efficient batch operation.`,z=N=>{try{const E=JSON.parse(N.trim());return!E.mcpServers||typeof E.mcpServers!="object"?(o(t("jsonImport.invalidFormat")),null):E}catch{return o(t("jsonImport.parseError")),null}},g=()=>{o(null);const N=z(a);N&&r(yt(N))},F=async()=>{if(D){S(!0),o(null);try{const N=await le("/servers/batch",{servers:D});if(N.success&&N.data){const{successCount:E,failureCount:C,results:O}=N.data;if(C>0){const M=O.filter(W=>!W.success).map(W=>`${W.name}: ${W.message||t("jsonImport.addFailed")}`);o(t("jsonImport.partialSuccess",{count:E,total:D.length})+`
35
- `+M.join(`
36
- `))}E>0&&s()}else o(N.message||t("jsonImport.importFailed"))}catch(N){console.error("Import error:",N),o(t("jsonImport.importFailed"))}finally{S(!1)}}};return e.jsx("div",{className:"fixed inset-0 bg-black/50 z-50 flex items-center justify-center p-4",children:e.jsxs("div",{className:"bg-white dark:bg-gray-800 shadow rounded-lg p-6 w-full max-w-4xl max-h-[90vh] overflow-y-auto",children:[e.jsxs("div",{className:"flex justify-between items-center mb-6",children:[e.jsx("h2",{className:"text-xl font-semibold text-gray-900",children:t("jsonImport.title")}),e.jsx("button",{onClick:n,className:"text-gray-500 hover:text-gray-700",children:"✕"})]}),f&&e.jsx("div",{className:"mb-4 bg-red-50 border-l-4 border-red-500 p-4 rounded",children:e.jsx("p",{className:"text-red-700 whitespace-pre-wrap",children:f})}),D?e.jsxs("div",{children:[e.jsxs("div",{className:"mb-4",children:[e.jsx("h3",{className:"text-lg font-medium text-gray-900 mb-3",children:t("jsonImport.previewTitle")}),e.jsx("div",{className:"space-y-3",children:D.map((N,E)=>e.jsx("div",{className:"bg-gray-50 dark:bg-gray-800 p-4 rounded-lg border border-gray-200 dark:border-gray-700",children:e.jsx("div",{className:"flex items-start justify-between",children:e.jsxs("div",{className:"flex-1",children:[e.jsx("h4",{className:"font-medium text-gray-900",children:N.name}),e.jsxs("div",{className:"mt-2 space-y-1 text-sm text-gray-600",children:[e.jsxs("div",{children:[e.jsxs("strong",{children:[t("server.type"),":"]})," ",N.config.type||"stdio"]}),N.config.command&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("server.command"),":"]})," ",N.config.command]}),N.config.args&&N.config.args.length>0&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("server.arguments"),":"]})," ",N.config.args.join(" ")]}),N.config.url&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("server.url"),":"]})," ",N.config.url]}),N.config.env&&Object.keys(N.config.env).length>0&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("server.envVars"),":"]})," ",Object.keys(N.config.env).join(", ")]}),N.config.headers&&Object.keys(N.config.headers).length>0&&e.jsxs("div",{children:[e.jsxs("strong",{children:[t("server.headers"),":"]})," ",Object.keys(N.config.headers).join(", ")]})]})]})})},E))})]}),e.jsxs("div",{className:"flex justify-end space-x-4",children:[e.jsx("button",{onClick:()=>r(null),disabled:j,className:"hub-btn",children:t("common.back")}),e.jsx("button",{onClick:F,disabled:j,className:"hub-btn primary",children:j?e.jsxs(e.Fragment,{children:[e.jsxs("svg",{className:"animate-spin h-4 w-4 mr-2",xmlns:"http://www.w3.org/2000/svg",fill:"none",viewBox:"0 0 24 24",children:[e.jsx("circle",{className:"opacity-25",cx:"12",cy:"12",r:"10",stroke:"currentColor",strokeWidth:"4"}),e.jsx("path",{className:"opacity-75",fill:"currentColor",d:"M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"})]}),t("jsonImport.importing")]}):t("jsonImport.import")})]})]}):e.jsxs("div",{children:[e.jsxs("div",{className:"mb-4",children:[e.jsx("label",{className:"block text-sm font-medium text-gray-700 mb-2",children:t("jsonImport.inputLabel")}),e.jsx("textarea",{value:a,onChange:N=>x(N.target.value),className:"w-full h-96 px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500 font-mono text-sm",placeholder:m}),e.jsx("p",{className:"text-xs text-gray-500 mt-2",children:t("jsonImport.inputHelp")})]}),e.jsxs("div",{className:"flex justify-end space-x-4",children:[e.jsx("button",{onClick:n,className:"hub-btn",children:t("common.cancel")}),e.jsx("button",{onClick:g,disabled:!a.trim(),className:"hub-btn primary",children:t("jsonImport.preview")})]})]})]})})},vt=s=>({all:s.length,online:s.filter(n=>n.status==="connected").length,issues:s.filter(n=>n.status!=="connected"&&n.enabled!==!1).length,disabled:s.filter(n=>n.enabled===!1).length}),Nt=(s,n,t="")=>{const a=t.trim().toLowerCase();return s.filter(x=>{var o,j;return n==="online"&&x.status!=="connected"||n==="issues"&&(x.status==="connected"||x.enabled===!1)||n==="disabled"&&x.enabled!==!1?!1:a?(x.name+" "+(((o=x.config)==null?void 0:o.description)||"")+" "+(((j=x.tools)==null?void 0:j.map(S=>S.name).join(" "))||"")).toLowerCase().includes(a):!0})},wt=(s,n,t,a,x)=>{const f=Nt(s,n,t),o=f.length,j=Math.max(1,Math.ceil(o/x)),S=Math.min(Math.max(1,a),j),D=(S-1)*x;return{servers:f.slice(D,D+x),pagination:{page:S,limit:x,total:o,totalPages:j,hasNextPage:S<j,hasPrevPage:S>1}}},_t=()=>{const{t:s}=te(),n=Ds(),{servers:t,allServers:a,error:x,setError:f,isLoading:o,currentPage:j,serversPerPage:S,setCurrentPage:D,setServersPerPage:r,handleServerAdd:m,handleServerEdit:z,handleServerRemove:g,handleServerToggle:F,handleServerVisibilityChange:N,handleServerReload:E,handleServerReinstall:C,handleServerOAuthDisconnect:O,triggerRefresh:M}=Fs({refreshOnMount:!0}),{serverCosts:W,refetch:R}=Is();d.useEffect(()=>{R()},[t,R]);const[B,T]=d.useState(null),[K,q]=d.useState(!1),[X,h]=d.useState(!1),[u,v]=d.useState(!1),[l,p]=d.useState("all"),[c,y]=d.useState(""),$=d.useMemo(()=>vt(a),[a]),{servers:I,pagination:_}=d.useMemo(()=>wt(a,l,c,j,S),[a,l,c,j,S]);d.useEffect(()=>{_.page!==j&&D(_.page)},[_.page,j,D]);const L=async A=>{const k=await z(A);k&&T(k)},Q=async()=>{q(!0);try{M(),await new Promise(A=>setTimeout(A,400))}finally{q(!1)}};return e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-end justify-between gap-4 mb-6",children:[e.jsxs("div",{children:[e.jsx("h1",{className:"hub-h1",children:s("pages.servers.title")}),e.jsxs("p",{className:"hub-sub",children:[e.jsx("span",{className:"hub-num",children:$.all})," ",s("nav.servers").toLowerCase()," ·"," ",e.jsx("span",{className:"hub-num",children:$.online})," ",s("status.online")," ·"," ",e.jsx("span",{className:"hub-num",children:$.issues})," ",s("common.inactive")||"issues"]})]}),e.jsxs("div",{className:"flex gap-2",children:[e.jsxs("button",{className:"hub-btn",onClick:()=>n("/market"),children:[e.jsx(Ws,{size:13})," ",s("nav.market")]}),e.jsxs("button",{className:"hub-btn",onClick:()=>v(!0),children:[e.jsx(qs,{size:13})," ",s("jsonImport.button")]}),e.jsxs("button",{className:"hub-btn",onClick:()=>h(!0),children:[e.jsx(Hs,{size:13})," ",s("mcpb.upload")]}),e.jsxs("button",{className:"hub-btn",onClick:Q,disabled:K,"aria-label":s("common.refresh"),children:[e.jsx(je,{size:13,className:K?"animate-spin":""}),s("common.refresh")]}),e.jsx(bt,{onAdd:m})]})]}),x&&e.jsxs("div",{className:"hub-card flex items-center justify-between gap-3 mb-4",style:{padding:"10px 14px",borderColor:"oklch(0.85 0.1 25)",background:"oklch(0.97 0.03 25)",color:"oklch(0.4 0.18 25)"},children:[e.jsxs("div",{className:"flex items-center gap-2 min-w-0",children:[e.jsx(we,{size:14,className:"flex-shrink-0"}),e.jsx("span",{className:"truncate text-[13px]",children:x})]}),e.jsx("button",{className:"hub-icon-btn sm",onClick:()=>f(null),"aria-label":s("app.closeButton"),children:e.jsx(Ee,{size:13})})]}),e.jsxs("div",{className:"flex items-center gap-2 mb-4 flex-wrap",children:[e.jsx("div",{className:"hub-card flex items-center",style:{padding:2,borderRadius:7,background:"var(--hub-surface)"},children:[["all",s("common.all")||"All",$.all],["online",s("status.online"),$.online],["issues",s("common.inactive")||"Issues",$.issues],["disabled",s("pages.dashboard.disabledServers")||"Disabled",$.disabled]].map(([A,k,U])=>e.jsxs("button",{onClick:()=>p(A),className:"inline-flex items-center gap-1.5 px-3 text-[12px]",style:{height:24,borderRadius:5,background:l===A?"var(--hub-bg-2)":"transparent",color:l===A?"var(--hub-ink)":"var(--hub-ink-3)",border:"1px solid "+(l===A?"var(--hub-line)":"transparent")},children:[k,e.jsx("span",{className:"hub-mono",style:{fontSize:11,color:"var(--hub-ink-3)"},children:U})]},A))}),e.jsxs("div",{className:"hub-card flex items-center gap-2 px-2.5 flex-1",style:{height:30,background:"var(--hub-surface)",maxWidth:360},children:[e.jsx(Ks,{size:13,style:{color:"var(--hub-ink-3)"}}),e.jsx("input",{value:c,onChange:A=>y(A.target.value),className:"flex-1 bg-transparent outline-none text-[13px]",style:{color:"var(--hub-ink)"},placeholder:s("market.searchPlaceholder")||"Search…"}),c&&e.jsx("button",{onClick:()=>y(""),className:"hub-icon-btn sm",children:e.jsx(Ee,{size:11})})]}),e.jsxs("div",{className:"ml-auto hub-mono text-[12px]",style:{color:"var(--hub-ink-3)"},children:[_.total,"/",a.length]})]}),o&&t.length===0?e.jsx("div",{className:"hub-card p-6 flex items-center justify-center",children:e.jsxs("div",{className:"flex flex-col items-center gap-2",children:[e.jsx(je,{size:20,className:"animate-spin",style:{color:"var(--hub-ink-3)"}}),e.jsx("p",{style:{color:"var(--hub-ink-3)"},children:s("app.loading")})]})}):I.length===0?e.jsx("div",{className:"hub-card p-10 text-center",style:{color:"var(--hub-ink-3)"},children:e.jsx("p",{children:t.length===0?s("app.noServers"):s("market.noServers")})}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"flex flex-col",children:I.map(A=>e.jsx(ht,{server:A,cost:W.find(k=>k.name===A.name),onRemove:g,onEdit:L,onToggle:F,onVisibilityChange:N,onRefresh:M,onReload:E,onReinstall:C,onOAuthDisconnect:O},A.name))}),e.jsxs("div",{className:"flex items-center mt-4 text-[12px]",style:{color:"var(--hub-ink-3)"},children:[e.jsx("div",{className:"flex-[2]",children:s("common.showing",{start:(_.page-1)*_.limit+1,end:Math.min(_.page*_.limit,_.total),total:_.total})}),e.jsx("div",{className:"flex-[4] flex justify-center",children:_.totalPages>1&&e.jsx(Zs,{currentPage:_.page,totalPages:_.totalPages,onPageChange:D,disabled:o})}),e.jsxs("div",{className:"flex-[2] flex items-center justify-end gap-2",children:[e.jsxs("label",{htmlFor:"perPage",children:[s("common.itemsPerPage"),":"]}),e.jsxs("select",{id:"perPage",value:S,onChange:A=>r(Number(A.target.value)),disabled:o,className:"hub-input",style:{height:26,width:70,padding:"0 6px",fontSize:12},children:[e.jsx("option",{value:5,children:"5"}),e.jsx("option",{value:10,children:"10"}),e.jsx("option",{value:20,children:"20"}),e.jsx("option",{value:50,children:"50"})]})]})]})]}),B&&e.jsx(ft,{server:B,onEdit:()=>{T(null),M()},onCancel:()=>T(null)}),X&&e.jsx(gt,{onSuccess:()=>{h(!1),M()},onCancel:()=>h(!1)}),u&&e.jsx(jt,{onSuccess:()=>{v(!1),M()},onCancel:()=>v(!1)})]})};export{_t as default};
37
- //# sourceMappingURL=ServersPage-BFwvEzGn.js.map