@gen3/workspaces 0.12.47 → 0.12.49
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.
- package/dist/dts/components/CompactDictionaryPanel/CompactDictionaryPanel.d.ts.map +1 -1
- package/dist/dts/components/CompactDictionaryPanel/CompactDictionaryPanel.js +6 -2
- package/dist/dts/components/CompactDictionaryPanel/CompactDictionaryPanel.js.map +1 -1
- package/dist/dts/components/CompactDictionaryPanel/data/large_dictionary.d.ts +11168 -0
- package/dist/dts/components/CompactDictionaryPanel/data/large_dictionary.d.ts.map +1 -0
- package/dist/dts/components/CompactDictionaryPanel/data/large_dictionary.js +13055 -0
- package/dist/dts/components/CompactDictionaryPanel/data/large_dictionary.js.map +1 -0
- package/dist/dts/components/DataToolsPanel.js +1 -1
- package/dist/dts/components/DataToolsPanel.js.map +1 -1
- package/dist/dts/components/KernelLifecyclePanel/KernelSelector.js +2 -2
- package/dist/dts/components/KernelLifecyclePanel/KernelSelector.js.map +1 -1
- package/dist/dts/config.d.ts +0 -2
- package/dist/dts/config.d.ts.map +1 -1
- package/dist/dts/config.js +0 -34
- package/dist/dts/config.js.map +1 -1
- package/dist/dts/core/hatcheryApi.d.ts +20 -20
- package/dist/dts/core/jegGatewayApi.d.ts +8 -8
- package/dist/dts/core/kernelApi.d.ts +12 -12
- package/dist/dts/pages/WorkspacesCenter/data.d.ts.map +1 -1
- package/dist/dts/pages/WorkspacesCenter/data.js +42 -3
- package/dist/dts/pages/WorkspacesCenter/data.js.map +1 -1
- package/dist/dts/server/workspaceAssetsHandler.d.ts.map +1 -1
- package/dist/dts/server/workspaceAssetsHandler.js +0 -1
- package/dist/dts/server/workspaceAssetsHandler.js.map +1 -1
- package/dist/dts/workspace/WorkspaceCenter.js +2 -2
- package/dist/dts/workspace/WorkspaceCenter.js.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/SettingsPanel.d.ts +1 -1
- package/dist/dts/workspace/WorkspaceLayout/SettingsPanel.d.ts.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/SettingsPanel.js +2 -2
- package/dist/dts/workspace/WorkspaceLayout/SettingsPanel.js.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/ToolsPanel.d.ts +2 -1
- package/dist/dts/workspace/WorkspaceLayout/ToolsPanel.d.ts.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/ToolsPanel.js +2 -2
- package/dist/dts/workspace/WorkspaceLayout/ToolsPanel.js.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceLayout.d.ts +3 -1
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceLayout.d.ts.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceLayout.js +17 -4
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceLayout.js.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceToolbar.d.ts +2 -1
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceToolbar.d.ts.map +1 -1
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceToolbar.js +10 -5
- package/dist/dts/workspace/WorkspaceLayout/WorkspaceToolbar.js.map +1 -1
- package/dist/dts/workspace/tiers/types.d.ts +4 -2
- package/dist/dts/workspace/tiers/types.d.ts.map +1 -1
- package/dist/dts/workspace/types.d.ts +1 -0
- package/dist/dts/workspace/types.d.ts.map +1 -1
- package/dist/index/cjs/index.js +122 -76
- package/dist/index/cjs/index.js.map +1 -1
- package/dist/index/esm/index.js +124 -78
- package/dist/index/esm/index.js.map +1 -1
- package/dist/index.d.ts +4 -2
- package/dist/server/cjs/server.js +0 -1
- package/dist/server/cjs/server.js.map +1 -1
- package/dist/server/esm/server.js +0 -1
- package/dist/server/esm/server.js.map +1 -1
- package/package.json +4 -4
- package/dist/dts/api/utils.d.ts +0 -2
- package/dist/dts/api/utils.d.ts.map +0 -1
- package/dist/dts/api/utils.js +0 -13
- package/dist/dts/api/utils.js.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.js","sources":["../../../src/constants.ts","../../../src/server/workspaceAssetsHandler.ts","../../../src/server/withJupyterWorkspaces.ts","../../../src/server/utils.ts","../../../src/server/kernelLifecycleProxy.ts","../../../src/api/workspaceAssetsApi.ts","../../../src/api/workspaceGatewayApiHandler.ts","../../../src/api/kernelApiHandler.ts","../../../src/server/hatcheryProxy.ts","../../../src/api/hatcheryApiHandler.ts"],"sourcesContent":["import { GEN3_API, GEN3_WORKSPACE_API } from '@gen3/core';\n\n// TODO: migrate this to @gen3/core\n\nexport const GEN3_HATCHERY_API =\n GEN3_WORKSPACE_API || '/workspace-api/workspace/hatchery'; // get replaced by revproxy\n\nexport const GEN3_KERNEL_API =\n process.env.GEN3_KERNEL_API || `${GEN3_API}/lw-workspace/proxy/jeg-panel/api`;\n\nexport const GEN3_JEG_GATEWAY_API =\n process.env.JEG_GATEWAY_API || `${GEN3_API}/lw-workspace/proxy/jeg-panel/api`;\n\n// TODO: resolve this with @gen3/core\nexport const GEN3_WORKSPACES_API =\n GEN3_WORKSPACE_API || `${GEN3_API}/lw-workspace`;\n\nexport const JEG_SERVICE_API =\n 'http://jupyter-enterprise-gateway.jupyter-pods.svc.cluster.local:8888';\n","/**\n * Next.js API route handler factory for serving JupyterLite static assets.\n *\n * Usage (consumer's `src/pages/api/workspace-assets/[tier]/[[...path]].ts`):\n *\n * import { createWorkspaceAssetsHandler } from '@gen3/jupyter-workspaces/server';\n * export default createWorkspaceAssetsHandler();\n *\n * Or with custom config:\n *\n * export default createWorkspaceAssetsHandler({\n * gatewayBaseUrl: '/api/workspace/gateway/',\n * });\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport nodePath from 'path';\nimport fs from 'fs';\nimport { getCookie } from 'cookies-next';\n\nconst MAX_FILE_SIZE_BYTES = 67108864; // 64 * 1024 * 1024\n\n// ---------- types ----------\n\nexport interface WorkspaceAssetsHandlerOptions {\n /** Gateway base URL injected into remote tier config (default: env JUPYTER_GATEWAY_BASE_URL or '/api/workspace/gateway/') */\n gatewayBaseUrl?: string;\n /**\n * Root directory containing the JupyterLite assets.\n * Default: `<cwd>/node_modules/@gen3/jupyter-workspaces/assets`\n */\n assetRoot?: string;\n /** Additional JupyterLite extensions to disable for the remote tier */\n additionalDisabledExtensions?: string[];\n /** Application name injected into JupyterLite config data and used as <title> override (opt-in branding). */\n appName?: string;\n /** Favicon URL injected into JupyterLite config data (opt-in branding). */\n faviconUrl?: string;\n}\n\n// ---------- constants ----------\n\nconst ALLOWED_TIERS = new Set(['free', 'remote']);\n\nconst SAFE_SEGMENT_RE = /^@?[A-Za-z0-9._-]+$/;\n\nconst MIME_TYPES: Record<string, string> = {\n '.html': 'text/html; charset=utf-8',\n '.js': 'application/javascript; charset=utf-8',\n '.mjs': 'application/javascript; charset=utf-8',\n '.json': 'application/json; charset=utf-8',\n '.css': 'text/css; charset=utf-8',\n '.wasm': 'application/wasm',\n '.txt': 'text/plain; charset=utf-8',\n '.svg': 'image/svg+xml',\n '.png': 'image/png',\n '.ico': 'image/x-icon',\n '.woff2': 'font/woff2',\n '.woff': 'font/woff',\n '.ttf': 'font/ttf',\n '.map': 'application/json; charset=utf-8',\n '.ipynb': 'application/json; charset=utf-8',\n};\n\nconst REMOTE_DISABLED_EXTENSIONS = [\n '@jupyterlite/services-extension:config-section-manager',\n '@jupyterlite/services-extension:default-drive',\n '@jupyterlite/services-extension:event-manager',\n '@jupyterlite/services-extension:exporters',\n '@jupyterlite/services-extension:kernel-manager',\n '@jupyterlite/services-extension:kernel-client',\n '@jupyterlite/services-extension:kernel-spec-client',\n '@jupyterlite/services-extension:kernel-spec-manager',\n '@jupyterlite/services-extension:kernel-specs',\n '@jupyterlite/services-extension:nbconvert-manager',\n '@jupyterlite/services-extension:session-manager',\n '@jupyterlite/application-extension:service-worker-manager',\n '@jupyterlab/apputils-extension:themes',\n];\n\n// ---------- helpers ----------\n\nconst ASSETS_ROOT_PATH =\n process.env.JUPYTER_ASSETS_ROOT_PATH || '/gen3/jupyter-workspaces/assets';\n\nfunction defaultAssetRoot(): string {\n return ASSETS_ROOT_PATH.startsWith('/')\n ? ASSETS_ROOT_PATH\n : nodePath.join(process.cwd(), ASSETS_ROOT_PATH);\n}\ninterface BrandingConfig {\n appName?: string;\n faviconUrl?: string;\n}\n\n/**\n * Resolve the origin from forwarding headers, with referer fallback.\n * Handles proxies that drop non-standard ports from the Host header.\n */\nfunction resolveOrigin(req: NextApiRequest): { proto: string; host: string } {\n const forwardedProto =\n (Array.isArray(req.headers['x-forwarded-proto'])\n ? req.headers['x-forwarded-proto'][0]\n : req.headers['x-forwarded-proto']) || 'http';\n const forwardedHost = Array.isArray(req.headers['x-forwarded-host'])\n ? req.headers['x-forwarded-host'][0]\n : req.headers['x-forwarded-host'];\n const hostHeader = Array.isArray(req.headers.host)\n ? req.headers.host[0]\n : req.headers.host;\n const refererHeader = Array.isArray(req.headers.referer)\n ? req.headers.referer[0]\n : req.headers.referer;\n\n let resolvedHost = (forwardedHost || hostHeader || '').trim();\n let resolvedProto = String(forwardedProto).trim() || 'http';\n\n if (refererHeader) {\n try {\n const refererUrl = new URL(refererHeader);\n if (!resolvedHost || !resolvedHost.includes(':')) {\n resolvedHost = refererUrl.host;\n }\n if (!resolvedProto) {\n resolvedProto = refererUrl.protocol.replace(':', '');\n }\n } catch {\n // Ignore malformed referer and keep header-derived values.\n }\n }\n\n if (!resolvedHost) {\n resolvedHost = 'localhost:8890';\n }\n\n return { proto: resolvedProto, host: resolvedHost };\n}\n\nfunction injectRemoteConfig(\n html: string,\n req: NextApiRequest,\n gatewayBaseUrl: string,\n disabledExtensions: string[],\n branding = {\n appName: 'JupyterLite',\n faviconUrl: '/favicon2.ico',\n } as BrandingConfig,\n): string {\n const { proto, host } = resolveOrigin(req);\n const absoluteGatewayBase = `${proto}://${host}${gatewayBaseUrl}`;\n\n // Inject server-side JEG token — overrides any client-supplied auth header.\n // This ensures calls from JupyterLite's own serverconnection.js are also authenticated.\n\n let accessToken = undefined;\n if (process.env.NODE_ENV === 'development') {\n // NOTE: This cookie can only be accessed from the client side\n // in development mode. Otherwise, the cookie is set as httpOnly\n accessToken = getCookie('credentials_token');\n }\n\n const configData: Record<string, unknown> = {\n remoteBaseUrl: absoluteGatewayBase,\n remoteToken: accessToken,\n disabledExtensions,\n fullThemesUrl: '/workspace-api/workspace-assets/remote/build/themes',\n };\n\n if (branding?.appName) configData.appName = branding.appName;\n if (branding?.faviconUrl) configData.faviconUrl = branding.faviconUrl;\n\n let result = html.replace(\n /(<script\\s+id=\"jupyter-config-data\"[^>]*>)\\s*(\\{[^]*?\\})\\s*(<\\/script>)/,\n (_match, openTag: string, existingJson: string, closeTag: string) => {\n let existing: Record<string, unknown> = {};\n try {\n existing = JSON.parse(existingJson);\n } catch {\n // empty or malformed — start fresh\n }\n const merged = { ...existing, ...configData };\n if (Array.isArray(existing.disabledExtensions)) {\n const combined = new Set([\n ...(existing.disabledExtensions as string[]),\n ...disabledExtensions,\n ]);\n merged.disabledExtensions = [...combined];\n }\n return `${openTag}${JSON.stringify(merged)}${closeTag}`;\n },\n );\n\n if (branding?.appName) {\n result = result.replace(\n /<title>[^<]*<\\/title>/,\n `<title>${branding.appName}</title>`,\n );\n }\n\n return result;\n}\n\nfunction injectBranding(html: string, branding: BrandingConfig): string {\n let result = html.replace(\n /(<script\\s+id=\"jupyter-config-data\"[^>]*>)\\s*(\\{[^]*?\\})\\s*(<\\/script>)/,\n (_match, openTag: string, existingJson: string, closeTag: string) => {\n let existing: Record<string, unknown> = {};\n try {\n existing = JSON.parse(existingJson);\n } catch (error: unknown) {\n // empty or malformed — start fresh\n if (error instanceof Error) {\n console.log('Failed to parse existing JSON', error.message);\n } else {\n console.log('Failed to parse existing JSON', error);\n }\n }\n if (branding.appName) existing.appName = branding.appName;\n if (branding.faviconUrl) existing.faviconUrl = branding.faviconUrl;\n return `${openTag}${JSON.stringify(existing)}${closeTag}`;\n },\n );\n\n if (branding.appName) {\n result = result.replace(\n /<title>[^<]*<\\/title>/,\n `<title>${branding.appName}</title>`,\n );\n }\n\n return result;\n}\n\n// ---------- factory ----------\n\nexport function createWorkspaceAssetsHandler(\n options?: WorkspaceAssetsHandlerOptions,\n) {\n const gatewayBaseUrl =\n options?.gatewayBaseUrl ??\n process.env.JUPYTER_GATEWAY_BASE_URL ??\n '/api/workspace/gateway/';\n\n console.log('' + 'gatewayBaseUrl:', gatewayBaseUrl);\n\n const assetRoot = options?.assetRoot ?? defaultAssetRoot();\n\n const disabledExtensions = options?.additionalDisabledExtensions\n ? [...REMOTE_DISABLED_EXTENSIONS, ...options.additionalDisabledExtensions]\n : REMOTE_DISABLED_EXTENSIONS;\n\n const branding: BrandingConfig | undefined =\n options?.appName || options?.faviconUrl\n ? { appName: options.appName, faviconUrl: options.faviconUrl }\n : undefined;\n\n // Build the allowed-file sets once at factory time (not per-request) to\n // avoid unbounded I/O on every incoming request (CWE-770).\n const walkDir = (dir: string, set: Set<string>): void => {\n try {\n for (const entry of fs.readdirSync(dir, { withFileTypes: true })) {\n const full = nodePath.join(dir, entry.name);\n if (entry.isDirectory()) {\n walkDir(full, set);\n } else {\n set.add(full);\n }\n }\n } catch {\n // Tier directory doesn't exist yet — set remains empty and handler will 404.\n }\n };\n\n const allowedFilesByTier: Record<string, Set<string>> = {\n free: new Set<string>(),\n remote: new Set<string>(),\n };\n for (const tier of ALLOWED_TIERS) {\n walkDir(nodePath.resolve(assetRoot, tier), allowedFilesByTier[tier]);\n }\n\n return function handler(req: NextApiRequest, res: NextApiResponse): void {\n const { tier, path: pathSegments } = req.query;\n\n if (typeof tier !== 'string' || !ALLOWED_TIERS.has(tier)) {\n res.status(404).end('Not found');\n return;\n }\n\n const segments: string[] = Array.isArray(pathSegments)\n ? pathSegments\n : pathSegments\n ? [pathSegments]\n : [];\n\n let tierRoot: string;\n if (tier === 'free') {\n tierRoot = nodePath.resolve(assetRoot, 'free');\n } else if (tier === 'remote') {\n tierRoot = nodePath.resolve(assetRoot, 'remote');\n } else {\n res.status(404).end('Not found');\n return;\n }\n\n const safeSegments: string[] = [];\n for (const seg of segments) {\n if (\n typeof seg !== 'string' ||\n !SAFE_SEGMENT_RE.test(seg) ||\n seg === '.' ||\n seg === '..'\n ) {\n res.status(403).end('Forbidden');\n return;\n }\n safeSegments.push(nodePath.basename(seg));\n }\n\n const allowedFiles = allowedFilesByTier[tier];\n\n const candidatePath = nodePath.resolve(tierRoot, ...safeSegments);\n const candidateIndex = nodePath.join(candidatePath, 'index.html');\n\n let filePath: string;\n if (allowedFiles.has(candidatePath)) {\n filePath = candidatePath;\n } else if (allowedFiles.has(candidateIndex)) {\n filePath = candidateIndex;\n } else {\n res.status(404).end('Not found');\n return;\n }\n\n const ext = nodePath.extname(filePath).toLowerCase();\n const contentType = MIME_TYPES[ext] || 'application/octet-stream';\n\n const isBuildAsset =\n filePath.includes(nodePath.join(tier, 'build')) ||\n filePath.includes(nodePath.join(tier, 'extensions'));\n\n res.setHeader('X-Content-Type-Options', 'nosniff');\n res.setHeader('Cross-Origin-Opener-Policy', 'same-origin');\n res.setHeader('Cross-Origin-Embedder-Policy', 'require-corp');\n res.setHeader('Cross-Origin-Resource-Policy', 'cross-origin');\n\n if (process.env.NODE_ENV === 'development') {\n // In dev there is no fence service to plant the access_token cookie, so\n // we derive it from credentials_token (which is NOT httpOnly in dev) and\n // set it here. The browser will then send it automatically with every\n // subsequent request to the same origin — including JupyterLite's direct\n // calls to /lw-workspace/proxy/jeg-proxy/api/kernelspecs (which bypass\n // the Next.js proxy and therefore need the cookie on the wire).\n const accessToken = req.cookies?.['credentials_token'];\n if (accessToken) {\n res.setHeader(\n 'Set-Cookie',\n `access_token=${encodeURIComponent(accessToken)}; Path=/; SameSite=Lax`,\n );\n }\n }\n\n if (nodePath.basename(filePath) === 'service-worker.js') {\n res.setHeader('Service-Worker-Allowed', '/');\n }\n\n const isRemoteLabHtml =\n tier === 'remote' &&\n ext === '.html' &&\n filePath.includes(nodePath.join('lab', 'index.html'));\n\n if (isRemoteLabHtml) {\n res.setHeader('Content-Type', contentType);\n res.setHeader('Cache-Control', 'no-cache, no-store, must-revalidate');\n try {\n const html = fs.readFileSync(filePath, 'utf-8');\n const injected = injectRemoteConfig(\n html,\n req,\n gatewayBaseUrl,\n disabledExtensions,\n branding,\n );\n res.status(200).send(injected);\n } catch {\n res.status(500).end('Internal server error');\n }\n return;\n }\n\n // Non-remote HTML (e.g. free-tier lab) — apply branding if configured\n const isHtmlResponse = ext === '.html';\n if (isHtmlResponse && branding) {\n res.setHeader('Content-Type', contentType);\n res.setHeader('Cache-Control', 'no-cache, no-store, must-revalidate');\n try {\n const html = fs.readFileSync(filePath, 'utf-8');\n res.status(200).send(injectBranding(html, branding));\n } catch {\n res.status(500).end('Internal server error');\n }\n return;\n }\n\n res.setHeader('Content-Type', contentType);\n res.setHeader(\n 'Cache-Control',\n isBuildAsset\n ? 'public, max-age=31536000, immutable'\n : 'public, max-age=3600, must-revalidate',\n );\n\n const stat = fs.statSync(filePath);\n if (stat.size > MAX_FILE_SIZE_BYTES) {\n res.status(413).end('File too large');\n return;\n }\n\n const stream = fs.createReadStream(filePath);\n stream.on('error', () => {\n res.status(500).end('Internal server error');\n });\n stream.pipe(res);\n };\n}\n\n/** Default handler — for one-liner re-exports */\nconst defaultHandler = createWorkspaceAssetsHandler();\nexport default defaultHandler;\n","/**\n * Next.js config wrapper that adds all workspace-related plumbing.\n *\n * Usage (consumer's `next.config.js`):\n *\n * const { withJupyterWorkspaces } = require('@gen3/workspaces/server');\n * module.exports = withJupyterWorkspaces(yourNextConfig);\n */\n\nimport type { NextConfig } from 'next';\nimport nodePath from 'path';\nimport type { WebpackConfigContext } from 'next/dist/server/config-shared';\nimport type { Configuration } from 'webpack';\n\nexport interface WithJupyterWorkspacesOptions {\n /**\n * URL of the gateway proxy for local dev rewrites.\n * Default: env `GATEWAY_PROXY_URL` or `http://localhost:8890`\n */\n gatewayProxyUrl?: string;\n /**\n * Workspace page routes that need COOP/COEP headers.\n * Default: ['/workspaces/jupyter', '/workspaces/jupyter-lite', '/workspaces/jupyter-kernel']\n */\n workspaceRoutes?: string[];\n}\n\nconst DEFAULT_WORKSPACE_ROUTES = ['/Workspaces'];\n\nexport function withJupyterWorkspaces(\n nextConfig: NextConfig,\n options?: WithJupyterWorkspacesOptions,\n): NextConfig {\n const workspaceRoutes = options?.workspaceRoutes ?? DEFAULT_WORKSPACE_ROUTES;\n\n return {\n ...nextConfig,\n\n // Merge transpilePackages\n transpilePackages: [\n ...(nextConfig.transpilePackages ?? []),\n ...['@gen3/workspaces'].filter(\n (pkg) => !(nextConfig.transpilePackages ?? []).includes(pkg),\n ),\n ],\n\n // Merge webpack config — add React dedup alias\n webpack(config: Configuration, ctx: WebpackConfigContext) {\n config.resolve = config.resolve ?? {};\n config.resolve.alias = {\n ...(config.resolve.alias ?? {}),\n react: nodePath.dirname(require.resolve('react/package.json')),\n 'react-dom': nodePath.dirname(\n require.resolve('react-dom/package.json'),\n ),\n };\n\n // Chain the consumer's existing webpack config\n if (typeof nextConfig.webpack === 'function') {\n return nextConfig.webpack(config, ctx);\n }\n return config;\n },\n\n // Merge rewrites — add gateway proxy rewrite in dev mode\n async rewrites() {\n const isDev = process.env.NODE_ENV === 'development';\n\n const existing =\n typeof nextConfig.rewrites === 'function'\n ? await nextConfig.rewrites()\n : [];\n\n if (!isDev) return existing;\n\n const gatewayProxyUrl =\n options?.gatewayProxyUrl ??\n process.env.GATEWAY_PROXY_URL ??\n 'http://localhost:8890';\n\n const gatewayRewrite = {\n source: '/api/workspace/gateway/:path*',\n destination: `${gatewayProxyUrl}/api/workspace/gateway/:path*`,\n };\n\n // rewrites() can return an array or { beforeFiles, afterFiles, fallback }\n if (Array.isArray(existing)) {\n return [gatewayRewrite, ...existing];\n }\n return {\n ...existing,\n beforeFiles: [gatewayRewrite, ...(existing.beforeFiles ?? [])],\n };\n },\n\n // Merge headers — add COOP/COEP for workspace routes\n async headers() {\n const existing =\n typeof nextConfig.headers === 'function'\n ? await nextConfig.headers()\n : [];\n\n const coopCoepHeaders = workspaceRoutes.map((route) => ({\n source: route,\n headers: [\n { key: 'Cross-Origin-Opener-Policy', value: 'same-origin' },\n { key: 'Cross-Origin-Embedder-Policy', value: 'credentialless' },\n ],\n }));\n\n return [...existing, ...coopCoepHeaders];\n },\n };\n}\n","/**\n * Shared HTTP proxy utility for server-side proxy handlers.\n * Streams request body through and forwards response status + body.\n *\n * Also exports two token helpers used by the proxy factories:\n * - extractTokenFallback: minimal cookie/header extraction used when the host\n * app has not injected its own getToken (standalone / test use).\n * - decodeJwtClaims: base64url decode of the JWT payload for REMOTE_USER header.\n * Crypto verification is Ambassador's job — we only need the sub/username claim.\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\n\n/**\n * Minimal JWT extraction fallback — used only when the host app does not inject\n * its own getToken. Prefers Authorization: Bearer, then access_token cookie.\n * In gen3-vectis production this is never reached — getAccessToken is always wired.\n */\nexport function extractTokenFallback(req: NextApiRequest): string | null {\n const auth = req.headers['authorization'];\n if (typeof auth === 'string' && auth.startsWith('Bearer ')) {\n return auth.slice(7).trim() || null;\n }\n const cookie = req.headers['cookie'] ?? '';\n const m = cookie.match(/(?:^|;\\s*)access_token=([^;]+)/);\n return m ? decodeURIComponent(m[1]).trim() || null : null;\n}\n\n/**\n * Decode JWT payload claims without cryptographic verification.\n * Ambassador has already verified the RS256 signature — we just need the sub claim\n * to set the REMOTE_USER header for per-user isolation enforcement downstream.\n */\n// Maximum JWT string length accepted before base64 decoding.\n// GA4GH RAS Passport JWTs embed multiple signed Visa JWTs as claims, so the\n// outer passport can easily exceed 8 KiB (50 visas × ~2 KB each ≈ 136 KB encoded).\n// 512 KiB covers the most complex real-world passports while still guarding against\n// crafted JWTs designed to exhaust server memory. Ambassador has already verified\n// the RS256 signature — this cap only defends the local base64/JSON decode step.\nconst MAX_JWT_LENGTH = 524288; // 512 KiB\n\nexport function decodeJwtClaims(jwt: string): Record<string, unknown> | null {\n if (jwt.length > MAX_JWT_LENGTH) return null;\n try {\n const parts = jwt.split('.');\n if (parts.length < 2) return null;\n const padded = parts[1]\n .replace(/-/g, '+')\n .replace(/_/g, '/')\n .padEnd(Math.ceil(parts[1].length / 4) * 4, '=');\n return JSON.parse(Buffer.from(padded, 'base64').toString('utf8')) as Record<\n string,\n unknown\n >;\n } catch {\n return null;\n }\n}\n\nexport interface ProxyRequestOptions {\n req: NextApiRequest;\n res: NextApiResponse;\n targetUrl: string;\n method: 'GET' | 'POST' | 'DELETE' | 'PUT' | 'PATCH';\n extraHeaders?: Record<string, string>;\n /** Whether to stream the incoming request body to the target. */\n forwardBody?: boolean;\n}\n\nexport async function createProxyRequest({\n req,\n res,\n targetUrl,\n method,\n extraHeaders = {},\n forwardBody = false,\n}: ProxyRequestOptions): Promise<void> {\n const headers: Record<string, string> = {\n ...extraHeaders,\n };\n if (\n forwardBody &&\n (method === 'POST' || method === 'PUT' || method === 'PATCH')\n ) {\n headers['Content-Type'] ??= 'application/json';\n }\n\n let body: BodyInit | undefined;\n if (\n forwardBody &&\n (method === 'POST' || method === 'PUT' || method === 'PATCH')\n ) {\n let buf: Buffer;\n try {\n buf = await bufferBody(req);\n } catch (err) {\n const statusCode = (err as { statusCode?: number }).statusCode ?? 400;\n const msg = err instanceof Error ? err.message : 'Bad request';\n res.status(statusCode).json({ error: msg });\n return;\n }\n // Node.js Buffer is a Uint8Array subclass; cast to silence DOM BodyInit mismatch\n body = buf as unknown as BodyInit;\n if (buf.length > 0) {\n headers['Content-Length'] = String(buf.length);\n }\n }\n\n let upRes: Response;\n try {\n upRes = await fetch(targetUrl, {\n method,\n headers,\n body,\n signal: AbortSignal.timeout(30_000),\n });\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n res.status(502).json({ error: `Upstream unreachable: ${msg}` });\n return;\n }\n\n // Forward status and content-type\n const contentType = upRes.headers.get('content-type') || 'application/json';\n res.setHeader('Content-Type', contentType);\n\n if (upRes.status === 204 || upRes.status === 304) {\n res.status(upRes.status).end();\n return;\n }\n\n // Do not forward raw upstream error bodies — they may contain stack traces or\n // internal hostnames. Log them server-side (CloudWatch) and return a generic message.\n if (upRes.status >= 500) {\n const errBody = await upRes.text().catch(() => '');\n console.error(\n '[proxy] upstream %d from %s: %s',\n upRes.status,\n targetUrl,\n errBody,\n );\n res.status(502).json({ error: 'Upstream service error.' });\n return;\n }\n\n const responseBody = await upRes.text();\n res.status(upRes.status).send(responseBody);\n}\n\n// Maximum request body size accepted by the proxy (1 MiB).\n// Prevents memory exhaustion from oversized payloads before any business logic runs.\nconst MAX_BODY_BYTES = 1 * 1024 * 1024;\n\nfunction bufferBody(req: NextApiRequest): Promise<Buffer> {\n return new Promise((resolve, reject) => {\n const chunks: Buffer[] = [];\n let total = 0;\n req.on('data', (chunk: Buffer) => {\n total += chunk.length;\n if (total > MAX_BODY_BYTES) {\n req.destroy();\n reject(\n Object.assign(new Error('Request body too large'), {\n statusCode: 413,\n }),\n );\n return;\n }\n chunks.push(chunk);\n });\n req.on('end', () => resolve(Buffer.concat(chunks)));\n req.on('error', reject);\n });\n}\n","/**\n * createKernelLifecycleProxyHandler — server-side Next.js API route handler\n * for all kernel control-plane traffic.\n *\n * Security properties:\n * - Billing gate: POST /kernels fetches Fence /credentials/cdis first;\n * if that fails, no kernel is ever launched.\n * - Kernel spec filtering: the browser receives only the names/costs defined in policy.\n * - REMOTE_USER forwarded on every upstream request — JEG enforces per-user isolation.\n * - KERNEL_ID_RE validates all kernel IDs before they reach the upstream URL.\n *\n * Token extraction:\n * Pass getToken to reuse the host app's cookie logic (strongly recommended).\n * In gen3-vectis: `(req) => getAccessToken(req.headers['cookie'] ?? '') ?? null`\n * Ambassador performs RS256 verification before any request reaches Next.js.\n *\n * Usage (src/pages/api/workspace/kernel/[...action].ts — generated by bin/init.mjs):\n * import { createKernelLifecycleProxyHandler } from '@gen3/jupyter-workspaces/server';\n * import { getAccessToken } from '../../lib/auth/getLoginStatus';\n * const policy = process.env.KERNEL_SPEC_POLICY ? JSON.parse(process.env.KERNEL_SPEC_POLICY) : {};\n * export default createKernelLifecycleProxyHandler({\n * gen3Endpoint: process.env.GEN3_ENDPOINT,\n * fenceUrl: process.env.FENCE_URL,\n * kernelSpecPolicy: policy,\n * getToken: (req) => getAccessToken(req.headers['cookie'] ?? '') ?? null,\n * });\n * export const config = { api: { bodyParser: false } };\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport { decodeJwtClaims, extractTokenFallback } from './utils';\nimport { fetchFence, GEN3_FENCE_SERVICE } from '@gen3/core';\nimport { GEN3_FENCE_API } from '@gen3/core/server';\nimport { JEG_SERVICE_API } from '../constants';\n\n/* ------------------------------------------------------------------ */\n/* Types */\n/* ------------------------------------------------------------------ */\n\n/** Kernel spec filtering and cost annotation policy (server-side only). */\nexport interface KernelSpecPolicy {\n /**\n * Raw JEG kernel spec names that are permitted for this deployment.\n * Only these will be returned to the browser.\n */\n allowedSpecs: string[];\n /**\n * Cost per hour for each spec. 0 = included in base subscription.\n * Injected into the spec as `costPerHour` before returning to browser.\n */\n costPerHour: Record<string, number>;\n /**\n * Human-readable display name per spec (replaces raw JEG spec name).\n * e.g. { \"python3_gpu_a100\": \"Python (GPU A100 — $2.40/hr)\" }\n */\n displayNames: Record<string, string>;\n /**\n * Node type label for UI badge.\n * e.g. { \"python3_micro\": \"micro\", \"python3_gpu_a100\": \"gpu\" }\n */\n nodeType: Record<string, string>;\n}\n\nexport interface BillingEvent {\n username: string;\n action: 'launch' | 'terminate';\n kernelSpec?: string;\n kernelId?: string;\n costTier: number;\n timestamp: string;\n}\n\nexport interface KernelLifecycleProxyConfig {\n /**\n * External hostname for Ambassador routing, e.g. \"mycommons.example.com\"\n * or \"localhost:30080\" in local dev.\n * Used to build the upstream URL: https://{gen3Endpoint}/lw-workspace/proxy/...\n */\n gen3Endpoint: string | undefined;\n /** Internal URL of the Fence service, e.g. http://fence.fence.svc:80 */\n fenceUrl: string | undefined;\n /** Kernel spec filtering + billing policy (server-side only). */\n kernelSpecPolicy: Partial<KernelSpecPolicy>;\n /**\n * Set to true when JEG is configured and enabled for this deployment.\n * Controlled by ENABLE_JEG=true env var in gen3-vectis.\n * When false (default), all routes except GET /api/status return 503 silently so\n * the UI fails gracefully without error spam.\n */\n jegEnabled?: boolean;\n /**\n * Number of idle days before a kernel is considered stale (for /api/reap).\n * Defaults to 10. Controlled by JEG_IDLE_KILL_DAYS env var.\n */\n idleKillDays?: number;\n /**\n * Maximum kernel age in days regardless of idle state (for /api/reap).\n * Defaults to 15. Controlled by JEG_MAX_KERNEL_AGE_DAYS env var.\n */\n maxKernelAgeDays?: number;\n /**\n * Optional billing event sink. Defaults to structured JSON to stdout (CloudWatch).\n * Swap for DynamoDB, Stripe, etc. without changing any other code.\n * The function MUST NOT block — fire and forget.\n */\n billingSink?: (event: BillingEvent) => void;\n /**\n * Token extractor injected by the host application.\n * In gen3-vectis: `(req) => getAccessToken(req.headers['cookie'] ?? '') ?? null`\n * When omitted a minimal Bearer-header/cookie fallback is used (dev/standalone only).\n * Ambassador has already done RS256 verification — this is extraction only.\n */\n getToken?: (req: NextApiRequest) => string | null;\n}\n\n/* ------------------------------------------------------------------ */\n/* Default billing sink — structured CloudWatch-compatible JSON log */\n/* ------------------------------------------------------------------ */\n\nfunction defaultBillingSink(event: BillingEvent): void {\n // CloudWatch Logs Insights picks up structured JSON automatically\n process.stdout.write(\n JSON.stringify({ type: 'WORKSPACE_BILLING', ...event }) + '\\n',\n );\n}\n\n/* ------------------------------------------------------------------ */\n/* Fence credential fetch */\n/* ------------------------------------------------------------------ */\n\ninterface FenceCreds {\n key_id: string;\n api_key: string; // pragma: allowlist secret\n}\n\nconst EMPTY_FENCE_CREDS: FenceCreds = {\n key_id: '',\n api_key: '', // pragma: allowlist secret\n};\n\nasync function fetchFenceCreds(\n fenceUrl: string,\n jwt: string,\n): Promise<FenceCreds> {\n let parsedFenceUrl: URL;\n try {\n parsedFenceUrl = new URL(fenceUrl);\n } catch {\n throw new Error('Fence URL is misconfigured.');\n }\n if (\n parsedFenceUrl.protocol !== 'http:' &&\n parsedFenceUrl.protocol !== 'https:'\n ) {\n throw new Error('Fence URL is misconfigured.');\n }\n try {\n const response = await fetchFence<FenceCreds>(\n {\n endpoint: 'credentials/api',\n method: 'GET',\n headers: {\n Authorization: `Bearer ${jwt}`,\n 'Content-Type': 'application/json',\n },\n },\n process.env.NODE_ENV === 'production', // use the FENCE Service if in production\n );\n if (!response?.data?.api_key) {\n console.error('No valid API key found in Fence response');\n return {\n api_key: '', // pragma: allowlist secret\n key_id: '',\n };\n }\n return response.data;\n } catch (error: unknown) {\n if (error instanceof Error) {\n console.error('Error fetching API key from Fence:', error);\n } else {\n console.error('Error fetching API key from Fence');\n }\n return EMPTY_FENCE_CREDS;\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Kernel spec response transformation */\n/* ------------------------------------------------------------------ */\n\ninterface RawKernelSpecsResponse {\n default: string;\n kernelspecs: Record<\n string,\n {\n name: string;\n spec: {\n display_name: string;\n language: string;\n argv?: string[];\n metadata?: Record<string, unknown>;\n };\n resources?: Record<string, string>;\n }\n >;\n}\n\nfunction filterAndAnnotateSpecs(\n raw: RawKernelSpecsResponse,\n policy: Partial<KernelSpecPolicy>,\n): RawKernelSpecsResponse {\n const allowedSpecs = policy.allowedSpecs ?? [];\n const costPerHour = policy.costPerHour ?? {};\n const displayNames = policy.displayNames ?? {};\n const nodeType = policy.nodeType ?? {};\n\n if (allowedSpecs.length === 0) {\n // No policy configured — return everything unannotated (useful during dev bootstrap)\n return raw;\n }\n\n const filteredSpecs: RawKernelSpecsResponse['kernelspecs'] = {};\n\n for (const specName of allowedSpecs) {\n const rawSpec = raw.kernelspecs[specName];\n if (!rawSpec) continue; // JEG doesn't have this spec — skip silently\n\n filteredSpecs[specName] = {\n ...rawSpec,\n spec: {\n ...rawSpec.spec,\n // Override display_name with our curated name if provided\n display_name: displayNames[specName] ?? rawSpec.spec.display_name,\n // Inject billing metadata into spec.metadata (available to browser)\n metadata: {\n ...(rawSpec.spec.metadata ?? {}),\n costPerHour: costPerHour[specName] ?? 0,\n nodeType: nodeType[specName] ?? 'unknown',\n },\n },\n };\n }\n\n // Use first allowed spec as default if original default was filtered out\n const filteredDefault = allowedSpecs.includes(raw.default)\n ? raw.default\n : (allowedSpecs[0] ?? '');\n\n return { default: filteredDefault, kernelspecs: filteredSpecs };\n}\n\n/* ------------------------------------------------------------------ */\n/* Body buffering (Next.js bodyParser: false) */\n/* ------------------------------------------------------------------ */\n\nfunction readBody(req: NextApiRequest): Promise<Buffer> {\n return new Promise((resolve, reject) => {\n const chunks: Buffer[] = [];\n req.on('data', (chunk: Buffer) => chunks.push(chunk));\n req.on('end', () => resolve(Buffer.concat(chunks)));\n req.on('error', reject);\n });\n}\n\n/* ------------------------------------------------------------------ */\n/* Ambassador upstream URL builder */\n/* ------------------------------------------------------------------ */\n\n// function buildAmbassadorUrl(gen3Endpoint: string, kernelPath: string): string {\n// // gen3Endpoint may or may not have a scheme\n// const base = gen3Endpoint.startsWith('http')\n// ? gen3Endpoint\n// : `https://${gen3Endpoint}`;\n// const parsed = new URL(base);\n// if (parsed.protocol !== 'http:' && parsed.protocol !== 'https:') {\n// throw new Error('gen3Endpoint must use http or https protocol.');\n// }\n// return `${parsed.origin}${parsed.pathname.replace(/\\/$/, '')}/lw-workspace/proxy${kernelPath}`;\n// }\n\nfunction buildAmbassadorUrl(gen3Endpoint: string, kernelPath: string): string {\n // gen3Endpoint may or may not have a scheme\n const base = gen3Endpoint.startsWith('http')\n ? gen3Endpoint\n : `https://${gen3Endpoint}`;\n const parsed = new URL(base);\n if (parsed.protocol !== 'http:' && parsed.protocol !== 'https:') {\n throw new Error('gen3Endpoint must use http or https protocol.');\n }\n return `${parsed.origin}${parsed.pathname.replace(/\\/$/, '')}/lw-workspace/proxy${kernelPath}`;\n}\n\n/* ------------------------------------------------------------------ */\n/* Route matching */\n/* ------------------------------------------------------------------ */\n\nconst KERNEL_ID_RE = /^[a-f0-9-]{8,36}$/i;\n\ntype KernelRoute =\n | { type: 'kernelspecs' }\n | { type: 'kernels_list' }\n | { type: 'kernel_launch' }\n | { type: 'kernel_delete'; kernelId: string }\n | { type: 'kernel_passthrough'; kernelPath: string }\n | { type: 'status' }\n | { type: 'reap' };\n\ntype SimpleRoute = Exclude<\n KernelRoute,\n { type: 'kernel_delete' | 'kernel_passthrough' }\n>;\n\n// Table-driven simple routes: all match /api/{resource} with no kernel ID segment.\nconst SIMPLE_ROUTES = new Map<string, SimpleRoute>([\n ['GET:status', { type: 'status' }],\n ['POST:reap', { type: 'reap' }],\n ['GET:kernelspecs', { type: 'kernelspecs' }],\n ['GET:kernels', { type: 'kernels_list' }],\n ['POST:kernels', { type: 'kernel_launch' }],\n]);\n\nfunction resolveKernelRoute(\n method: string,\n actionSegments: string[],\n): KernelRoute | null {\n const [seg1, seg2] = actionSegments;\n\n if (!seg2) {\n return SIMPLE_ROUTES.get(`${method}:${seg1}`) ?? null;\n }\n\n // Routes with a kernel ID segment — validate format before use.\n if (seg1 === 'kernels' && KERNEL_ID_RE.test(seg2)) {\n if (method === 'DELETE') {\n return { type: 'kernel_delete', kernelId: seg2 };\n }\n // GET /api/kernels/{id}/channels or similar (passthrough for WebSocket upgrade info)\n if (method === 'GET') {\n const rest = actionSegments.slice(2).join('/');\n return {\n type: 'kernel_passthrough',\n kernelPath: `/api/kernels/${seg2}/${rest}`,\n };\n }\n }\n\n return null;\n}\n\n/* ------------------------------------------------------------------ */\n/* Main factory — shared types and per-route handlers */\n/* ------------------------------------------------------------------ */\n\nfunction errMsg(err: unknown): string {\n return err instanceof Error ? err.message : String(err);\n}\n\ninterface RouteContext {\n req: NextApiRequest;\n gen3Endpoint: string;\n fenceUrl: string | undefined;\n kernelSpecPolicy: Partial<KernelSpecPolicy>;\n ambassadorHeaders: Record<string, string>;\n /** Unsanitised JWT — use only for non-header contexts (e.g. Fence fetch body). */\n jwt: string;\n username: string;\n sink: (event: BillingEvent) => void;\n idleKillDays: number;\n maxKernelAgeDays: number;\n}\n\n/* -------- GET /api/kernelspecs -------- */\nasync function handleKernelSpecs(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernelspecs');\n try {\n const upRes = await fetch(upstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n if (!upRes.ok) {\n res\n .status(upRes.status)\n .json({ error: `Gateway ${upRes.status}: ${upRes.statusText}` });\n return;\n }\n const rawSpecs = (await upRes.json()) as RawKernelSpecsResponse;\n res\n .status(200)\n .json(filterAndAnnotateSpecs(rawSpecs, ctx.kernelSpecPolicy));\n } catch {\n res.status(502).json({ error: 'Failed to fetch kernel specs.' });\n }\n}\n\n/* -------- GET /api/kernels -------- */\nasync function handleKernelsList(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernels');\n try {\n const upRes = await fetch(upstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n if (!upRes.ok) {\n res\n .status(upRes.status)\n .json({ error: `Gateway ${upRes.status}: ${upRes.statusText}` });\n return;\n }\n res.status(200).json(await upRes.json());\n } catch {\n res.status(502).json({ error: 'Failed to list kernels.' });\n }\n}\n\n/* -------- POST /api/reap — bulk-delete stale/aged kernels -------- */\nasync function handleReap(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n // const listUpstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernels');\n const listUpstream = `${ctx.gen3Endpoint}/api/kernels`;\n let kernelList: Array<{ id: string; name: string; last_activity?: string }> =\n [];\n try {\n const listRes = await fetch(listUpstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n\n if (!listRes.ok) {\n res\n .status(listRes.status)\n .json({ error: `Failed to list kernels: ${listRes.status}` });\n return;\n }\n kernelList = (await listRes.json()) as typeof kernelList;\n } catch (err) {\n res.status(502).json({ error: `Kernel list unavailable: ${errMsg(err)}` });\n return;\n }\n\n const now = Date.now();\n const idleKillMins = ctx.idleKillDays * 24 * 60;\n const maxAgeMins = ctx.maxKernelAgeDays * 24 * 60;\n const reaped: string[] = [];\n const errors: string[] = [];\n\n for (const kernel of kernelList) {\n if (!KERNEL_ID_RE.test(kernel.id)) continue; // skip any malformed IDs from upstream\n const lastActivity = kernel.last_activity\n ? new Date(kernel.last_activity).getTime()\n : 0;\n const idleMins =\n lastActivity > 0 ? (now - lastActivity) / 60_000 : Infinity;\n if (idleMins <= idleKillMins && idleMins <= maxAgeMins) continue;\n\n const deleteUpstream = buildAmbassadorUrl(\n ctx.gen3Endpoint,\n `/api/kernels/${encodeURIComponent(kernel.id)}`,\n );\n try {\n await fetch(deleteUpstream, {\n method: 'DELETE',\n headers: ctx.ambassadorHeaders,\n });\n reaped.push(kernel.id);\n ctx.sink({\n username: ctx.username,\n action: 'terminate',\n kernelId: kernel.id,\n costTier: 0,\n timestamp: new Date().toISOString(),\n });\n } catch {\n errors.push(kernel.id);\n }\n }\n\n res.status(200).json({ reaped, errors });\n}\n\n/* -------- POST /api/kernels — launch with Fence cred injection -------- */\nasync function handleKernelLaunch(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n if (!ctx.fenceUrl) {\n res.status(503).json({ error: 'FENCE_URL is not configured.' });\n return;\n }\n\n // 1. Fetch per-user S3 credentials from Fence.\n // If this fails, we return 502 and do NOT launch a kernel.\n let fenceCreds: FenceCreds;\n try {\n fenceCreds = await fetchFenceCreds(ctx.fenceUrl, ctx.jwt);\n } catch (err) {\n res\n .status(502)\n .json({ error: `Storage credentials unavailable: ${errMsg(err)}` });\n return;\n }\n\n // 2. Read the original launch body from the client.\n const rawBody = await readBody(ctx.req);\n let launchBody: Record<string, unknown> = {};\n try {\n launchBody = JSON.parse(rawBody.toString('utf8')) as Record<\n string,\n unknown\n >;\n } catch {\n // empty or invalid JSON — proceed with empty body\n }\n\n const kernelSpec = (launchBody.name as string) || '';\n\n // 3. Inject gen3-fuse credential env vars into the kernel launch body.\n // JEG forwards these to the kernel pod → init container writes /.gen3/credentials.json\n // → gen3-fuse sidecar mounts the user's S3 bucket.\n const enrichedBody = {\n ...launchBody,\n env: {\n ...((launchBody.env as Record<string, string>) ?? {}),\n GEN3_API_KEY_ID: fenceCreds.key_id,\n GEN3_API_KEY_SECRET: fenceCreds.api_key, // pragma: allowlist secret\n NAMESPACE: process.env.NAMESPACE || 'jupyter-pods',\n GEN3_ENDPOINT: ctx.gen3Endpoint,\n },\n };\n\n // 4. Non-blocking billing event (launch intent).\n const launchTimestamp = new Date().toISOString();\n const costTier = ctx.kernelSpecPolicy.costPerHour?.[kernelSpec] ?? 0;\n ctx.sink({\n username: ctx.username,\n action: 'launch',\n kernelSpec,\n costTier,\n timestamp: launchTimestamp,\n });\n\n // TODO:\n // BILLING_HOOK: pricing/quota check — runs before kernel is launched.\n // Replace the resolved value below with an async pricing/quota API call.\n // Return false here to block launch with a 402 Payment Required.\n // Example: const approved = await checkQuotaAndPrice({ username, kernelSpec, costTier });\n const billingApproved = true; // TODO: hook pricing gate here\n if (!billingApproved) {\n res\n .status(402)\n .json({ error: 'Kernel launch requires billing authorization.' });\n return;\n }\n\n // 5. Forward to JEG via Ambassador.\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernels');\n let launchRes: Response;\n try {\n launchRes = await fetch(upstream, {\n method: 'POST',\n headers: { ...ctx.ambassadorHeaders, 'Content-Type': 'application/json' },\n body: JSON.stringify(enrichedBody),\n });\n } catch (err) {\n res.status(502).json({ error: `Kernel launch failed: ${errMsg(err)}` });\n return;\n }\n\n if (!launchRes.ok) {\n res.status(launchRes.status).json({\n error: `Kernel launch failed: ${launchRes.status} ${launchRes.statusText}`,\n });\n return;\n }\n\n const kernelData = (await launchRes.json()) as Record<string, unknown>;\n\n // 6. Non-blocking: record kernelId in billing log.\n const kernelId = kernelData?.id as string | undefined;\n if (kernelId) {\n ctx.sink({\n username: ctx.username,\n action: 'launch',\n kernelSpec,\n kernelId,\n costTier,\n timestamp: launchTimestamp,\n });\n }\n\n res.status(201).json(kernelData);\n}\n\n/* -------- DELETE /api/kernels/{id} -------- */\nasync function handleKernelDelete(\n ctx: RouteContext,\n route: Extract<KernelRoute, { type: 'kernel_delete' }>,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(\n ctx.gen3Endpoint,\n `/api/kernels/${encodeURIComponent(route.kernelId)}`,\n );\n try {\n const upRes = await fetch(upstream, {\n method: 'DELETE',\n headers: ctx.ambassadorHeaders,\n });\n // 404 = already gone = success (idempotent terminate)\n if (!upRes.ok && upRes.status !== 404) {\n res.status(upRes.status).json({\n error: `Kernel terminate failed: ${upRes.status} ${upRes.statusText}`,\n });\n return;\n }\n } catch (err) {\n res.status(502).json({ error: `Kernel terminate failed: ${errMsg(err)}` });\n return;\n }\n\n // Non-blocking billing event (terminate)\n ctx.sink({\n username: ctx.username,\n action: 'terminate',\n kernelId: route.kernelId,\n costTier: 0, // actual cost determined from launch event by billing system\n timestamp: new Date().toISOString(),\n });\n\n res.status(204).end();\n}\n\n/* -------- GET /api/kernels/{id}/... passthrough -------- */\nasync function handleKernelPassthrough(\n ctx: RouteContext,\n route: Extract<KernelRoute, { type: 'kernel_passthrough' }>,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, route.kernelPath);\n try {\n const upRes = await fetch(upstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n res.status(upRes.status).json(await upRes.json().catch(() => ({})));\n } catch {\n res.status(502).json({ error: 'Upstream unreachable.' });\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Factory */\n/* ------------------------------------------------------------------ */\n\nconst ALLOWED_FENCE_URLS = [GEN3_FENCE_SERVICE, GEN3_FENCE_API];\n\nconst ALLOWED_JEG_URLS = [JEG_SERVICE_API, '/lw-workspace/proxy/jeg-panel'];\n\nexport function createKernelProxyHandler(config: KernelLifecycleProxyConfig) {\n const sink = config.billingSink ?? defaultBillingSink;\n const jegEnabled = config.jegEnabled === true;\n const idleKillDays = config.idleKillDays ?? 10;\n const maxKernelAgeDays = config.maxKernelAgeDays ?? 15;\n\n return async function kernelLifecycleProxyHandler(\n req: NextApiRequest,\n res: NextApiResponse,\n ): Promise<void> {\n const { gen3Endpoint, fenceUrl, kernelSpecPolicy } = config;\n\n if (fenceUrl && !ALLOWED_FENCE_URLS.includes(fenceUrl)) {\n res.status(503).json({ error: 'Fence service URL is misconfigured.' });\n return;\n }\n\n if (gen3Endpoint && !ALLOWED_JEG_URLS.includes(gen3Endpoint)) {\n res.status(503).json({ error: 'JEG service URL is misconfigured.' });\n return;\n }\n\n // --- Route resolution (done early so /api/status can short-circuit) ---\n const rawAction = req.query.action;\n const actionSegments: string[] = Array.isArray(rawAction)\n ? rawAction.filter((s): s is string => typeof s === 'string')\n : [];\n const route = resolveKernelRoute(req.method || '', actionSegments);\n\n // GET /api/status is the JEG feature-gate probe — always returns 200 with { enabled }.\n // This allows useGatewayConnection to detect whether JEG is configured before polling.\n if (route?.type === 'status') {\n res.setHeader('Cache-Control', 'no-store');\n res.status(200).json({ enabled: jegEnabled });\n return;\n }\n\n // All other routes are gated — silently return 503 so the UI fails gracefully.\n if (!jegEnabled) {\n res.setHeader('Cache-Control', 'no-store');\n res\n .status(503)\n .json({ error: 'JEG not configured for this deployment.' });\n return;\n }\n\n if (!gen3Endpoint) {\n res.status(503).json({ error: 'GEN3_ENDPOINT is not configured.' });\n return;\n }\n\n // --- Auth: host-injected extractor first, minimal fallback for dev/standalone ---\n const jwt = config.getToken\n ? config.getToken(req)\n : extractTokenFallback(req);\n\n if (!jwt) {\n res.status(401).json({ error: 'Authentication required.' });\n return;\n }\n\n if (!route) {\n res.status(404).json({ error: 'Route not found.' });\n return;\n }\n\n // Extract sub claim for REMOTE_USER — Ambassador already verified the signature.\n const claims = decodeJwtClaims(jwt);\n const rawUsername =\n claims?.sub ??\n claims?.preferred_username ??\n claims?.username ??\n 'unknown';\n const username: string =\n typeof rawUsername === 'string' ? rawUsername : 'unknown';\n\n // Strip CRLF to prevent HTTP header injection (defense-in-depth)\n const safeJwt = jwt.replace(/[\\r\\n]/g, '');\n const safeUsername = username.replace(/[\\r\\n]/g, '');\n\n const ambassadorHeaders: Record<string, string> = {\n Authorization: `Bearer ${safeJwt}`,\n REMOTE_USER: safeUsername,\n };\n\n // No-store for all control plane responses\n res.setHeader('Cache-Control', 'no-store');\n\n const ctx: RouteContext = {\n req,\n gen3Endpoint,\n fenceUrl,\n kernelSpecPolicy,\n ambassadorHeaders,\n jwt,\n username,\n sink,\n idleKillDays,\n maxKernelAgeDays,\n };\n\n switch (route.type) {\n case 'kernelspecs':\n return handleKernelSpecs(ctx, res);\n case 'kernels_list':\n return handleKernelsList(ctx, res);\n case 'reap':\n return handleReap(ctx, res);\n case 'kernel_launch':\n return handleKernelLaunch(ctx, res);\n case 'kernel_delete':\n return handleKernelDelete(ctx, route, res);\n case 'kernel_passthrough':\n return handleKernelPassthrough(ctx, route, res);\n default:\n res.status(404).json({ error: 'Route not matched.' });\n }\n };\n}\n","import type { NextApiRequest, NextApiResponse } from 'next';\nimport { createWorkspaceAssetsHandler } from '../server/workspaceAssetsHandler';\nimport { GEN3_COMMONS_NAME } from '@gen3/core';\n\nconst upstreamHandler = createWorkspaceAssetsHandler({\n // Route JupyterLite remote-mode kernel WebSocket traffic through revproxy's\n // /lw-workspace/proxy/ nginx block → ambassador-service (ExternalName → Emissary)\n // → JEG. Next.js API routes cannot handle WebSocket upgrades, so we must\n // bypass them and use the nginx path that has allow_upgrade + long timeouts.\n gatewayBaseUrl: '/lw-workspace/proxy/',\n});\n\nconst VECTIS_WORKSPACE_APP_NAME = 'Vectis Workspaces';\nconst VECTIS_FAVICON_URL = '/icons/Vectis_Logo_Colored_LightTheme.svg';\n\n/** Escape characters that are special inside an HTML text node / attribute. */\nfunction escapeHtml(text: string): string {\n return text\n .replace(/&/g, '&')\n .replace(/</g, '<')\n .replace(/>/g, '>')\n .replace(/\"/g, '"')\n .replace(/'/g, ''');\n}\n\n/**\n * Return the first value of a header that Node.js may (in rare edge cases)\n * expose as an array. `host` and `referer` are always strings in practice,\n * but this keeps the helper safe for any header name.\n */\nfunction firstHeader(value: string | string[] | undefined): string | undefined {\n if (Array.isArray(value)) return value[0];\n return value;\n}\n\nfunction resolveOrigin(req: NextApiRequest): {\n proto: string;\n host: string;\n} {\n const forwardedProto = firstHeader(req.headers['x-forwarded-proto']);\n const forwardedHost = firstHeader(req.headers['x-forwarded-host']);\n // `host` is always a single string per Node.js HTTP spec; firstHeader is\n // used for type-safety only.\n const hostHeader = firstHeader(req.headers.host);\n const refererHeader = firstHeader(req.headers.referer);\n\n let proto = (forwardedProto ?? '').trim();\n let host = (forwardedHost || hostHeader || '').trim();\n\n if (refererHeader) {\n try {\n const refererUrl = new URL(refererHeader);\n // Prefer referer origin when the host header dropped a non-default port.\n if (!host || !host.includes(':')) {\n host = refererUrl.host;\n }\n // Only fall back to referer protocol when nothing better is available.\n if (!proto) {\n proto = refererUrl.protocol.replace(':', '');\n }\n } catch {\n // Ignore malformed referer; keep header-derived values.\n }\n }\n\n return {\n proto: proto || 'http',\n host: host || 'localhost:30080',\n };\n}\n\nfunction injectVectisBranding(html: string, req: NextApiRequest): string {\n const isRemoteTierRequest =\n (Array.isArray(req.query.tier) ? req.query.tier[0] : req.query.tier) ===\n 'remote';\n\n // Resolve origin only when needed (remote tier).\n const absoluteRemoteBaseUrl = isRemoteTierRequest\n ? (() => {\n const { proto, host } = resolveOrigin(req);\n return { base: `${proto}://${host}/lw-workspace/proxy/`, proto, host };\n })()\n : null;\n\n const withConfig = html.replace(\n /(<script\\s+id=\"jupyter-config-data\"[^>]*>)([\\s\\S]*?)(<\\/script>)/,\n (_match, openTag: string, rawContent: string, closeTag: string) => {\n // Strip leading/trailing whitespace left by the template.\n const trimmed = rawContent.trim();\n // Verify the captured content looks like a JSON object before parsing.\n if (!trimmed.startsWith('{') || !trimmed.endsWith('}')) {\n console.error(\n '[vectis-branding] jupyter-config-data content is not a JSON object; skipping merge.',\n );\n return _match;\n }\n\n let existing: Record<string, unknown> = {};\n try {\n existing = JSON.parse(trimmed) as Record<string, unknown>;\n } catch (err) {\n console.error(\n '[vectis-branding] Failed to parse jupyter-config-data JSON; skipping merge.',\n err,\n );\n return _match;\n }\n\n const existingDisabled = Array.isArray(existing.disabledExtensions)\n ? (existing.disabledExtensions as string[])\n : [];\n const remoteDisabledExtensions = isRemoteTierRequest\n ? [...existingDisabled, '@jupyterlite/pyodide-kernel-extension:kernel']\n : existingDisabled;\n\n const merged: Record<string, unknown> = {\n ...existing,\n appName: GEN3_COMMONS_NAME,\n faviconUrl: VECTIS_FAVICON_URL,\n ...(remoteDisabledExtensions.length > 0\n ? {\n disabledExtensions: Array.from(new Set(remoteDisabledExtensions)),\n }\n : {}),\n ...(isRemoteTierRequest && absoluteRemoteBaseUrl\n ? {\n // Use an absolute URL so JupyterLite does not resolve WS endpoints\n // relative to /workspace-api/workspace-assets/remote/.\n remoteBaseUrl: absoluteRemoteBaseUrl.base,\n // Route all kernel ops through jeg-proxy so JupyterLite sees merged\n // Python3 (container) + JEG GPU kernelspecs. The handler routes\n // Python3 kernel launches/channels to the container; GPU kernel\n // launches are gated (403) with a message to use the Kernel Panel.\n remoteKernelsBaseUrl: `${absoluteRemoteBaseUrl.proto}://${absoluteRemoteBaseUrl.host}/lw-workspace/proxy/jeg-proxy`,\n fullThemesUrl:\n '/workspace-api/workspace-assets/remote/build/themes',\n }\n : {}),\n };\n return `${openTag}${JSON.stringify(merged)}${closeTag}`;\n },\n );\n\n // Escape the app name before placing it into the HTML title element.\n return withConfig.replace(\n /<title>[^<]*<\\/title>/,\n `<title>${escapeHtml(VECTIS_WORKSPACE_APP_NAME)}</title>`,\n );\n}\n\nfunction isHtmlResponse(res: NextApiResponse): boolean {\n const contentType = res.getHeader('content-type');\n if (typeof contentType === 'string') return contentType.includes('text/html');\n if (Array.isArray(contentType))\n return contentType.some((v) => v.includes('text/html'));\n return false;\n}\n\nexport default function handler(req: NextApiRequest, res: NextApiResponse) {\n const originalSend = res.send.bind(res);\n\n res.send = ((body: unknown) => {\n if (\n typeof body === 'string' &&\n isHtmlResponse(res) &&\n body.includes('id=\"jupyter-config-data\"') &&\n body.includes('<title>')\n ) {\n return originalSend(injectVectisBranding(body, req));\n }\n return originalSend(body);\n }) as typeof res.send;\n\n return upstreamHandler(req, res);\n}\n","import type { NextApiRequest, NextApiResponse } from 'next';\nimport { getCookie } from 'cookies-next';\n\n// Allowed path prefixes — keeps proxying scoped to the Jupyter Gateway API surface\nconst ALLOWED_PREFIXES = ['/api/kernels', '/api/sessions', '/api/kernelspecs'];\n\nfunction buildUpstreamPath(segments: string[]): string {\n const clean = segments\n .filter(Boolean)\n .map((s) => s.replace(/^\\/+|\\/+$/g, ''));\n\n if (clean.some((s) => s === '..' || s === '.')) {\n throw new Error('Invalid path segment');\n }\n\n return `/${clean.join('/')}`;\n}\n\nfunction isAllowedPath(path: string): boolean {\n return ALLOWED_PREFIXES.some(\n (prefix) => path === prefix || path.startsWith(`${prefix}/`),\n );\n}\n\nfunction buildQueryString(\n rawUrl: string | undefined,\n excludeKey: string,\n): string {\n if (!rawUrl) return '';\n const queryPart = rawUrl.split('?')[1];\n if (!queryPart) return '';\n\n const params = new URLSearchParams(queryPart);\n params.delete(excludeKey);\n\n const result = params.toString();\n return result ? `?${result}` : '';\n}\n\nfunction readBody(req: NextApiRequest): Promise<Buffer | undefined> {\n return new Promise((resolve, reject) => {\n if (!req.method || ['GET', 'HEAD'].includes(req.method.toUpperCase())) {\n resolve(undefined);\n return;\n }\n const chunks: Buffer[] = [];\n req.on('data', (chunk: Buffer | string) => {\n chunks.push(Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk));\n });\n req.on('end', () =>\n resolve(chunks.length ? Buffer.concat(chunks) : undefined),\n );\n req.on('error', reject);\n });\n}\n\nexport default async function handler(\n req: NextApiRequest,\n res: NextApiResponse,\n) {\n const gatewayUrl = process.env.JUPYTER_GATEWAY_URL;\n\n if (!gatewayUrl) {\n res.status(500).json({ error: 'JUPYTER_GATEWAY_URL is not configured' });\n return;\n }\n\n const gatewayBase = gatewayUrl.replace(/\\/+$/, '');\n\n const actionSegments = Array.isArray(req.query.action)\n ? req.query.action\n : req.query.action\n ? [req.query.action]\n : [];\n\n let upstreamPath: string;\n try {\n upstreamPath = buildUpstreamPath(actionSegments);\n } catch {\n res.status(400).json({ error: 'Invalid path' });\n return;\n }\n\n if (!isAllowedPath(upstreamPath)) {\n res.status(403).json({ error: 'Forbidden path' });\n return;\n }\n\n const queryString = buildQueryString(req.url, 'action');\n const targetUrl = `${gatewayBase}${upstreamPath}${queryString}`;\n\n const forwardHeaders = new Headers();\n for (const [key, value] of Object.entries(req.headers)) {\n if (!value) continue;\n const lower = key.toLowerCase();\n if (\n lower === 'host' ||\n lower === 'content-length' ||\n lower === 'transfer-encoding'\n )\n continue;\n forwardHeaders.set(key, Array.isArray(value) ? value.join(',') : value);\n }\n\n // Inject server-side JEG token — overrides any client-supplied auth header.\n // This ensures calls from JupyterLite's own serverconnection.js are also authenticated.\n if (process.env.NODE_ENV === 'development') {\n // NOTE: This cookie can only be accessed from the client side\n // in development mode. Otherwise, the cookie is set as httpOnly\n const accessToken = getCookie('credentials_token');\n if (accessToken) {\n forwardHeaders.set('Authorization', `Bearer ${accessToken}`);\n }\n }\n\n let body: Buffer | undefined;\n try {\n body = await readBody(req);\n } catch {\n res.status(500).json({ error: 'Failed to read request body' });\n return;\n }\n\n if (body) {\n forwardHeaders.set('content-length', String(body.byteLength));\n }\n\n let upstream: Response;\n try {\n upstream = await fetch(targetUrl, {\n method: req.method,\n headers: forwardHeaders,\n body: body ? new Uint8Array(body) : undefined,\n signal: AbortSignal.timeout(30_000),\n });\n } catch (err) {\n const isTimeout = err instanceof Error && err.name === 'TimeoutError';\n res.status(isTimeout ? 504 : 502).json({\n error: isTimeout ? 'Gateway timeout' : 'Gateway unreachable',\n });\n return;\n }\n\n res.status(upstream.status);\n upstream.headers.forEach((value, key) => {\n const lower = key.toLowerCase();\n if (\n lower === 'transfer-encoding' ||\n lower === 'content-type' ||\n lower === 'content-security-policy'\n )\n return;\n res.setHeader(key, value);\n });\n\n const upstreamContentType = upstream.headers.get('content-type') || '';\n const safeContentType = /html|xml|svg/i.test(upstreamContentType)\n ? 'text/plain; charset=utf-8'\n : upstreamContentType || 'application/octet-stream';\n res.setHeader('Content-Type', safeContentType);\n res.setHeader('X-Content-Type-Options', 'nosniff');\n res.setHeader('Content-Security-Policy', \"default-src 'none'; sandbox\");\n res.setHeader('Content-Disposition', 'attachment');\n\n if (upstream.body) {\n const reader = upstream.body.getReader();\n try {\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n res.write(value);\n }\n } finally {\n reader.releaseLock();\n }\n res.end();\n } else {\n res.end();\n }\n}\n\nexport const config = { api: { bodyParser: false } };\n","// Kernel lifecycle proxy — billing gate + Fence credential injection.\n// Browser never sees JEG URL or raw kernel spec names.\n// POST /kernels calls Fence /credentials/cdis first — if it fails, no kernel is launched.\n// getToken reuses this app's cookie extraction — no JWT reinvention.\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport { createKernelProxyHandler } from '../server/kernelLifecycleProxy';\nimport { getAccessToken } from '@gen3/frontend/server';\nimport { GEN3_FENCE_API } from '@gen3/core/server';\nimport { JEG_SERVICE_API } from '../constants';\nimport { GEN3_FENCE_SERVICE } from '@gen3/core';\n\nconst inCluster = Boolean(process.env.KUBERNETES_SERVICE_HOST);\nconst defaultGen3Endpoint = inCluster\n ? JEG_SERVICE_API\n : '/lw-workspace/proxy/jeg-panel';\nconst defaultFenceUrl = inCluster ? GEN3_FENCE_SERVICE : GEN3_FENCE_API;\n\nconst gen3Endpoint = process.env.JEG_SERVICE_API ?? defaultGen3Endpoint;\nconst fenceUrl = defaultFenceUrl;\n\nif (!gen3Endpoint) {\n console.warn(\n '[workspace-kernel] JEG_SERVICE_API is not set and not running in-cluster — kernel proxy will likely fail',\n );\n}\nif (!fenceUrl) {\n console.warn(\n '[workspace-kernel] FENCE_URL is not set and not running in-cluster — credential injection will likely fail',\n );\n}\n\nlet policy: Record<string, unknown> = {};\nif (process.env.KERNEL_SPEC_POLICY) {\n try {\n policy = JSON.parse(process.env.KERNEL_SPEC_POLICY);\n } catch (err) {\n throw new Error(\n `[workspace-kernel] KERNEL_SPEC_POLICY is not valid JSON: ${(err as Error).message}`,\n );\n }\n}\n\nconst upstreamHandler = createKernelProxyHandler({\n gen3Endpoint,\n fenceUrl,\n kernelSpecPolicy: policy,\n jegEnabled: process.env.ENABLE_JEG === 'true',\n getToken: (req) => {\n const token = getAccessToken(req.headers['cookie'] ?? '') ?? null;\n if (!token) {\n console.warn(\n '[workspace-kernel] No access token found in request cookies',\n );\n }\n return token;\n },\n});\n\nexport default async function handler(\n req: NextApiRequest,\n res: NextApiResponse,\n) {\n const action = Array.isArray(req.query.action) ? req.query.action : [];\n const isStatusPath = action[0] === 'api' && action[1] === 'status';\n try {\n await upstreamHandler(req, res);\n } catch (err) {\n console.error('[workspace-kernel] Upstream handler threw:', err);\n if (!res.headersSent) {\n res.status(502).json({ error: 'Bad gateway' });\n }\n return;\n }\n}\n\nexport const config = { api: { bodyParser: false } };\n","/**\n * createHatcheryProxyHandler — server-side Next.js API route handler for Hatchery\n * micro-container lifecycle (launch, terminate, status, options).\n *\n * Security properties:\n * - Strict allowlist: only /options, /status, /launch, /terminate are proxied.\n * - All other paths return 404 — Hatchery internals are never reachable.\n * - JWT forwarded as Bearer; user identity set as REMOTE_USER for server-side isolation.\n * - `id` query param sanitized against SAFE_ID_RE (SSRF and injection prevention).\n *\n * Token extraction:\n * Pass getToken to reuse the host app's existing cookie logic (strongly recommended).\n * In gen3-vectis this is getAccessToken from lib/auth/getLoginStatus.\n * Without getToken, a minimal Bearer/cookie fallback is used (dev/standalone only).\n * Ambassador performs RS256 verification before any request reaches Next.js.\n *\n * Usage (src/pages/api/workspace/hatchery/[...action].ts — generated by bin/init.mjs):\n * import { createHatcheryProxyHandler } from '@gen3/jupyter-workspaces/server';\n * import { getAccessToken } from '../../lib/auth/getLoginStatus';\n * export default createHatcheryProxyHandler({\n * hatcheryUrl: process.env.HATCHERY_URL,\n * getToken: (req) => getAccessToken(req.headers['cookie'] ?? '') ?? null,\n * });\n * export const config = { api: { bodyParser: false } };\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport {\n createProxyRequest,\n decodeJwtClaims,\n extractTokenFallback,\n} from './utils';\n\nexport interface HatcheryProxyConfig {\n /** Internal URL of the Hatchery service, e.g. http://hatchery.hatchery.svc:8000 */\n hatcheryUrl: string | undefined;\n /**\n * Token extractor injected by the host application.\n * In gen3-vectis: `(req) => getAccessToken(req.headers['cookie'] ?? '') ?? null`\n * When omitted, a minimal Bearer-header/cookie fallback is used (dev/standalone only).\n * Ambassador has already done RS256 verification — this is extraction only.\n */\n getToken?: (req: NextApiRequest) => string | null;\n}\n\ntype HatcheryRoute =\n | { method: 'GET'; path: '/options' }\n | { method: 'GET'; path: '/status' }\n | { method: 'POST'; path: '/launch' }\n | { method: 'POST'; path: '/terminate' };\n\nconst SAFE_ID_RE = /^[a-zA-Z0-9]([a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?$/;\n\nfunction resolveHatcheryRoute(\n method: string,\n actionSegments: string[],\n): HatcheryRoute | null {\n const action = actionSegments[0] || '';\n const routes: Record<string, HatcheryRoute> = {\n 'GET:options': { method: 'GET', path: '/options' },\n 'GET:status': { method: 'GET', path: '/status' },\n 'POST:launch': { method: 'POST', path: '/launch' },\n 'POST:terminate': { method: 'POST', path: '/terminate' },\n };\n return routes[`${method}:${action}`] ?? null;\n}\n\nconst ALLOWED_HATCHERY_URLS = [\n '/lw-workspace',\n 'http://hatchery-service.gen3.svc.cluster.local',\n];\n\nexport function createHatcheryProxyHandler(config: HatcheryProxyConfig) {\n return async function hatcheryProxyHandler(\n req: NextApiRequest,\n res: NextApiResponse,\n ): Promise<void> {\n const hatcheryUrl = config.hatcheryUrl;\n\n if (!hatcheryUrl) {\n res.status(503).json({\n error: 'Hatchery service is not configured (HATCHERY_URL missing).',\n });\n return;\n }\n\n if (!ALLOWED_HATCHERY_URLS.includes(hatcheryUrl)) {\n res.status(503).json({ error: 'Hatchery service URL is misconfigured.' });\n return;\n }\n\n let parsedHatcheryUrl: URL;\n try {\n parsedHatcheryUrl = new URL(hatcheryUrl);\n } catch {\n res.status(503).json({ error: 'Hatchery service URL is misconfigured.' });\n return;\n }\n if (\n parsedHatcheryUrl.protocol !== 'http:' &&\n parsedHatcheryUrl.protocol !== 'https:'\n ) {\n res.status(503).json({ error: 'Hatchery service URL is misconfigured.' });\n return;\n }\n\n // --- Auth: host-injected extractor first, minimal fallback for dev/standalone ---\n const jwt = config.getToken\n ? config.getToken(req)\n : extractTokenFallback(req);\n if (!jwt) {\n res.status(401).json({ error: 'Authentication required.' });\n return;\n }\n\n // Validate JWT format to prevent injection attacks\n // JWT should be three base64url-encoded segments separated by dots\n const JWT_FORMAT_RE = /^[A-Za-z0-9_-]+\\.[A-Za-z0-9_-]+\\.[A-Za-z0-9_-]+$/;\n if (!JWT_FORMAT_RE.test(jwt)) {\n console.error('[hatcheryProxy] Invalid JWT format detected');\n res.status(401).json({ error: 'Invalid authentication token format.' });\n return;\n }\n\n // Additional length check to prevent extremely long tokens\n if (jwt.length > 8192) {\n console.error('[hatcheryProxy] JWT exceeds maximum length');\n res.status(401).json({ error: 'Authentication token too long.' });\n return;\n }\n\n // Extract sub claim for REMOTE_USER — Ambassador already verified the signature.\n const claims = decodeJwtClaims(jwt);\n const rawUsername =\n claims?.sub ?? claims?.preferred_username ?? claims?.username;\n const username: string | undefined =\n typeof rawUsername === 'string' ? rawUsername : undefined;\n if (!username) {\n res\n .status(401)\n .json({ error: 'Unable to determine username from token.' });\n return;\n }\n // Strip CRLF to prevent HTTP header injection (defense-in-depth)\n const safeJwt = jwt.replace(/[\\r\\n]/g, '');\n const safeUsername = username.replace(/[\\r\\n]/g, '');\n\n // --- Route resolution ---\n const actionSegments = (req.query.action as string[]) || [];\n const route = resolveHatcheryRoute(req.method || '', actionSegments);\n if (!route) {\n res.status(404).json({ error: 'Route not found.' });\n return;\n }\n\n // --- Sanitize launch/terminate id param (SSRF prevention) ---\n let queryString = '';\n if (route.path === '/launch' || route.path === '/terminate') {\n const id = (req.query.id as string) || '';\n if (id) {\n if (!SAFE_ID_RE.test(id)) {\n res.status(400).json({ error: 'Invalid container identifier.' });\n return;\n }\n queryString = `?id=${encodeURIComponent(id)}`;\n }\n } else if (route.path === '/status' || route.path === '/options') {\n // Pass id through safely for status/options\n const id = (req.query.id as string) || '';\n if (id) {\n if (!SAFE_ID_RE.test(id)) {\n res.status(400).json({ error: 'Invalid container identifier.' });\n return;\n }\n queryString = `?id=${encodeURIComponent(id)}`;\n }\n }\n\n const hatcheryBase = `${parsedHatcheryUrl.origin}${parsedHatcheryUrl.pathname.replace(/\\/$/, '')}`;\n const targetUrl = `${hatcheryBase}${route.path}${queryString}`;\n\n await createProxyRequest({\n req,\n res,\n targetUrl,\n method: route.method,\n extraHeaders: {\n Authorization: `Bearer ${safeJwt}`,\n REMOTE_USER: safeUsername,\n remote_user: safeUsername,\n },\n // Hatchery doesn't need a body for GET routes\n forwardBody: route.method === 'POST',\n });\n };\n}\n","// Hatchery proxy — strict allowlist: /options, /status, /launch, /terminate\n// Injects Authorization + REMOTE_USER headers; sanitizes id param (SSRF prevention).\n// getToken reuses this app's cookie extraction — no JWT reinvention.\nimport { createHatcheryProxyHandler } from '../server/hatcheryProxy';\nimport { getAccessToken } from '@gen3/frontend/server';\nimport type { NextApiRequest, NextApiResponse } from 'next';\n\nconst defaultHatcheryUrl = process.env.KUBERNETES_SERVICE_HOST\n ? 'http://hatchery-service.gen3.svc.cluster.local'\n : '/lw-workspace';\n\nconst upstreamHandler = createHatcheryProxyHandler({\n hatcheryUrl: defaultHatcheryUrl,\n getToken: (req) => getAccessToken(req.headers['cookie'] ?? '') ?? null,\n});\n\nfunction decodeJwtUsername(jwt: string): string {\n try {\n const payload = jwt.split('.')[1];\n const claims = JSON.parse(\n Buffer.from(payload, 'base64url').toString('utf8'),\n ) as Record<string, unknown>;\n const raw = claims.sub ?? claims.preferred_username ?? claims.username;\n return typeof raw === 'string'\n ? raw\n : `<non-string:${JSON.stringify(raw)}>`;\n } catch {\n return '<decode-error>';\n }\n}\n\nexport default async function handler(\n req: NextApiRequest,\n res: NextApiResponse,\n) {\n const action = req.query.action?.[0];\n\n // Intercept res.send to capture response body for logging\n let capturedBody = '';\n const originalSend = res.send.bind(res) as typeof res.send;\n res.send = (body: unknown) => {\n capturedBody = (\n typeof body === 'string' ? body : JSON.stringify(body)\n ).slice(0, 300);\n return originalSend(body);\n };\n\n await upstreamHandler(req, res);\n}\n\nexport const config = { api: { bodyParser: false } };\n"],"names":["GEN3_HATCHERY_API","GEN3_WORKSPACE_API","process","env","GEN3_KERNEL_API","GEN3_API","JEG_GATEWAY_API","JEG_SERVICE_API","MAX_FILE_SIZE_BYTES","ALLOWED_TIERS","Set","SAFE_SEGMENT_RE","MIME_TYPES","REMOTE_DISABLED_EXTENSIONS","ASSETS_ROOT_PATH","JUPYTER_ASSETS_ROOT_PATH","defaultAssetRoot","startsWith","nodePath","join","cwd","resolveOrigin","req","forwardedProto","Array","isArray","headers","forwardedHost","hostHeader","host","refererHeader","referer","resolvedHost","trim","resolvedProto","String","refererUrl","URL","includes","protocol","replace","proto","injectRemoteConfig","html","gatewayBaseUrl","disabledExtensions","branding","appName","faviconUrl","absoluteGatewayBase","accessToken","undefined","NODE_ENV","getCookie","configData","remoteBaseUrl","remoteToken","fullThemesUrl","result","_match","openTag","existingJson","closeTag","existing","JSON","parse","merged","combined","stringify","injectBranding","error","Error","console","log","message","createWorkspaceAssetsHandler","options","JUPYTER_GATEWAY_BASE_URL","assetRoot","additionalDisabledExtensions","walkDir","dir","set","entry","fs","readdirSync","withFileTypes","full","name","isDirectory","add","allowedFilesByTier","free","remote","tier","resolve","handler","res","path","pathSegments","query","has","status","end","segments","tierRoot","safeSegments","seg","test","push","basename","allowedFiles","candidatePath","candidateIndex","filePath","ext","extname","toLowerCase","contentType","isBuildAsset","setHeader","cookies","encodeURIComponent","isRemoteLabHtml","readFileSync","injected","send","isHtmlResponse","stat","statSync","size","stream","createReadStream","on","pipe","DEFAULT_WORKSPACE_ROUTES","withJupyterWorkspaces","nextConfig","workspaceRoutes","transpilePackages","filter","pkg","webpack","config","ctx","alias","react","dirname","require","rewrites","isDev","gatewayProxyUrl","GATEWAY_PROXY_URL","gatewayRewrite","source","destination","beforeFiles","coopCoepHeaders","map","route","key","value","extractTokenFallback","auth","slice","cookie","m","match","decodeURIComponent","MAX_JWT_LENGTH","decodeJwtClaims","jwt","length","parts","split","padded","padEnd","Math","ceil","Buffer","from","toString","createProxyRequest","targetUrl","method","extraHeaders","forwardBody","body","buf","bufferBody","err","statusCode","msg","json","upRes","fetch","signal","AbortSignal","timeout","get","errBody","text","catch","responseBody","MAX_BODY_BYTES","Promise","reject","chunks","total","chunk","destroy","Object","assign","concat","defaultBillingSink","event","stdout","write","type","EMPTY_FENCE_CREDS","key_id","api_key","fetchFenceCreds","fenceUrl","parsedFenceUrl","response","fetchFence","endpoint","Authorization","data","filterAndAnnotateSpecs","raw","policy","allowedSpecs","costPerHour","displayNames","nodeType","filteredSpecs","specName","rawSpec","kernelspecs","spec","display_name","metadata","filteredDefault","default","readBody","buildAmbassadorUrl","gen3Endpoint","kernelPath","base","parsed","origin","pathname","KERNEL_ID_RE","SIMPLE_ROUTES","Map","resolveKernelRoute","actionSegments","seg1","seg2","kernelId","rest","errMsg","handleKernelSpecs","upstream","ambassadorHeaders","ok","statusText","rawSpecs","kernelSpecPolicy","handleKernelsList","handleReap","listUpstream","kernelList","listRes","now","Date","idleKillMins","idleKillDays","maxAgeMins","maxKernelAgeDays","reaped","errors","kernel","id","lastActivity","last_activity","getTime","idleMins","Infinity","deleteUpstream","sink","username","action","costTier","timestamp","toISOString","handleKernelLaunch","fenceCreds","rawBody","launchBody","kernelSpec","enrichedBody","GEN3_API_KEY_ID","GEN3_API_KEY_SECRET","NAMESPACE","GEN3_ENDPOINT","launchTimestamp","launchRes","kernelData","handleKernelDelete","handleKernelPassthrough","ALLOWED_FENCE_URLS","GEN3_FENCE_SERVICE","GEN3_FENCE_API","ALLOWED_JEG_URLS","createKernelProxyHandler","billingSink","jegEnabled","kernelLifecycleProxyHandler","rawAction","s","enabled","getToken","claims","rawUsername","sub","preferred_username","safeJwt","safeUsername","REMOTE_USER","upstreamHandler","VECTIS_WORKSPACE_APP_NAME","VECTIS_FAVICON_URL","escapeHtml","firstHeader","injectVectisBranding","isRemoteTierRequest","absoluteRemoteBaseUrl","withConfig","rawContent","trimmed","endsWith","existingDisabled","remoteDisabledExtensions","GEN3_COMMONS_NAME","remoteKernelsBaseUrl","getHeader","some","v","originalSend","bind","ALLOWED_PREFIXES","buildUpstreamPath","clean","Boolean","isAllowedPath","prefix","buildQueryString","rawUrl","excludeKey","queryPart","params","URLSearchParams","delete","toUpperCase","isBuffer","gatewayUrl","JUPYTER_GATEWAY_URL","gatewayBase","upstreamPath","queryString","url","forwardHeaders","Headers","entries","lower","byteLength","Uint8Array","isTimeout","forEach","upstreamContentType","safeContentType","reader","getReader","done","read","releaseLock","inCluster","KUBERNETES_SERVICE_HOST","defaultGen3Endpoint","defaultFenceUrl","warn","KERNEL_SPEC_POLICY","ENABLE_JEG","token","getAccessToken","headersSent","SAFE_ID_RE","resolveHatcheryRoute","routes","ALLOWED_HATCHERY_URLS","createHatcheryProxyHandler","hatcheryProxyHandler","hatcheryUrl","parsedHatcheryUrl","JWT_FORMAT_RE","hatcheryBase","remote_user","defaultHatcheryUrl","capturedBody"],"mappings":";;;;;;;;;AAEA;AAEO,MAAMA,iBAAAA,GACXC,uBAAAA,IAAsB,oCAAoC;AAG1DC,OAAAA,CAAQC,GAAG,CAACC,eAAe,IAAI,CAAA,EAAGC,aAAAA,CAAS,iCAAiC;AAG5EH,OAAAA,CAAQC,GAAG,CAACG,eAAe,IAAI,CAAA,EAAGD,aAAAA,CAAS,iCAAiC;AAMvE,MAAME,kBACX,uEAAA;;ACEF,MAAMC,mBAAAA,GAAsB;AAoB5B;AAEA,MAAMC,aAAAA,GAAgB,IAAIC,GAAAA,CAAI;AAAC,IAAA,MAAA;AAAQ,IAAA;AAAS,CAAA,CAAA;AAEhD,MAAMC,eAAAA,GAAkB,qBAAA;AAExB,MAAMC,UAAAA,GAAqC;IACzC,OAAA,EAAS,0BAAA;IACT,KAAA,EAAO,uCAAA;IACP,MAAA,EAAQ,uCAAA;IACR,OAAA,EAAS,iCAAA;IACT,MAAA,EAAQ,yBAAA;IACR,OAAA,EAAS,kBAAA;IACT,MAAA,EAAQ,2BAAA;IACR,MAAA,EAAQ,eAAA;IACR,MAAA,EAAQ,WAAA;IACR,MAAA,EAAQ,cAAA;IACR,QAAA,EAAU,YAAA;IACV,OAAA,EAAS,WAAA;IACT,MAAA,EAAQ,UAAA;IACR,MAAA,EAAQ,iCAAA;IACR,QAAA,EAAU;AACZ,CAAA;AAEA,MAAMC,0BAAAA,GAA6B;AACjC,IAAA,wDAAA;AACA,IAAA,+CAAA;AACA,IAAA,+CAAA;AACA,IAAA,2CAAA;AACA,IAAA,gDAAA;AACA,IAAA,+CAAA;AACA,IAAA,oDAAA;AACA,IAAA,qDAAA;AACA,IAAA,8CAAA;AACA,IAAA,mDAAA;AACA,IAAA,iDAAA;AACA,IAAA,2DAAA;AACA,IAAA;AACD,CAAA;AAED;AAEA,MAAMC,gBAAAA,GACJZ,OAAAA,CAAQC,GAAG,CAACY,wBAAwB,IAAI,iCAAA;AAE1C,SAASC,gBAAAA,GAAAA;IACP,OAAOF,gBAAAA,CAAiBG,UAAU,CAAC,GAAA,CAAA,GAC/BH,gBAAAA,GACAI,SAASC,IAAI,CAACjB,OAAAA,CAAQkB,GAAG,EAAA,EAAIN,gBAAAA,CAAAA;AACnC;AAMA;;;IAIA,SAASO,gBAAcC,GAAmB,EAAA;IACxC,MAAMC,cAAAA,GACJ,CAACC,KAAAA,CAAMC,OAAO,CAACH,GAAAA,CAAII,OAAO,CAAC,mBAAA,CAAoB,CAAA,GAC3CJ,IAAII,OAAO,CAAC,mBAAA,CAAoB,CAAC,CAAA,CAAE,GACnCJ,IAAII,OAAO,CAAC,mBAAA,CAAmB,KAAM,MAAA;AAC3C,IAAA,MAAMC,gBAAgBH,KAAAA,CAAMC,OAAO,CAACH,GAAAA,CAAII,OAAO,CAAC,kBAAA,CAAmB,CAAA,GAC/DJ,IAAII,OAAO,CAAC,mBAAmB,CAAC,CAAA,CAAE,GAClCJ,GAAAA,CAAII,OAAO,CAAC,kBAAA,CAAmB;AACnC,IAAA,MAAME,aAAaJ,KAAAA,CAAMC,OAAO,CAACH,GAAAA,CAAII,OAAO,CAACG,IAAI,CAAA,GAC7CP,IAAII,OAAO,CAACG,IAAI,CAAC,CAAA,CAAE,GACnBP,GAAAA,CAAII,OAAO,CAACG,IAAI;AACpB,IAAA,MAAMC,gBAAgBN,KAAAA,CAAMC,OAAO,CAACH,GAAAA,CAAII,OAAO,CAACK,OAAO,CAAA,GACnDT,IAAII,OAAO,CAACK,OAAO,CAAC,CAAA,CAAE,GACtBT,GAAAA,CAAII,OAAO,CAACK,OAAO;AAEvB,IAAA,IAAIC,eAAe,CAACL,iBAAiBC,UAAAA,IAAc,EAAC,EAAGK,IAAI,EAAA;AAC3D,IAAA,IAAIC,aAAAA,GAAgBC,MAAAA,CAAOZ,cAAAA,CAAAA,CAAgBU,IAAI,EAAA,IAAM,MAAA;AAErD,IAAA,IAAIH,aAAAA,EAAe;QACjB,IAAI;YACF,MAAMM,UAAAA,GAAa,IAAIC,GAAAA,CAAIP,aAAAA,CAAAA;AAC3B,YAAA,IAAI,CAACE,YAAAA,IAAgB,CAACA,YAAAA,CAAaM,QAAQ,CAAC,GAAA,CAAA,EAAM;AAChDN,gBAAAA,YAAAA,GAAeI,WAAWP,IAAI;AAChC,YAAA;AACA,YAAA,IAAI,CAACK,aAAAA,EAAe;AAClBA,gBAAAA,aAAAA,GAAgBE,UAAAA,CAAWG,QAAQ,CAACC,OAAO,CAAC,GAAA,EAAK,EAAA,CAAA;AACnD,YAAA;AACF,QAAA,CAAA,CAAE,OAAM;;AAER,QAAA;AACF,IAAA;AAEA,IAAA,IAAI,CAACR,YAAAA,EAAc;QACjBA,YAAAA,GAAe,gBAAA;AACjB,IAAA;IAEA,OAAO;QAAES,KAAAA,EAAOP,aAAAA;QAAeL,IAAAA,EAAMG;AAAa,KAAA;AACpD;AAEA,SAASU,kBAAAA,CACPC,IAAY,EACZrB,GAAmB,EACnBsB,cAAsB,EACtBC,kBAA4B,EAC5BC,QAAAA,GAAW;IACTC,OAAAA,EAAS,aAAA;IACTC,UAAAA,EAAY;AACd,CAAmB,EAAA;AAEnB,IAAA,MAAM,EAAEP,KAAK,EAAEZ,IAAI,EAAE,GAAGR,eAAAA,CAAcC,GAAAA,CAAAA;AACtC,IAAA,MAAM2B,sBAAsB,CAAA,EAAGR,KAAAA,CAAM,GAAG,EAAEZ,OAAOe,cAAAA,CAAAA,CAAgB;;;AAKjE,IAAA,IAAIM,WAAAA,GAAcC,SAAAA;AAClB,IAAA,IAAIjD,OAAAA,CAAQC,GAAG,CAACiD,QAAQ,KAAK,aAAA,EAAe;;;AAG1CF,QAAAA,WAAAA,GAAcG,qBAAAA,CAAU,mBAAA,CAAA;AAC1B,IAAA;AAEA,IAAA,MAAMC,UAAAA,GAAsC;QAC1CC,aAAAA,EAAeN,mBAAAA;QACfO,WAAAA,EAAaN,WAAAA;AACbL,QAAAA,kBAAAA;QACAY,aAAAA,EAAe;AACjB,KAAA;AAEA,IAAA,IAAIX,UAAUC,OAAAA,EAASO,UAAAA,CAAWP,OAAO,GAAGD,SAASC,OAAO;AAC5D,IAAA,IAAID,UAAUE,UAAAA,EAAYM,UAAAA,CAAWN,UAAU,GAAGF,SAASE,UAAU;IAErE,IAAIU,MAAAA,GAASf,KAAKH,OAAO,CACvB,2EACA,CAACmB,MAAAA,EAAQC,SAAiBC,YAAAA,EAAsBC,QAAAA,GAAAA;AAC9C,QAAA,IAAIC,WAAoC,EAAC;QACzC,IAAI;YACFA,QAAAA,GAAWC,IAAAA,CAAKC,KAAK,CAACJ,YAAAA,CAAAA;AACxB,QAAA,CAAA,CAAE,OAAM;;AAER,QAAA;AACA,QAAA,MAAMK,MAAAA,GAAS;AAAE,YAAA,GAAGH,QAAQ;AAAE,YAAA,GAAGT;AAAW,SAAA;AAC5C,QAAA,IAAI9B,KAAAA,CAAMC,OAAO,CAACsC,QAAAA,CAASlB,kBAAkB,CAAA,EAAG;YAC9C,MAAMsB,QAAAA,GAAW,IAAIzD,GAAAA,CAAI;AACnBqD,gBAAAA,GAAAA,QAAAA,CAASlB,kBAAkB;AAC5BA,gBAAAA,GAAAA;AACJ,aAAA,CAAA;AACDqB,YAAAA,MAAAA,CAAOrB,kBAAkB,GAAG;AAAIsB,gBAAAA,GAAAA;AAAS,aAAA;AAC3C,QAAA;AACA,QAAA,OAAO,GAAGP,OAAAA,CAAAA,EAAUI,IAAAA,CAAKI,SAAS,CAACF,UAAUJ,QAAAA,CAAAA,CAAU;AACzD,IAAA,CAAA,CAAA;AAGF,IAAA,IAAIhB,UAAUC,OAAAA,EAAS;QACrBW,MAAAA,GAASA,MAAAA,CAAOlB,OAAO,CACrB,uBAAA,EACA,CAAC,OAAO,EAAEM,QAAAA,CAASC,OAAO,CAAC,QAAQ,CAAC,CAAA;AAExC,IAAA;IAEA,OAAOW,MAAAA;AACT;AAEA,SAASW,cAAAA,CAAe1B,IAAY,EAAEG,QAAwB,EAAA;IAC5D,IAAIY,MAAAA,GAASf,KAAKH,OAAO,CACvB,2EACA,CAACmB,MAAAA,EAAQC,SAAiBC,YAAAA,EAAsBC,QAAAA,GAAAA;AAC9C,QAAA,IAAIC,WAAoC,EAAC;QACzC,IAAI;YACFA,QAAAA,GAAWC,IAAAA,CAAKC,KAAK,CAACJ,YAAAA,CAAAA;AACxB,QAAA,CAAA,CAAE,OAAOS,KAAAA,EAAgB;;AAEvB,YAAA,IAAIA,iBAAiBC,KAAAA,EAAO;AAC1BC,gBAAAA,OAAAA,CAAQC,GAAG,CAAC,+BAAA,EAAiCH,KAAAA,CAAMI,OAAO,CAAA;YAC5D,CAAA,MAAO;gBACLF,OAAAA,CAAQC,GAAG,CAAC,+BAAA,EAAiCH,KAAAA,CAAAA;AAC/C,YAAA;AACF,QAAA;AACA,QAAA,IAAIxB,SAASC,OAAO,EAAEgB,SAAShB,OAAO,GAAGD,SAASC,OAAO;AACzD,QAAA,IAAID,SAASE,UAAU,EAAEe,SAASf,UAAU,GAAGF,SAASE,UAAU;AAClE,QAAA,OAAO,GAAGY,OAAAA,CAAAA,EAAUI,IAAAA,CAAKI,SAAS,CAACL,YAAYD,QAAAA,CAAAA,CAAU;AAC3D,IAAA,CAAA,CAAA;IAGF,IAAIhB,QAAAA,CAASC,OAAO,EAAE;QACpBW,MAAAA,GAASA,MAAAA,CAAOlB,OAAO,CACrB,uBAAA,EACA,CAAC,OAAO,EAAEM,QAAAA,CAASC,OAAO,CAAC,QAAQ,CAAC,CAAA;AAExC,IAAA;IAEA,OAAOW,MAAAA;AACT;AAEA;AAEO,SAASiB,6BACdC,OAAuC,EAAA;AAEvC,IAAA,MAAMhC,iBACJgC,OAAAA,EAAShC,cAAAA,IACT1C,QAAQC,GAAG,CAAC0E,wBAAwB,IACpC,yBAAA;IAEFL,OAAAA,CAAQC,GAAG,CAAC,EAAA,GAAK,iBAAA,EAAmB7B,cAAAA,CAAAA;IAEpC,MAAMkC,SAAAA,GAAYF,SAASE,SAAAA,IAAa9D,gBAAAA,EAAAA;IAExC,MAAM6B,kBAAAA,GAAqB+B,SAASG,4BAAAA,GAChC;AAAIlE,QAAAA,GAAAA,0BAAAA;AAA+B+D,QAAAA,GAAAA,OAAAA,CAAQG;KAA6B,GACxElE,0BAAAA;AAEJ,IAAA,MAAMiC,QAAAA,GACJ8B,OAAAA,EAAS7B,OAAAA,IAAW6B,OAAAA,EAAS5B,UAAAA,GACzB;AAAED,QAAAA,OAAAA,EAAS6B,QAAQ7B,OAAO;AAAEC,QAAAA,UAAAA,EAAY4B,QAAQ5B;KAAW,GAC3DG,SAAAA;;;IAIN,MAAM6B,OAAAA,GAAU,CAACC,GAAAA,EAAaC,GAAAA,GAAAA;QAC5B,IAAI;AACF,YAAA,KAAK,MAAMC,KAAAA,IAASC,EAAAA,CAAGC,WAAW,CAACJ,GAAAA,EAAK;gBAAEK,aAAAA,EAAe;aAAK,CAAA,CAAI;AAChE,gBAAA,MAAMC,OAAOrE,QAAAA,CAASC,IAAI,CAAC8D,GAAAA,EAAKE,MAAMK,IAAI,CAAA;gBAC1C,IAAIL,KAAAA,CAAMM,WAAW,EAAA,EAAI;AACvBT,oBAAAA,OAAAA,CAAQO,IAAAA,EAAML,GAAAA,CAAAA;gBAChB,CAAA,MAAO;AACLA,oBAAAA,GAAAA,CAAIQ,GAAG,CAACH,IAAAA,CAAAA;AACV,gBAAA;AACF,YAAA;AACF,QAAA,CAAA,CAAE,OAAM;;AAER,QAAA;AACF,IAAA,CAAA;AAEA,IAAA,MAAMI,kBAAAA,GAAkD;AACtDC,QAAAA,IAAAA,EAAM,IAAIlF,GAAAA,EAAAA;AACVmF,QAAAA,MAAAA,EAAQ,IAAInF,GAAAA;AACd,KAAA;IACA,KAAK,MAAMoF,QAAQrF,aAAAA,CAAe;AAChCuE,QAAAA,OAAAA,CAAQ9D,SAAS6E,OAAO,CAACjB,WAAWgB,IAAAA,CAAAA,EAAOH,kBAAkB,CAACG,IAAAA,CAAK,CAAA;AACrE,IAAA;AAEA,IAAA,OAAO,SAASE,OAAAA,CAAQ1E,GAAmB,EAAE2E,GAAoB,EAAA;QAC/D,MAAM,EAAEH,IAAI,EAAEI,IAAAA,EAAMC,YAAY,EAAE,GAAG7E,IAAI8E,KAAK;AAE9C,QAAA,IAAI,OAAON,IAAAA,KAAS,QAAA,IAAY,CAACrF,aAAAA,CAAc4F,GAAG,CAACP,IAAAA,CAAAA,EAAO;AACxDG,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,WAAA,CAAA;AACpB,YAAA;AACF,QAAA;AAEA,QAAA,MAAMC,WAAqBhF,KAAAA,CAAMC,OAAO,CAAC0E,YAAAA,CAAAA,GACrCA,eACAA,YAAAA,GACE;AAACA,YAAAA;AAAa,SAAA,GACd,EAAE;QAER,IAAIM,QAAAA;AACJ,QAAA,IAAIX,SAAS,MAAA,EAAQ;YACnBW,QAAAA,GAAWvF,QAAAA,CAAS6E,OAAO,CAACjB,SAAAA,EAAW,MAAA,CAAA;QACzC,CAAA,MAAO,IAAIgB,SAAS,QAAA,EAAU;YAC5BW,QAAAA,GAAWvF,QAAAA,CAAS6E,OAAO,CAACjB,SAAAA,EAAW,QAAA,CAAA;QACzC,CAAA,MAAO;AACLmB,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,WAAA,CAAA;AACpB,YAAA;AACF,QAAA;AAEA,QAAA,MAAMG,eAAyB,EAAE;QACjC,KAAK,MAAMC,OAAOH,QAAAA,CAAU;YAC1B,IACE,OAAOG,GAAAA,KAAQ,QAAA,IACf,CAAChG,eAAAA,CAAgBiG,IAAI,CAACD,GAAAA,CAAAA,IACtBA,GAAAA,KAAQ,GAAA,IACRA,GAAAA,KAAQ,IAAA,EACR;AACAV,gBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,WAAA,CAAA;AACpB,gBAAA;AACF,YAAA;AACAG,YAAAA,YAAAA,CAAaG,IAAI,CAAC3F,QAAAA,CAAS4F,QAAQ,CAACH,GAAAA,CAAAA,CAAAA;AACtC,QAAA;QAEA,MAAMI,YAAAA,GAAepB,kBAAkB,CAACG,IAAAA,CAAK;AAE7C,QAAA,MAAMkB,aAAAA,GAAgB9F,QAAAA,CAAS6E,OAAO,CAACU,QAAAA,EAAAA,GAAaC,YAAAA,CAAAA;AACpD,QAAA,MAAMO,cAAAA,GAAiB/F,QAAAA,CAASC,IAAI,CAAC6F,aAAAA,EAAe,YAAA,CAAA;QAEpD,IAAIE,QAAAA;QACJ,IAAIH,YAAAA,CAAaV,GAAG,CAACW,aAAAA,CAAAA,EAAgB;YACnCE,QAAAA,GAAWF,aAAAA;AACb,QAAA,CAAA,MAAO,IAAID,YAAAA,CAAaV,GAAG,CAACY,cAAAA,CAAAA,EAAiB;YAC3CC,QAAAA,GAAWD,cAAAA;QACb,CAAA,MAAO;AACLhB,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,WAAA,CAAA;AACpB,YAAA;AACF,QAAA;AAEA,QAAA,MAAMY,GAAAA,GAAMjG,QAAAA,CAASkG,OAAO,CAACF,UAAUG,WAAW,EAAA;AAClD,QAAA,MAAMC,WAAAA,GAAc1G,UAAU,CAACuG,GAAAA,CAAI,IAAI,0BAAA;AAEvC,QAAA,MAAMI,YAAAA,GACJL,QAAAA,CAAS5E,QAAQ,CAACpB,SAASC,IAAI,CAAC2E,IAAAA,EAAM,OAAA,CAAA,CAAA,IACtCoB,SAAS5E,QAAQ,CAACpB,QAAAA,CAASC,IAAI,CAAC2E,IAAAA,EAAM,YAAA,CAAA,CAAA;QAExCG,GAAAA,CAAIuB,SAAS,CAAC,wBAAA,EAA0B,SAAA,CAAA;QACxCvB,GAAAA,CAAIuB,SAAS,CAAC,4BAAA,EAA8B,aAAA,CAAA;QAC5CvB,GAAAA,CAAIuB,SAAS,CAAC,8BAAA,EAAgC,cAAA,CAAA;QAC9CvB,GAAAA,CAAIuB,SAAS,CAAC,8BAAA,EAAgC,cAAA,CAAA;AAE9C,QAAA,IAAItH,OAAAA,CAAQC,GAAG,CAACiD,QAAQ,KAAK,aAAA,EAAe;;;;;;;AAO1C,YAAA,MAAMF,WAAAA,GAAc5B,GAAAA,CAAImG,OAAO,GAAG,mBAAA,CAAoB;AACtD,YAAA,IAAIvE,WAAAA,EAAa;gBACf+C,GAAAA,CAAIuB,SAAS,CACX,YAAA,EACA,CAAC,aAAa,EAAEE,kBAAAA,CAAmBxE,WAAAA,CAAAA,CAAa,sBAAsB,CAAC,CAAA;AAE3E,YAAA;AACF,QAAA;AAEA,QAAA,IAAIhC,QAAAA,CAAS4F,QAAQ,CAACI,QAAAA,CAAAA,KAAc,mBAAA,EAAqB;YACvDjB,GAAAA,CAAIuB,SAAS,CAAC,wBAAA,EAA0B,GAAA,CAAA;AAC1C,QAAA;QAEA,MAAMG,eAAAA,GACJ7B,IAAAA,KAAS,QAAA,IACTqB,GAAAA,KAAQ,OAAA,IACRD,QAAAA,CAAS5E,QAAQ,CAACpB,QAAAA,CAASC,IAAI,CAAC,KAAA,EAAO,YAAA,CAAA,CAAA;AAEzC,QAAA,IAAIwG,eAAAA,EAAiB;YACnB1B,GAAAA,CAAIuB,SAAS,CAAC,cAAA,EAAgBF,WAAAA,CAAAA;YAC9BrB,GAAAA,CAAIuB,SAAS,CAAC,eAAA,EAAiB,qCAAA,CAAA;YAC/B,IAAI;AACF,gBAAA,MAAM7E,IAAAA,GAAOyC,EAAAA,CAAGwC,YAAY,CAACV,QAAAA,EAAU,OAAA,CAAA;AACvC,gBAAA,MAAMW,QAAAA,GAAWnF,kBAAAA,CACfC,IAAAA,EACArB,GAAAA,EACAsB,gBACAC,kBAAAA,EACAC,QAAAA,CAAAA;AAEFmD,gBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKwB,IAAI,CAACD,QAAAA,CAAAA;AACvB,YAAA,CAAA,CAAE,OAAM;AACN5B,gBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,uBAAA,CAAA;AACtB,YAAA;AACA,YAAA;AACF,QAAA;;AAGA,QAAA,MAAMwB,iBAAiBZ,GAAAA,KAAQ,OAAA;AAC/B,QAAA,IAAIY,kBAAkBjF,QAAAA,EAAU;YAC9BmD,GAAAA,CAAIuB,SAAS,CAAC,cAAA,EAAgBF,WAAAA,CAAAA;YAC9BrB,GAAAA,CAAIuB,SAAS,CAAC,eAAA,EAAiB,qCAAA,CAAA;YAC/B,IAAI;AACF,gBAAA,MAAM7E,IAAAA,GAAOyC,EAAAA,CAAGwC,YAAY,CAACV,QAAAA,EAAU,OAAA,CAAA;AACvCjB,gBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKwB,IAAI,CAACzD,eAAe1B,IAAAA,EAAMG,QAAAA,CAAAA,CAAAA;AAC5C,YAAA,CAAA,CAAE,OAAM;AACNmD,gBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,uBAAA,CAAA;AACtB,YAAA;AACA,YAAA;AACF,QAAA;QAEAN,GAAAA,CAAIuB,SAAS,CAAC,cAAA,EAAgBF,WAAAA,CAAAA;AAC9BrB,QAAAA,GAAAA,CAAIuB,SAAS,CACX,eAAA,EACAD,YAAAA,GACI,qCAAA,GACA,uCAAA,CAAA;QAGN,MAAMS,IAAAA,GAAO5C,EAAAA,CAAG6C,QAAQ,CAACf,QAAAA,CAAAA;QACzB,IAAIc,IAAAA,CAAKE,IAAI,GAAG1H,mBAAAA,EAAqB;AACnCyF,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,gBAAA,CAAA;AACpB,YAAA;AACF,QAAA;QAEA,MAAM4B,MAAAA,GAAS/C,EAAAA,CAAGgD,gBAAgB,CAAClB,QAAAA,CAAAA;QACnCiB,MAAAA,CAAOE,EAAE,CAAC,OAAA,EAAS,IAAA;AACjBpC,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,CAAC,uBAAA,CAAA;AACtB,QAAA,CAAA,CAAA;AACA4B,QAAAA,MAAAA,CAAOG,IAAI,CAACrC,GAAAA,CAAAA;AACd,IAAA,CAAA;AACF;AAEA,kDACuBtB,4BAAAA;;AChZvB,MAAM4D,wBAAAA,GAA2B;AAAC,IAAA;AAAc,CAAA;AAEzC,SAASC,qBAAAA,CACdC,UAAsB,EACtB7D,OAAsC,EAAA;IAEtC,MAAM8D,eAAAA,GAAkB9D,SAAS8D,eAAAA,IAAmBH,wBAAAA;IAEpD,OAAO;AACL,QAAA,GAAGE,UAAU;;QAGbE,iBAAAA,EAAmB;eACbF,UAAAA,CAAWE,iBAAiB,IAAI,EAAE;AACnC,YAAA,GAAA;AAAC,gBAAA;AAAmB,aAAA,CAACC,MAAM,CAC5B,CAACC,GAAAA,GAAQ,CAAC,CAACJ,UAAAA,CAAWE,iBAAiB,IAAI,EAAE,EAAErG,QAAQ,CAACuG,GAAAA,CAAAA;AAE3D,SAAA;;QAGDC,OAAAA,CAAAA,CAAQC,MAAqB,EAAEC,GAAyB,EAAA;AACtDD,YAAAA,MAAAA,CAAOhD,OAAO,GAAGgD,MAAAA,CAAOhD,OAAO,IAAI,EAAC;YACpCgD,MAAAA,CAAOhD,OAAO,CAACkD,KAAK,GAAG;AACrB,gBAAA,GAAIF,OAAOhD,OAAO,CAACkD,KAAK,IAAI,EAAE;AAC9BC,gBAAAA,KAAAA,EAAOhI,QAAAA,CAASiI,OAAO,CAACC,OAAAA,CAAQrD,OAAO,CAAC,oBAAA,CAAA,CAAA;AACxC,gBAAA,WAAA,EAAa7E,QAAAA,CAASiI,OAAO,CAC3BC,OAAAA,CAAQrD,OAAO,CAAC,wBAAA,CAAA;AAEpB,aAAA;;AAGA,YAAA,IAAI,OAAO0C,UAAAA,CAAWK,OAAO,KAAK,UAAA,EAAY;gBAC5C,OAAOL,UAAAA,CAAWK,OAAO,CAACC,MAAAA,EAAQC,GAAAA,CAAAA;AACpC,YAAA;YACA,OAAOD,MAAAA;AACT,QAAA,CAAA;;QAGA,MAAMM,QAAAA,CAAAA,GAAAA;AACJ,YAAA,MAAMC,KAAAA,GAAQpJ,OAAAA,CAAQC,GAAG,CAACiD,QAAQ,KAAK,aAAA;YAEvC,MAAMW,QAAAA,GACJ,OAAO0E,UAAAA,CAAWY,QAAQ,KAAK,aAC3B,MAAMZ,UAAAA,CAAWY,QAAQ,EAAA,GACzB,EAAE;YAER,IAAI,CAACC,OAAO,OAAOvF,QAAAA;AAEnB,YAAA,MAAMwF,kBACJ3E,OAAAA,EAAS2E,eAAAA,IACTrJ,QAAQC,GAAG,CAACqJ,iBAAiB,IAC7B,uBAAA;AAEF,YAAA,MAAMC,cAAAA,GAAiB;gBACrBC,MAAAA,EAAQ,+BAAA;gBACRC,WAAAA,EAAa,CAAA,EAAGJ,eAAAA,CAAgB,6BAA6B;AAC/D,aAAA;;YAGA,IAAI/H,KAAAA,CAAMC,OAAO,CAACsC,QAAAA,CAAAA,EAAW;gBAC3B,OAAO;AAAC0F,oBAAAA,cAAAA;AAAmB1F,oBAAAA,GAAAA;AAAS,iBAAA;AACtC,YAAA;YACA,OAAO;AACL,gBAAA,GAAGA,QAAQ;gBACX6F,WAAAA,EAAa;AAACH,oBAAAA,cAAAA;uBAAoB1F,QAAAA,CAAS6F,WAAW,IAAI;AAAI;AAChE,aAAA;AACF,QAAA,CAAA;;QAGA,MAAMlI,OAAAA,CAAAA,GAAAA;YACJ,MAAMqC,QAAAA,GACJ,OAAO0E,UAAAA,CAAW/G,OAAO,KAAK,aAC1B,MAAM+G,UAAAA,CAAW/G,OAAO,EAAA,GACxB,EAAE;AAER,YAAA,MAAMmI,kBAAkBnB,eAAAA,CAAgBoB,GAAG,CAAC,CAACC,SAAW;oBACtDL,MAAAA,EAAQK,KAAAA;oBACRrI,OAAAA,EAAS;AACP,wBAAA;4BAAEsI,GAAAA,EAAK,4BAAA;4BAA8BC,KAAAA,EAAO;AAAc,yBAAA;AAC1D,wBAAA;4BAAED,GAAAA,EAAK,8BAAA;4BAAgCC,KAAAA,EAAO;AAAiB;AAChE;iBACH,CAAA,CAAA;YAEA,OAAO;AAAIlG,gBAAAA,GAAAA,QAAAA;AAAa8F,gBAAAA,GAAAA;AAAgB,aAAA;AAC1C,QAAA;AACF,KAAA;AACF;;ACjHA;;;;;;;;;;;;;IAkBO,SAASK,oBAAAA,CAAqB5I,GAAmB,EAAA;AACtD,IAAA,MAAM6I,IAAAA,GAAO7I,GAAAA,CAAII,OAAO,CAAC,eAAA,CAAgB;AACzC,IAAA,IAAI,OAAOyI,IAAAA,KAAS,QAAA,IAAYA,IAAAA,CAAKlJ,UAAU,CAAC,SAAA,CAAA,EAAY;AAC1D,QAAA,OAAOkJ,IAAAA,CAAKC,KAAK,CAAC,CAAA,CAAA,CAAGnI,IAAI,EAAA,IAAM,IAAA;AACjC,IAAA;AACA,IAAA,MAAMoI,MAAAA,GAAS/I,GAAAA,CAAII,OAAO,CAAC,SAAS,IAAI,EAAA;IACxC,MAAM4I,CAAAA,GAAID,MAAAA,CAAOE,KAAK,CAAC,gCAAA,CAAA;IACvB,OAAOD,CAAAA,GAAIE,mBAAmBF,CAAC,CAAC,EAAE,CAAA,CAAErI,IAAI,MAAM,IAAA,GAAO,IAAA;AACvD;AAEA;;;;AAIC;AAED;AACA;AACA;AACA;AACA;AACA,MAAMwI,cAAAA,GAAiB;AAEhB,SAASC,gBAAgBC,GAAW,EAAA;AACzC,IAAA,IAAIA,GAAAA,CAAIC,MAAM,GAAGH,cAAAA,EAAgB,OAAO,IAAA;IACxC,IAAI;QACF,MAAMI,KAAAA,GAAQF,GAAAA,CAAIG,KAAK,CAAC,GAAA,CAAA;AACxB,QAAA,IAAID,KAAAA,CAAMD,MAAM,GAAG,CAAA,EAAG,OAAO,IAAA;QAC7B,MAAMG,MAAAA,GAASF,KAAK,CAAC,CAAA,CAAE,CACpBrI,OAAO,CAAC,IAAA,EAAM,GAAA,CAAA,CACdA,OAAO,CAAC,IAAA,EAAM,KACdwI,MAAM,CAACC,IAAAA,CAAKC,IAAI,CAACL,KAAK,CAAC,CAAA,CAAE,CAACD,MAAM,GAAG,CAAA,CAAA,GAAK,CAAA,EAAG,GAAA,CAAA;QAC9C,OAAO5G,IAAAA,CAAKC,KAAK,CAACkH,MAAAA,CAAOC,IAAI,CAACL,MAAAA,EAAQ,QAAA,CAAA,CAAUM,QAAQ,CAAC,MAAA,CAAA,CAAA;AAI3D,IAAA,CAAA,CAAE,OAAM;QACN,OAAO,IAAA;AACT,IAAA;AACF;AAYO,eAAeC,kBAAAA,CAAmB,EACvChK,GAAG,EACH2E,GAAG,EACHsF,SAAS,EACTC,MAAM,EACNC,YAAAA,GAAe,EAAE,EACjBC,WAAAA,GAAc,KAAK,EACC,EAAA;AACpB,IAAA,MAAMhK,OAAAA,GAAkC;AACtC,QAAA,GAAG+J;AACL,KAAA;IACA,IACEC,WAAAA,KACCF,MAAAA,KAAW,MAAA,IAAUA,WAAW,KAAA,IAASA,MAAAA,KAAW,OAAM,CAAA,EAC3D;QACA9J,OAAO,CAAC,eAAe,KAAK,kBAAA;AAC9B,IAAA;IAEA,IAAIiK,IAAAA;IACJ,IACED,WAAAA,KACCF,MAAAA,KAAW,MAAA,IAAUA,WAAW,KAAA,IAASA,MAAAA,KAAW,OAAM,CAAA,EAC3D;QACA,IAAII,GAAAA;QACJ,IAAI;AACFA,YAAAA,GAAAA,GAAM,MAAMC,UAAAA,CAAWvK,GAAAA,CAAAA;AACzB,QAAA,CAAA,CAAE,OAAOwK,GAAAA,EAAK;AACZ,YAAA,MAAMC,UAAAA,GAAcD,GAAAA,CAAgCC,UAAU,IAAI,GAAA;AAClE,YAAA,MAAMC,GAAAA,GAAMF,GAAAA,YAAevH,KAAAA,GAAQuH,GAAAA,CAAIpH,OAAO,GAAG,aAAA;AACjDuB,YAAAA,GAAAA,CAAIK,MAAM,CAACyF,UAAAA,CAAAA,CAAYE,IAAI,CAAC;gBAAE3H,KAAAA,EAAO0H;AAAI,aAAA,CAAA;AACzC,YAAA;AACF,QAAA;;QAEAL,IAAAA,GAAOC,GAAAA;QACP,IAAIA,GAAAA,CAAIhB,MAAM,GAAG,CAAA,EAAG;AAClBlJ,YAAAA,OAAO,CAAC,gBAAA,CAAiB,GAAGS,MAAAA,CAAOyJ,IAAIhB,MAAM,CAAA;AAC/C,QAAA;AACF,IAAA;IAEA,IAAIsB,KAAAA;IACJ,IAAI;QACFA,KAAAA,GAAQ,MAAMC,MAAMZ,SAAAA,EAAW;AAC7BC,YAAAA,MAAAA;AACA9J,YAAAA,OAAAA;AACAiK,YAAAA,IAAAA;YACAS,MAAAA,EAAQC,WAAAA,CAAYC,OAAO,CAAC,MAAA;AAC9B,SAAA,CAAA;AACF,IAAA,CAAA,CAAE,OAAOR,GAAAA,EAAK;AACZ,QAAA,MAAME,MAAMF,GAAAA,YAAevH,KAAAA,GAAQuH,GAAAA,CAAIpH,OAAO,GAAGvC,MAAAA,CAAO2J,GAAAA,CAAAA;AACxD7F,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO,CAAC,sBAAsB,EAAE0H,GAAAA,CAAAA;AAAM,SAAA,CAAA;AAC7D,QAAA;AACF,IAAA;;AAGA,IAAA,MAAM1E,cAAc4E,KAAAA,CAAMxK,OAAO,CAAC6K,GAAG,CAAC,cAAA,CAAA,IAAmB,kBAAA;IACzDtG,GAAAA,CAAIuB,SAAS,CAAC,cAAA,EAAgBF,WAAAA,CAAAA;AAE9B,IAAA,IAAI4E,MAAM5F,MAAM,KAAK,OAAO4F,KAAAA,CAAM5F,MAAM,KAAK,GAAA,EAAK;AAChDL,QAAAA,GAAAA,CAAIK,MAAM,CAAC4F,KAAAA,CAAM5F,MAAM,EAAEC,GAAG,EAAA;AAC5B,QAAA;AACF,IAAA;;;IAIA,IAAI2F,KAAAA,CAAM5F,MAAM,IAAI,GAAA,EAAK;AACvB,QAAA,MAAMkG,UAAU,MAAMN,KAAAA,CAAMO,IAAI,EAAA,CAAGC,KAAK,CAAC,IAAM,EAAA,CAAA;AAC/ClI,QAAAA,OAAAA,CAAQF,KAAK,CACX,iCAAA,EACA4H,KAAAA,CAAM5F,MAAM,EACZiF,SAAAA,EACAiB,OAAAA,CAAAA;AAEFvG,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAA0B,SAAA,CAAA;AACxD,QAAA;AACF,IAAA;IAEA,MAAMqI,YAAAA,GAAe,MAAMT,KAAAA,CAAMO,IAAI,EAAA;AACrCxG,IAAAA,GAAAA,CAAIK,MAAM,CAAC4F,KAAAA,CAAM5F,MAAM,CAAA,CAAEwB,IAAI,CAAC6E,YAAAA,CAAAA;AAChC;AAEA;AACA;AACA,MAAMC,cAAAA,GAAiB,IAAI,IAAA,GAAO,IAAA;AAElC,SAASf,WAAWvK,GAAmB,EAAA;IACrC,OAAO,IAAIuL,OAAAA,CAAQ,CAAC9G,OAAAA,EAAS+G,MAAAA,GAAAA;AAC3B,QAAA,MAAMC,SAAmB,EAAE;AAC3B,QAAA,IAAIC,KAAAA,GAAQ,CAAA;QACZ1L,GAAAA,CAAI+G,EAAE,CAAC,MAAA,EAAQ,CAAC4E,KAAAA,GAAAA;AACdD,YAAAA,KAAAA,IAASC,MAAMrC,MAAM;AACrB,YAAA,IAAIoC,QAAQJ,cAAAA,EAAgB;AAC1BtL,gBAAAA,GAAAA,CAAI4L,OAAO,EAAA;AACXJ,gBAAAA,MAAAA,CACEK,MAAAA,CAAOC,MAAM,CAAC,IAAI7I,MAAM,wBAAA,CAAA,EAA2B;oBACjDwH,UAAAA,EAAY;AACd,iBAAA,CAAA,CAAA;AAEF,gBAAA;AACF,YAAA;AACAgB,YAAAA,MAAAA,CAAOlG,IAAI,CAACoG,KAAAA,CAAAA;AACd,QAAA,CAAA,CAAA;AACA3L,QAAAA,GAAAA,CAAI+G,EAAE,CAAC,KAAA,EAAO,IAAMtC,OAAAA,CAAQoF,MAAAA,CAAOkC,MAAM,CAACN,MAAAA,CAAAA,CAAAA,CAAAA;QAC1CzL,GAAAA,CAAI+G,EAAE,CAAC,OAAA,EAASyE,MAAAA,CAAAA;AAClB,IAAA,CAAA,CAAA;AACF;;AC1DA,4NAIA,SAASQ,mBAAmBC,KAAmB,EAAA;;AAE7CrN,IAAAA,OAAAA,CAAQsN,MAAM,CAACC,KAAK,CAClBzJ,IAAAA,CAAKI,SAAS,CAAC;QAAEsJ,IAAAA,EAAM,mBAAA;AAAqB,QAAA,GAAGH;KAAM,CAAA,GAAK,IAAA,CAAA;AAE9D;AAWA,MAAMI,iBAAAA,GAAgC;IACpCC,MAAAA,EAAQ,EAAA;IACRC,OAAAA,EAAS;AACX,CAAA;AAEA,eAAeC,eAAAA,CACbC,QAAgB,EAChBpD,GAAW,EAAA;IAEX,IAAIqD,cAAAA;IACJ,IAAI;AACFA,QAAAA,cAAAA,GAAiB,IAAI3L,GAAAA,CAAI0L,QAAAA,CAAAA;AAC3B,IAAA,CAAA,CAAE,OAAM;AACN,QAAA,MAAM,IAAIxJ,KAAAA,CAAM,6BAAA,CAAA;AAClB,IAAA;AACA,IAAA,IACEyJ,eAAezL,QAAQ,KAAK,WAC5ByL,cAAAA,CAAezL,QAAQ,KAAK,QAAA,EAC5B;AACA,QAAA,MAAM,IAAIgC,KAAAA,CAAM,6BAAA,CAAA;AAClB,IAAA;IACA,IAAI;QACF,MAAM0J,QAAAA,GAAW,MAAMC,eAAAA,CACrB;YACEC,QAAAA,EAAU,iBAAA;YACV3C,MAAAA,EAAQ,KAAA;YACR9J,OAAAA,EAAS;gBACP0M,aAAAA,EAAe,CAAC,OAAO,EAAEzD,GAAAA,CAAAA,CAAK;gBAC9B,cAAA,EAAgB;AAClB;AACF,SAAA,EACAzK,OAAAA,CAAQC,GAAG,CAACiD,QAAQ,KAAK,YAAA,CAAA;QAE3B,IAAI,CAAC6K,QAAAA,EAAUI,IAAAA,EAAMR,OAAAA,EAAS;AAC5BrJ,YAAAA,OAAAA,CAAQF,KAAK,CAAC,0CAAA,CAAA;YACd,OAAO;gBACLuJ,OAAAA,EAAS,EAAA;gBACTD,MAAAA,EAAQ;AACV,aAAA;AACF,QAAA;AACA,QAAA,OAAOK,SAASI,IAAI;AACtB,IAAA,CAAA,CAAE,OAAO/J,KAAAA,EAAgB;AACvB,QAAA,IAAIA,iBAAiBC,KAAAA,EAAO;YAC1BC,OAAAA,CAAQF,KAAK,CAAC,oCAAA,EAAsCA,KAAAA,CAAAA;QACtD,CAAA,MAAO;AACLE,YAAAA,OAAAA,CAAQF,KAAK,CAAC,mCAAA,CAAA;AAChB,QAAA;QACA,OAAOqJ,iBAAAA;AACT,IAAA;AACF;AAuBA,SAASW,sBAAAA,CACPC,GAA2B,EAC3BC,MAAiC,EAAA;AAEjC,IAAA,MAAMC,YAAAA,GAAeD,MAAAA,CAAOC,YAAY,IAAI,EAAE;AAC9C,IAAA,MAAMC,WAAAA,GAAcF,MAAAA,CAAOE,WAAW,IAAI,EAAC;AAC3C,IAAA,MAAMC,YAAAA,GAAeH,MAAAA,CAAOG,YAAY,IAAI,EAAC;AAC7C,IAAA,MAAMC,QAAAA,GAAWJ,MAAAA,CAAOI,QAAQ,IAAI,EAAC;IAErC,IAAIH,YAAAA,CAAa7D,MAAM,KAAK,CAAA,EAAG;;QAE7B,OAAO2D,GAAAA;AACT,IAAA;AAEA,IAAA,MAAMM,gBAAuD,EAAC;IAE9D,KAAK,MAAMC,YAAYL,YAAAA,CAAc;AACnC,QAAA,MAAMM,OAAAA,GAAUR,GAAAA,CAAIS,WAAW,CAACF,QAAAA,CAAS;QACzC,IAAI,CAACC,OAAAA,EAAS,SAAA;QAEdF,aAAa,CAACC,SAAS,GAAG;AACxB,YAAA,GAAGC,OAAO;YACVE,IAAAA,EAAM;AACJ,gBAAA,GAAGF,QAAQE,IAAI;;AAEfC,gBAAAA,YAAAA,EAAcP,YAAY,CAACG,QAAAA,CAAS,IAAIC,OAAAA,CAAQE,IAAI,CAACC,YAAY;;gBAEjEC,QAAAA,EAAU;AACR,oBAAA,GAAIJ,QAAQE,IAAI,CAACE,QAAQ,IAAI,EAAE;oBAC/BT,WAAAA,EAAaA,WAAW,CAACI,QAAAA,CAAS,IAAI,CAAA;oBACtCF,QAAAA,EAAUA,QAAQ,CAACE,QAAAA,CAAS,IAAI;AAClC;AACF;AACF,SAAA;AACF,IAAA;;AAGA,IAAA,MAAMM,eAAAA,GAAkBX,YAAAA,CAAanM,QAAQ,CAACiM,GAAAA,CAAIc,OAAO,CAAA,GACrDd,GAAAA,CAAIc,OAAO,GACVZ,YAAY,CAAC,EAAE,IAAI,EAAA;IAExB,OAAO;QAAEY,OAAAA,EAASD,eAAAA;QAAiBJ,WAAAA,EAAaH;AAAc,KAAA;AAChE;AAEA,6NAIA,SAASS,WAAShO,GAAmB,EAAA;IACnC,OAAO,IAAIuL,OAAAA,CAAQ,CAAC9G,OAAAA,EAAS+G,MAAAA,GAAAA;AAC3B,QAAA,MAAMC,SAAmB,EAAE;AAC3BzL,QAAAA,GAAAA,CAAI+G,EAAE,CAAC,MAAA,EAAQ,CAAC4E,KAAAA,GAAkBF,MAAAA,CAAOlG,IAAI,CAACoG,KAAAA,CAAAA,CAAAA;AAC9C3L,QAAAA,GAAAA,CAAI+G,EAAE,CAAC,KAAA,EAAO,IAAMtC,OAAAA,CAAQoF,MAAAA,CAAOkC,MAAM,CAACN,MAAAA,CAAAA,CAAAA,CAAAA;QAC1CzL,GAAAA,CAAI+G,EAAE,CAAC,OAAA,EAASyE,MAAAA,CAAAA;AAClB,IAAA,CAAA,CAAA;AACF;AAEA;AAKA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AAEA,SAASyC,kBAAAA,CAAmBC,YAAoB,EAAEC,UAAkB,EAAA;;IAElE,MAAMC,IAAAA,GAAOF,aAAavO,UAAU,CAAC,UACjCuO,YAAAA,GACA,CAAC,QAAQ,EAAEA,YAAAA,CAAAA,CAAc;IAC7B,MAAMG,MAAAA,GAAS,IAAItN,GAAAA,CAAIqN,IAAAA,CAAAA;AACvB,IAAA,IAAIC,OAAOpN,QAAQ,KAAK,WAAWoN,MAAAA,CAAOpN,QAAQ,KAAK,QAAA,EAAU;AAC/D,QAAA,MAAM,IAAIgC,KAAAA,CAAM,+CAAA,CAAA;AAClB,IAAA;AACA,IAAA,OAAO,CAAA,EAAGoL,MAAAA,CAAOC,MAAM,CAAA,EAAGD,MAAAA,CAAOE,QAAQ,CAACrN,OAAO,CAAC,KAAA,EAAO,EAAA,CAAA,CAAI,mBAAmB,EAAEiN,UAAAA,CAAAA,CAAY;AAChG;AAEA,6NAIA,MAAMK,YAAAA,GAAe,oBAAA;AAgBrB;AACA,MAAMC,aAAAA,GAAgB,IAAIC,GAAAA,CAAyB;AACjD,IAAA;AAAC,QAAA,YAAA;AAAc,QAAA;YAAEtC,IAAAA,EAAM;AAAS;AAAE,KAAA;AAClC,IAAA;AAAC,QAAA,WAAA;AAAa,QAAA;YAAEA,IAAAA,EAAM;AAAO;AAAE,KAAA;AAC/B,IAAA;AAAC,QAAA,iBAAA;AAAmB,QAAA;YAAEA,IAAAA,EAAM;AAAc;AAAE,KAAA;AAC5C,IAAA;AAAC,QAAA,aAAA;AAAe,QAAA;YAAEA,IAAAA,EAAM;AAAe;AAAE,KAAA;AACzC,IAAA;AAAC,QAAA,cAAA;AAAgB,QAAA;YAAEA,IAAAA,EAAM;AAAgB;AAAE;AAC5C,CAAA,CAAA;AAED,SAASuC,kBAAAA,CACPzE,MAAc,EACd0E,cAAwB,EAAA;IAExB,MAAM,CAACC,IAAAA,EAAMC,IAAAA,CAAK,GAAGF,cAAAA;AAErB,IAAA,IAAI,CAACE,IAAAA,EAAM;QACT,OAAOL,aAAAA,CAAcxD,GAAG,CAAC,CAAA,EAAGf,OAAO,CAAC,EAAE2E,MAAM,CAAA,IAAK,IAAA;AACnD,IAAA;;AAGA,IAAA,IAAIA,IAAAA,KAAS,SAAA,IAAaL,YAAAA,CAAalJ,IAAI,CAACwJ,IAAAA,CAAAA,EAAO;AACjD,QAAA,IAAI5E,WAAW,QAAA,EAAU;YACvB,OAAO;gBAAEkC,IAAAA,EAAM,eAAA;gBAAiB2C,QAAAA,EAAUD;AAAK,aAAA;AACjD,QAAA;;AAEA,QAAA,IAAI5E,WAAW,KAAA,EAAO;AACpB,YAAA,MAAM8E,OAAOJ,cAAAA,CAAe9F,KAAK,CAAC,CAAA,CAAA,CAAGjJ,IAAI,CAAC,GAAA,CAAA;YAC1C,OAAO;gBACLuM,IAAAA,EAAM,oBAAA;AACN+B,gBAAAA,UAAAA,EAAY,CAAC,aAAa,EAAEW,IAAAA,CAAK,CAAC,EAAEE,IAAAA,CAAAA;AACtC,aAAA;AACF,QAAA;AACF,IAAA;IAEA,OAAO,IAAA;AACT;AAEA,6NAIA,SAASC,OAAOzE,GAAY,EAAA;AAC1B,IAAA,OAAOA,GAAAA,YAAevH,KAAAA,GAAQuH,GAAAA,CAAIpH,OAAO,GAAGvC,MAAAA,CAAO2J,GAAAA,CAAAA;AACrD;AAgBA,6CACA,eAAe0E,iBAAAA,CACbxH,GAAiB,EACjB/C,GAAoB,EAAA;AAEpB,IAAA,MAAMwK,QAAAA,GAAWlB,kBAAAA,CAAmBvG,GAAAA,CAAIwG,YAAY,EAAE,kBAAA,CAAA;IACtD,IAAI;QACF,MAAMtD,KAAAA,GAAQ,MAAMC,KAAAA,CAAMsE,QAAAA,EAAU;YAClCjF,MAAAA,EAAQ,KAAA;AACR9J,YAAAA,OAAAA,EAASsH,IAAI0H;AACf,SAAA,CAAA;QACA,IAAI,CAACxE,KAAAA,CAAMyE,EAAE,EAAE;AACb1K,YAAAA,GAAAA,CACGK,MAAM,CAAC4F,KAAAA,CAAM5F,MAAM,CAAA,CACnB2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO,CAAC,QAAQ,EAAE4H,KAAAA,CAAM5F,MAAM,CAAC,EAAE,EAAE4F,KAAAA,CAAM0E,UAAU,CAAA;AAAG,aAAA,CAAA;AAChE,YAAA;AACF,QAAA;QACA,MAAMC,QAAAA,GAAY,MAAM3E,KAAAA,CAAMD,IAAI,EAAA;QAClChG,GAAAA,CACGK,MAAM,CAAC,GAAA,CAAA,CACP2F,IAAI,CAACqC,sBAAAA,CAAuBuC,QAAAA,EAAU7H,IAAI8H,gBAAgB,CAAA,CAAA;AAC/D,IAAA,CAAA,CAAE,OAAM;AACN7K,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAAgC,SAAA,CAAA;AAChE,IAAA;AACF;AAEA,yCACA,eAAeyM,iBAAAA,CACb/H,GAAiB,EACjB/C,GAAoB,EAAA;AAEpB,IAAA,MAAMwK,QAAAA,GAAWlB,kBAAAA,CAAmBvG,GAAAA,CAAIwG,YAAY,EAAE,cAAA,CAAA;IACtD,IAAI;QACF,MAAMtD,KAAAA,GAAQ,MAAMC,KAAAA,CAAMsE,QAAAA,EAAU;YAClCjF,MAAAA,EAAQ,KAAA;AACR9J,YAAAA,OAAAA,EAASsH,IAAI0H;AACf,SAAA,CAAA;QACA,IAAI,CAACxE,KAAAA,CAAMyE,EAAE,EAAE;AACb1K,YAAAA,GAAAA,CACGK,MAAM,CAAC4F,KAAAA,CAAM5F,MAAM,CAAA,CACnB2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO,CAAC,QAAQ,EAAE4H,KAAAA,CAAM5F,MAAM,CAAC,EAAE,EAAE4F,KAAAA,CAAM0E,UAAU,CAAA;AAAG,aAAA,CAAA;AAChE,YAAA;AACF,QAAA;AACA3K,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC,MAAMC,MAAMD,IAAI,EAAA,CAAA;AACvC,IAAA,CAAA,CAAE,OAAM;AACNhG,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAA0B,SAAA,CAAA;AAC1D,IAAA;AACF;AAEA,wEACA,eAAe0M,UAAAA,CACbhI,GAAiB,EACjB/C,GAAoB,EAAA;;AAGpB,IAAA,MAAMgL,eAAe,CAAA,EAAGjI,GAAAA,CAAIwG,YAAY,CAAC,YAAY,CAAC;AACtD,IAAA,IAAI0B,aACF,EAAE;IACJ,IAAI;QACF,MAAMC,OAAAA,GAAU,MAAMhF,KAAAA,CAAM8E,YAAAA,EAAc;YACxCzF,MAAAA,EAAQ,KAAA;AACR9J,YAAAA,OAAAA,EAASsH,IAAI0H;AACf,SAAA,CAAA;QAEA,IAAI,CAACS,OAAAA,CAAQR,EAAE,EAAE;AACf1K,YAAAA,GAAAA,CACGK,MAAM,CAAC6K,OAAAA,CAAQ7K,MAAM,CAAA,CACrB2F,IAAI,CAAC;AAAE3H,gBAAAA,KAAAA,EAAO,CAAC,wBAAwB,EAAE6M,OAAAA,CAAQ7K,MAAM,CAAA;AAAG,aAAA,CAAA;AAC7D,YAAA;AACF,QAAA;QACA4K,UAAAA,GAAc,MAAMC,QAAQlF,IAAI,EAAA;AAClC,IAAA,CAAA,CAAE,OAAOH,GAAAA,EAAK;AACZ7F,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;AAAE3H,YAAAA,KAAAA,EAAO,CAAC,yBAAyB,EAAEiM,MAAAA,CAAOzE,GAAAA,CAAAA,CAAAA;AAAO,SAAA,CAAA;AACxE,QAAA;AACF,IAAA;IAEA,MAAMsF,GAAAA,GAAMC,KAAKD,GAAG,EAAA;AACpB,IAAA,MAAME,YAAAA,GAAetI,GAAAA,CAAIuI,YAAY,GAAG,EAAA,GAAK,EAAA;AAC7C,IAAA,MAAMC,UAAAA,GAAaxI,GAAAA,CAAIyI,gBAAgB,GAAG,EAAA,GAAK,EAAA;AAC/C,IAAA,MAAMC,SAAmB,EAAE;AAC3B,IAAA,MAAMC,SAAmB,EAAE;IAE3B,KAAK,MAAMC,UAAUV,UAAAA,CAAY;QAC/B,IAAI,CAACpB,aAAalJ,IAAI,CAACgL,OAAOC,EAAE,CAAA,EAAG;QACnC,MAAMC,YAAAA,GAAeF,MAAAA,CAAOG,aAAa,GACrC,IAAIV,KAAKO,MAAAA,CAAOG,aAAa,CAAA,CAAEC,OAAO,EAAA,GACtC,CAAA;QACJ,MAAMC,QAAAA,GACJH,eAAe,CAAA,GAAKV,CAAAA,GAAAA,GAAMU,YAAW,IAAK,MAAA,GAASI,QAAAA;QACrD,IAAID,QAAAA,IAAYX,YAAAA,IAAgBW,QAAAA,IAAYT,UAAAA,EAAY;QAExD,MAAMW,cAAAA,GAAiB5C,kBAAAA,CACrBvG,GAAAA,CAAIwG,YAAY,EAChB,CAAC,aAAa,EAAE9H,kBAAAA,CAAmBkK,MAAAA,CAAOC,EAAE,CAAA,CAAA,CAAG,CAAA;QAEjD,IAAI;AACF,YAAA,MAAM1F,MAAMgG,cAAAA,EAAgB;gBAC1B3G,MAAAA,EAAQ,QAAA;AACR9J,gBAAAA,OAAAA,EAASsH,IAAI0H;AACf,aAAA,CAAA;YACAgB,MAAAA,CAAO7K,IAAI,CAAC+K,MAAAA,CAAOC,EAAE,CAAA;AACrB7I,YAAAA,GAAAA,CAAIoJ,IAAI,CAAC;AACPC,gBAAAA,QAAAA,EAAUrJ,IAAIqJ,QAAQ;gBACtBC,MAAAA,EAAQ,WAAA;AACRjC,gBAAAA,QAAAA,EAAUuB,OAAOC,EAAE;gBACnBU,QAAAA,EAAU,CAAA;gBACVC,SAAAA,EAAW,IAAInB,OAAOoB,WAAW;AACnC,aAAA,CAAA;AACF,QAAA,CAAA,CAAE,OAAM;YACNd,MAAAA,CAAO9K,IAAI,CAAC+K,MAAAA,CAAOC,EAAE,CAAA;AACvB,QAAA;AACF,IAAA;AAEA5L,IAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;AAAEyF,QAAAA,MAAAA;AAAQC,QAAAA;AAAO,KAAA,CAAA;AACxC;AAEA,6EACA,eAAee,kBAAAA,CACb1J,GAAiB,EACjB/C,GAAoB,EAAA;IAEpB,IAAI,CAAC+C,GAAAA,CAAI+E,QAAQ,EAAE;AACjB9H,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAA+B,SAAA,CAAA;AAC7D,QAAA;AACF,IAAA;;;IAIA,IAAIqO,UAAAA;IACJ,IAAI;AACFA,QAAAA,UAAAA,GAAa,MAAM7E,eAAAA,CAAgB9E,GAAAA,CAAI+E,QAAQ,EAAE/E,IAAI2B,GAAG,CAAA;AAC1D,IAAA,CAAA,CAAE,OAAOmB,GAAAA,EAAK;AACZ7F,QAAAA,GAAAA,CACGK,MAAM,CAAC,GAAA,CAAA,CACP2F,IAAI,CAAC;AAAE3H,YAAAA,KAAAA,EAAO,CAAC,iCAAiC,EAAEiM,MAAAA,CAAOzE,GAAAA,CAAAA,CAAAA;AAAO,SAAA,CAAA;AACnE,QAAA;AACF,IAAA;;AAGA,IAAA,MAAM8G,OAAAA,GAAU,MAAMtD,UAAAA,CAAStG,GAAAA,CAAI1H,GAAG,CAAA;AACtC,IAAA,IAAIuR,aAAsC,EAAC;IAC3C,IAAI;AACFA,QAAAA,UAAAA,GAAa7O,IAAAA,CAAKC,KAAK,CAAC2O,OAAAA,CAAQvH,QAAQ,CAAC,MAAA,CAAA,CAAA;AAI3C,IAAA,CAAA,CAAE,OAAM;;AAER,IAAA;AAEA,IAAA,MAAMyH,UAAAA,GAAcD,UAAAA,CAAWrN,IAAI,IAAe,EAAA;;;;AAKlD,IAAA,MAAMuN,YAAAA,GAAe;AACnB,QAAA,GAAGF,UAAU;QACb1S,GAAAA,EAAK;AACH,YAAA,GAAI,UAAC0S,CAAW1S,GAAG,IAA+B,EAAE;AACpD6S,YAAAA,eAAAA,EAAiBL,WAAW/E,MAAM;AAClCqF,YAAAA,mBAAAA,EAAqBN,WAAW9E,OAAO;AACvCqF,YAAAA,SAAAA,EAAWhT,OAAAA,CAAQC,GAAG,CAAC+S,SAAS,IAAI,cAAA;AACpCC,YAAAA,aAAAA,EAAenK,IAAIwG;AACrB;AACF,KAAA;;IAGA,MAAM4D,eAAAA,GAAkB,IAAI/B,IAAAA,EAAAA,CAAOoB,WAAW,EAAA;IAC9C,MAAMF,QAAAA,GAAWvJ,IAAI8H,gBAAgB,CAACpC,WAAW,GAAGoE,WAAW,IAAI,CAAA;AACnE9J,IAAAA,GAAAA,CAAIoJ,IAAI,CAAC;AACPC,QAAAA,QAAAA,EAAUrJ,IAAIqJ,QAAQ;QACtBC,MAAAA,EAAQ,QAAA;AACRQ,QAAAA,UAAAA;AACAP,QAAAA,QAAAA;QACAC,SAAAA,EAAWY;AACb,KAAA,CAAA;;AAgBA,IAAA,MAAM3C,QAAAA,GAAWlB,kBAAAA,CAAmBvG,GAAAA,CAAIwG,YAAY,EAAE,cAAA,CAAA;IACtD,IAAI6D,SAAAA;IACJ,IAAI;QACFA,SAAAA,GAAY,MAAMlH,MAAMsE,QAAAA,EAAU;YAChCjF,MAAAA,EAAQ,MAAA;YACR9J,OAAAA,EAAS;AAAE,gBAAA,GAAGsH,IAAI0H,iBAAiB;gBAAE,cAAA,EAAgB;AAAmB,aAAA;YACxE/E,IAAAA,EAAM3H,IAAAA,CAAKI,SAAS,CAAC2O,YAAAA;AACvB,SAAA,CAAA;AACF,IAAA,CAAA,CAAE,OAAOjH,GAAAA,EAAK;AACZ7F,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;AAAE3H,YAAAA,KAAAA,EAAO,CAAC,sBAAsB,EAAEiM,MAAAA,CAAOzE,GAAAA,CAAAA,CAAAA;AAAO,SAAA,CAAA;AACrE,QAAA;AACF,IAAA;IAEA,IAAI,CAACuH,SAAAA,CAAU1C,EAAE,EAAE;AACjB1K,QAAAA,GAAAA,CAAIK,MAAM,CAAC+M,SAAAA,CAAU/M,MAAM,CAAA,CAAE2F,IAAI,CAAC;YAChC3H,KAAAA,EAAO,CAAC,sBAAsB,EAAE+O,SAAAA,CAAU/M,MAAM,CAAC,CAAC,EAAE+M,SAAAA,CAAUzC,UAAU,CAAA;AAC1E,SAAA,CAAA;AACA,QAAA;AACF,IAAA;IAEA,MAAM0C,UAAAA,GAAc,MAAMD,SAAAA,CAAUpH,IAAI,EAAA;;AAGxC,IAAA,MAAMoE,WAAWiD,UAAAA,EAAYzB,EAAAA;AAC7B,IAAA,IAAIxB,QAAAA,EAAU;AACZrH,QAAAA,GAAAA,CAAIoJ,IAAI,CAAC;AACPC,YAAAA,QAAAA,EAAUrJ,IAAIqJ,QAAQ;YACtBC,MAAAA,EAAQ,QAAA;AACRQ,YAAAA,UAAAA;AACAzC,YAAAA,QAAAA;AACAkC,YAAAA,QAAAA;YACAC,SAAAA,EAAWY;AACb,SAAA,CAAA;AACF,IAAA;AAEAnN,IAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAACqH,UAAAA,CAAAA;AACvB;AAEA,iDACA,eAAeC,kBAAAA,CACbvK,GAAiB,EACjBe,KAAsD,EACtD9D,GAAoB,EAAA;IAEpB,MAAMwK,QAAAA,GAAWlB,kBAAAA,CACfvG,GAAAA,CAAIwG,YAAY,EAChB,CAAC,aAAa,EAAE9H,kBAAAA,CAAmBqC,KAAAA,CAAMsG,QAAQ,CAAA,CAAA,CAAG,CAAA;IAEtD,IAAI;QACF,MAAMnE,KAAAA,GAAQ,MAAMC,KAAAA,CAAMsE,QAAAA,EAAU;YAClCjF,MAAAA,EAAQ,QAAA;AACR9J,YAAAA,OAAAA,EAASsH,IAAI0H;AACf,SAAA,CAAA;;AAEA,QAAA,IAAI,CAACxE,KAAAA,CAAMyE,EAAE,IAAIzE,KAAAA,CAAM5F,MAAM,KAAK,GAAA,EAAK;AACrCL,YAAAA,GAAAA,CAAIK,MAAM,CAAC4F,KAAAA,CAAM5F,MAAM,CAAA,CAAE2F,IAAI,CAAC;gBAC5B3H,KAAAA,EAAO,CAAC,yBAAyB,EAAE4H,KAAAA,CAAM5F,MAAM,CAAC,CAAC,EAAE4F,KAAAA,CAAM0E,UAAU,CAAA;AACrE,aAAA,CAAA;AACA,YAAA;AACF,QAAA;AACF,IAAA,CAAA,CAAE,OAAO9E,GAAAA,EAAK;AACZ7F,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;AAAE3H,YAAAA,KAAAA,EAAO,CAAC,yBAAyB,EAAEiM,MAAAA,CAAOzE,GAAAA,CAAAA,CAAAA;AAAO,SAAA,CAAA;AACxE,QAAA;AACF,IAAA;;AAGA9C,IAAAA,GAAAA,CAAIoJ,IAAI,CAAC;AACPC,QAAAA,QAAAA,EAAUrJ,IAAIqJ,QAAQ;QACtBC,MAAAA,EAAQ,WAAA;AACRjC,QAAAA,QAAAA,EAAUtG,MAAMsG,QAAQ;QACxBkC,QAAAA,EAAU,CAAA;QACVC,SAAAA,EAAW,IAAInB,OAAOoB,WAAW;AACnC,KAAA,CAAA;IAEAxM,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAKC,GAAG,EAAA;AACrB;AAEA,8DACA,eAAeiN,uBAAAA,CACbxK,GAAiB,EACjBe,KAA2D,EAC3D9D,GAAoB,EAAA;AAEpB,IAAA,MAAMwK,WAAWlB,kBAAAA,CAAmBvG,GAAAA,CAAIwG,YAAY,EAAEzF,MAAM0F,UAAU,CAAA;IACtE,IAAI;QACF,MAAMvD,KAAAA,GAAQ,MAAMC,KAAAA,CAAMsE,QAAAA,EAAU;YAClCjF,MAAAA,EAAQ,KAAA;AACR9J,YAAAA,OAAAA,EAASsH,IAAI0H;AACf,SAAA,CAAA;AACAzK,QAAAA,GAAAA,CAAIK,MAAM,CAAC4F,KAAAA,CAAM5F,MAAM,CAAA,CAAE2F,IAAI,CAAC,MAAMC,KAAAA,CAAMD,IAAI,GAAGS,KAAK,CAAC,KAAO,EAAC,CAAA,CAAA,CAAA;AACjE,IAAA,CAAA,CAAE,OAAM;AACNzG,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAAwB,SAAA,CAAA;AACxD,IAAA;AACF;AAEA,6NAIA,MAAMmP,kBAAAA,GAAqB;AAACC,IAAAA,uBAAAA;AAAoBC,IAAAA;AAAe,CAAA;AAE/D,MAAMC,gBAAAA,GAAmB;AAACrT,IAAAA,eAAAA;AAAiB,IAAA;AAAgC,CAAA;AAEpE,SAASsT,yBAAyB9K,MAAkC,EAAA;IACzE,MAAMqJ,IAAAA,GAAOrJ,MAAAA,CAAO+K,WAAW,IAAIxG,kBAAAA;IACnC,MAAMyG,UAAAA,GAAahL,MAAAA,CAAOgL,UAAU,KAAK,IAAA;IACzC,MAAMxC,YAAAA,GAAexI,MAAAA,CAAOwI,YAAY,IAAI,EAAA;IAC5C,MAAME,gBAAAA,GAAmB1I,MAAAA,CAAO0I,gBAAgB,IAAI,EAAA;AAEpD,IAAA,OAAO,eAAeuC,2BAAAA,CACpB1S,GAAmB,EACnB2E,GAAoB,EAAA;AAEpB,QAAA,MAAM,EAAEuJ,YAAY,EAAEzB,QAAQ,EAAE+C,gBAAgB,EAAE,GAAG/H,MAAAA;AAErD,QAAA,IAAIgF,QAAAA,IAAY,CAAC0F,kBAAAA,CAAmBnR,QAAQ,CAACyL,QAAAA,CAAAA,EAAW;AACtD9H,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAsC,aAAA,CAAA;AACpE,YAAA;AACF,QAAA;AAEA,QAAA,IAAIkL,YAAAA,IAAgB,CAACoE,gBAAAA,CAAiBtR,QAAQ,CAACkN,YAAAA,CAAAA,EAAe;AAC5DvJ,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAoC,aAAA,CAAA;AAClE,YAAA;AACF,QAAA;;AAGA,QAAA,MAAM2P,SAAAA,GAAY3S,GAAAA,CAAI8E,KAAK,CAACkM,MAAM;AAClC,QAAA,MAAMpC,cAAAA,GAA2B1O,KAAAA,CAAMC,OAAO,CAACwS,SAAAA,CAAAA,GAC3CA,SAAAA,CAAUrL,MAAM,CAAC,CAACsL,CAAAA,GAAmB,OAAOA,CAAAA,KAAM,YAClD,EAAE;AACN,QAAA,MAAMnK,KAAAA,GAAQkG,kBAAAA,CAAmB3O,GAAAA,CAAIkK,MAAM,IAAI,EAAA,EAAI0E,cAAAA,CAAAA;;;QAInD,IAAInG,KAAAA,EAAO2D,SAAS,QAAA,EAAU;YAC5BzH,GAAAA,CAAIuB,SAAS,CAAC,eAAA,EAAiB,UAAA,CAAA;AAC/BvB,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAEkI,OAAAA,EAASJ;AAAW,aAAA,CAAA;AAC3C,YAAA;AACF,QAAA;;AAGA,QAAA,IAAI,CAACA,UAAAA,EAAY;YACf9N,GAAAA,CAAIuB,SAAS,CAAC,eAAA,EAAiB,UAAA,CAAA;AAC/BvB,YAAAA,GAAAA,CACGK,MAAM,CAAC,GAAA,CAAA,CACP2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAA0C,aAAA,CAAA;AAC3D,YAAA;AACF,QAAA;AAEA,QAAA,IAAI,CAACkL,YAAAA,EAAc;AACjBvJ,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAmC,aAAA,CAAA;AACjE,YAAA;AACF,QAAA;;QAGA,MAAMqG,GAAAA,GAAM5B,OAAOqL,QAAQ,GACvBrL,OAAOqL,QAAQ,CAAC9S,OAChB4I,oBAAAA,CAAqB5I,GAAAA,CAAAA;AAEzB,QAAA,IAAI,CAACqJ,GAAAA,EAAK;AACR1E,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAA2B,aAAA,CAAA;AACzD,YAAA;AACF,QAAA;AAEA,QAAA,IAAI,CAACyF,KAAAA,EAAO;AACV9D,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAmB,aAAA,CAAA;AACjD,YAAA;AACF,QAAA;;AAGA,QAAA,MAAM+P,SAAS3J,eAAAA,CAAgBC,GAAAA,CAAAA;AAC/B,QAAA,MAAM2J,cACJD,MAAAA,EAAQE,GAAAA,IACRF,MAAAA,EAAQG,kBAAAA,IACRH,QAAQhC,QAAAA,IACR,SAAA;AACF,QAAA,MAAMA,QAAAA,GACJ,OAAOiC,WAAAA,KAAgB,QAAA,GAAWA,WAAAA,GAAc,SAAA;;AAGlD,QAAA,MAAMG,OAAAA,GAAU9J,GAAAA,CAAInI,OAAO,CAAC,SAAA,EAAW,EAAA,CAAA;AACvC,QAAA,MAAMkS,YAAAA,GAAerC,QAAAA,CAAS7P,OAAO,CAAC,SAAA,EAAW,EAAA,CAAA;AAEjD,QAAA,MAAMkO,iBAAAA,GAA4C;YAChDtC,aAAAA,EAAe,CAAC,OAAO,EAAEqG,OAAAA,CAAAA,CAAS;YAClCE,WAAAA,EAAaD;AACf,SAAA;;QAGAzO,GAAAA,CAAIuB,SAAS,CAAC,eAAA,EAAiB,UAAA,CAAA;AAE/B,QAAA,MAAMwB,GAAAA,GAAoB;AACxB1H,YAAAA,GAAAA;AACAkO,YAAAA,YAAAA;AACAzB,YAAAA,QAAAA;AACA+C,YAAAA,gBAAAA;AACAJ,YAAAA,iBAAAA;AACA/F,YAAAA,GAAAA;AACA0H,YAAAA,QAAAA;AACAD,YAAAA,IAAAA;AACAb,YAAAA,YAAAA;AACAE,YAAAA;AACF,SAAA;AAEA,QAAA,OAAQ1H,MAAM2D,IAAI;YAChB,KAAK,aAAA;AACH,gBAAA,OAAO8C,kBAAkBxH,GAAAA,EAAK/C,GAAAA,CAAAA;YAChC,KAAK,cAAA;AACH,gBAAA,OAAO8K,kBAAkB/H,GAAAA,EAAK/C,GAAAA,CAAAA;YAChC,KAAK,MAAA;AACH,gBAAA,OAAO+K,WAAWhI,GAAAA,EAAK/C,GAAAA,CAAAA;YACzB,KAAK,eAAA;AACH,gBAAA,OAAOyM,mBAAmB1J,GAAAA,EAAK/C,GAAAA,CAAAA;YACjC,KAAK,eAAA;gBACH,OAAOsN,kBAAAA,CAAmBvK,KAAKe,KAAAA,EAAO9D,GAAAA,CAAAA;YACxC,KAAK,oBAAA;gBACH,OAAOuN,uBAAAA,CAAwBxK,KAAKe,KAAAA,EAAO9D,GAAAA,CAAAA;AAC7C,YAAA;AACEA,gBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;oBAAE3H,KAAAA,EAAO;AAAqB,iBAAA,CAAA;AACvD;AACF,IAAA,CAAA;AACF;;AC3wBA,MAAMsQ,oBAAkBjQ,4BAAAA,CAA6B;;;;;IAKnD/B,cAAAA,EAAgB;AAClB,CAAA,CAAA;AAEA,MAAMiS,yBAAAA,GAA4B,mBAAA;AAClC,MAAMC,kBAAAA,GAAqB,2CAAA;AAE3B,gFACA,SAASC,UAAAA,CAAWtI,IAAY,EAAA;AAC9B,IAAA,OAAOA,KACJjK,OAAO,CAAC,MAAM,OAAA,CAAA,CACdA,OAAO,CAAC,IAAA,EAAM,MAAA,CAAA,CACdA,OAAO,CAAC,IAAA,EAAM,QACdA,OAAO,CAAC,MAAM,QAAA,CAAA,CACdA,OAAO,CAAC,IAAA,EAAM,QAAA,CAAA;AACnB;AAEA;;;;IAKA,SAASwS,YAAY/K,KAAoC,EAAA;AACvD,IAAA,IAAIzI,MAAMC,OAAO,CAACwI,QAAQ,OAAOA,KAAK,CAAC,CAAA,CAAE;IACzC,OAAOA,KAAAA;AACT;AAEA,SAAS5I,cAAcC,GAAmB,EAAA;AAIxC,IAAA,MAAMC,cAAAA,GAAiByT,WAAAA,CAAY1T,GAAAA,CAAII,OAAO,CAAC,mBAAA,CAAoB,CAAA;AACnE,IAAA,MAAMC,aAAAA,GAAgBqT,WAAAA,CAAY1T,GAAAA,CAAII,OAAO,CAAC,kBAAA,CAAmB,CAAA;;;AAGjE,IAAA,MAAME,UAAAA,GAAaoT,WAAAA,CAAY1T,GAAAA,CAAII,OAAO,CAACG,IAAI,CAAA;AAC/C,IAAA,MAAMC,aAAAA,GAAgBkT,WAAAA,CAAY1T,GAAAA,CAAII,OAAO,CAACK,OAAO,CAAA;AAErD,IAAA,IAAIU,QAAQ,CAAClB,cAAAA,IAAkB,EAAC,EAAGU,IAAI,EAAA;AACvC,IAAA,IAAIJ,OAAO,CAACF,iBAAiBC,UAAAA,IAAc,EAAC,EAAGK,IAAI,EAAA;AAEnD,IAAA,IAAIH,aAAAA,EAAe;QACjB,IAAI;YACF,MAAMM,UAAAA,GAAa,IAAIC,GAAAA,CAAIP,aAAAA,CAAAA;;AAE3B,YAAA,IAAI,CAACD,IAAAA,IAAQ,CAACA,IAAAA,CAAKS,QAAQ,CAAC,GAAA,CAAA,EAAM;AAChCT,gBAAAA,IAAAA,GAAOO,WAAWP,IAAI;AACxB,YAAA;;AAEA,YAAA,IAAI,CAACY,KAAAA,EAAO;AACVA,gBAAAA,KAAAA,GAAQL,UAAAA,CAAWG,QAAQ,CAACC,OAAO,CAAC,GAAA,EAAK,EAAA,CAAA;AAC3C,YAAA;AACF,QAAA,CAAA,CAAE,OAAM;;AAER,QAAA;AACF,IAAA;IAEA,OAAO;AACLC,QAAAA,KAAAA,EAAOA,KAAAA,IAAS,MAAA;AAChBZ,QAAAA,IAAAA,EAAMA,IAAAA,IAAQ;AAChB,KAAA;AACF;AAEA,SAASoT,oBAAAA,CAAqBtS,IAAY,EAAErB,GAAmB,EAAA;IAC7D,MAAM4T,mBAAAA,GACJ,CAAC1T,KAAAA,CAAMC,OAAO,CAACH,GAAAA,CAAI8E,KAAK,CAACN,IAAI,CAAA,GAAIxE,IAAI8E,KAAK,CAACN,IAAI,CAAC,CAAA,CAAE,GAAGxE,IAAI8E,KAAK,CAACN,IAAG,MAClE,QAAA;;IAGF,MAAMqP,qBAAAA,GAAwBD,mBAAAA,GACzB,CAAA,IAAA;AACC,QAAA,MAAM,EAAEzS,KAAK,EAAEZ,IAAI,EAAE,GAAGR,aAAAA,CAAcC,GAAAA,CAAAA;QACtC,OAAO;AAAEoO,YAAAA,IAAAA,EAAM,GAAGjN,KAAAA,CAAM,GAAG,EAAEZ,IAAAA,CAAK,oBAAoB,CAAC;AAAEY,YAAAA,KAAAA;AAAOZ,YAAAA;AAAK,SAAA;AACvE,IAAA,CAAA,GAAA,GACA,IAAA;IAEJ,MAAMuT,UAAAA,GAAazS,KAAKH,OAAO,CAC7B,oEACA,CAACmB,MAAAA,EAAQC,SAAiByR,UAAAA,EAAoBvR,QAAAA,GAAAA;;QAE5C,MAAMwR,OAAAA,GAAUD,WAAWpT,IAAI,EAAA;;QAE/B,IAAI,CAACqT,QAAQrU,UAAU,CAAC,QAAQ,CAACqU,OAAAA,CAAQC,QAAQ,CAAC,GAAA,CAAA,EAAM;AACtD/Q,YAAAA,OAAAA,CAAQF,KAAK,CACX,qFAAA,CAAA;YAEF,OAAOX,MAAAA;AACT,QAAA;AAEA,QAAA,IAAII,WAAoC,EAAC;QACzC,IAAI;YACFA,QAAAA,GAAWC,IAAAA,CAAKC,KAAK,CAACqR,OAAAA,CAAAA;AACxB,QAAA,CAAA,CAAE,OAAOxJ,GAAAA,EAAK;YACZtH,OAAAA,CAAQF,KAAK,CACX,6EAAA,EACAwH,GAAAA,CAAAA;YAEF,OAAOnI,MAAAA;AACT,QAAA;QAEA,MAAM6R,gBAAAA,GAAmBhU,KAAAA,CAAMC,OAAO,CAACsC,QAAAA,CAASlB,kBAAkB,CAAA,GAC7DkB,QAAAA,CAASlB,kBAAkB,GAC5B,EAAE;AACN,QAAA,MAAM4S,2BAA2BP,mBAAAA,GAC7B;AAAIM,YAAAA,GAAAA,gBAAAA;AAAkB,YAAA;SAA+C,GACrEA,gBAAAA;AAEJ,QAAA,MAAMtR,MAAAA,GAAkC;AACtC,YAAA,GAAGH,QAAQ;YACXhB,OAAAA,EAAS2S,sBAAAA;YACT1S,UAAAA,EAAY8R,kBAAAA;YACZ,GAAIW,wBAAAA,CAAyB7K,MAAM,GAAG,CAAA,GAClC;AACE/H,gBAAAA,kBAAAA,EAAoBrB,KAAAA,CAAM4J,IAAI,CAAC,IAAI1K,GAAAA,CAAI+U,wBAAAA,CAAAA;AACzC,aAAA,GACA,EAAE;AACN,YAAA,GAAIP,uBAAuBC,qBAAAA,GACvB;;;AAGE5R,gBAAAA,aAAAA,EAAe4R,sBAAsBzF,IAAI;;;;;gBAKzCiG,oBAAAA,EAAsB,CAAA,EAAGR,qBAAAA,CAAsB1S,KAAK,CAAC,GAAG,EAAE0S,qBAAAA,CAAsBtT,IAAI,CAAC,6BAA6B,CAAC;gBACnH4B,aAAAA,EACE;AACJ,aAAA,GACA;AACN,SAAA;AACA,QAAA,OAAO,GAAGG,OAAAA,CAAAA,EAAUI,IAAAA,CAAKI,SAAS,CAACF,UAAUJ,QAAAA,CAAAA,CAAU;AACzD,IAAA,CAAA,CAAA;;IAIF,OAAOsR,UAAAA,CAAW5S,OAAO,CACvB,uBAAA,EACA,CAAC,OAAO,EAAEuS,UAAAA,CAAWF,yBAAAA,CAAAA,CAA2B,QAAQ,CAAC,CAAA;AAE7D;AAEA,SAAS9M,eAAe9B,GAAoB,EAAA;IAC1C,MAAMqB,WAAAA,GAAcrB,GAAAA,CAAI2P,SAAS,CAAC,cAAA,CAAA;AAClC,IAAA,IAAI,OAAOtO,WAAAA,KAAgB,QAAA,EAAU,OAAOA,WAAAA,CAAYhF,QAAQ,CAAC,WAAA,CAAA;AACjE,IAAA,IAAId,KAAAA,CAAMC,OAAO,CAAC6F,WAAAA,CAAAA,EAChB,OAAOA,WAAAA,CAAYuO,IAAI,CAAC,CAACC,CAAAA,GAAMA,CAAAA,CAAExT,QAAQ,CAAC,WAAA,CAAA,CAAA;IAC5C,OAAO,KAAA;AACT;AAEe,SAAS0D,SAAAA,CAAQ1E,GAAmB,EAAE2E,GAAoB,EAAA;AACvE,IAAA,MAAM8P,YAAAA,GAAe9P,GAAAA,CAAI6B,IAAI,CAACkO,IAAI,CAAC/P,GAAAA,CAAAA;IAEnCA,GAAAA,CAAI6B,IAAI,GAAI,CAAC6D,IAAAA,GAAAA;AACX,QAAA,IACE,OAAOA,IAAAA,KAAS,QAAA,IAChB5D,cAAAA,CAAe9B,GAAAA,CAAAA,IACf0F,IAAAA,CAAKrJ,QAAQ,CAAC,0BAAA,CAAA,IACdqJ,IAAAA,CAAKrJ,QAAQ,CAAC,SAAA,CAAA,EACd;YACA,OAAOyT,YAAAA,CAAad,qBAAqBtJ,IAAAA,EAAMrK,GAAAA,CAAAA,CAAAA;AACjD,QAAA;AACA,QAAA,OAAOyU,YAAAA,CAAapK,IAAAA,CAAAA;AACtB,IAAA,CAAA;AAEA,IAAA,OAAOiJ,kBAAgBtT,GAAAA,EAAK2E,GAAAA,CAAAA;AAC9B;;AC3KA;AACA,MAAMgQ,gBAAAA,GAAmB;AAAC,IAAA,cAAA;AAAgB,IAAA,eAAA;AAAiB,IAAA;AAAmB,CAAA;AAE9E,SAASC,kBAAkB1P,QAAkB,EAAA;AAC3C,IAAA,MAAM2P,KAAAA,GAAQ3P,QAAAA,CACXoC,MAAM,CAACwN,OAAAA,CAAAA,CACPtM,GAAG,CAAC,CAACoK,CAAAA,GAAMA,CAAAA,CAAE1R,OAAO,CAAC,YAAA,EAAc,EAAA,CAAA,CAAA;IAEtC,IAAI2T,KAAAA,CAAMN,IAAI,CAAC,CAAC3B,IAAMA,CAAAA,KAAM,IAAA,IAAQA,MAAM,GAAA,CAAA,EAAM;AAC9C,QAAA,MAAM,IAAI3P,KAAAA,CAAM,sBAAA,CAAA;AAClB,IAAA;AAEA,IAAA,OAAO,CAAC,CAAC,EAAE4R,KAAAA,CAAMhV,IAAI,CAAC,GAAA,CAAA,CAAA,CAAM;AAC9B;AAEA,SAASkV,cAAcnQ,IAAY,EAAA;AACjC,IAAA,OAAO+P,gBAAAA,CAAiBJ,IAAI,CAC1B,CAACS,MAAAA,GAAWpQ,IAAAA,KAASoQ,MAAAA,IAAUpQ,IAAAA,CAAKjF,UAAU,CAAC,CAAA,EAAGqV,MAAAA,CAAO,CAAC,CAAC,CAAA,CAAA;AAE/D;AAEA,SAASC,gBAAAA,CACPC,MAA0B,EAC1BC,UAAkB,EAAA;IAElB,IAAI,CAACD,QAAQ,OAAO,EAAA;AACpB,IAAA,MAAME,YAAYF,MAAAA,CAAO1L,KAAK,CAAC,GAAA,CAAI,CAAC,CAAA,CAAE;IACtC,IAAI,CAAC4L,WAAW,OAAO,EAAA;IAEvB,MAAMC,MAAAA,GAAS,IAAIC,eAAAA,CAAgBF,SAAAA,CAAAA;AACnCC,IAAAA,MAAAA,CAAOE,MAAM,CAACJ,UAAAA,CAAAA;IAEd,MAAM/S,MAAAA,GAASiT,OAAOtL,QAAQ,EAAA;AAC9B,IAAA,OAAO3H,MAAAA,GAAS,CAAC,CAAC,EAAEA,QAAQ,GAAG,EAAA;AACjC;AAEA,SAAS4L,SAAShO,GAAmB,EAAA;IACnC,OAAO,IAAIuL,OAAAA,CAAQ,CAAC9G,OAAAA,EAAS+G,MAAAA,GAAAA;QAC3B,IAAI,CAACxL,GAAAA,CAAIkK,MAAM,IAAI;AAAC,YAAA,KAAA;AAAO,YAAA;AAAO,SAAA,CAAClJ,QAAQ,CAAChB,GAAAA,CAAIkK,MAAM,CAACsL,WAAW,EAAA,CAAA,EAAK;YACrE/Q,OAAAA,CAAQ5C,SAAAA,CAAAA;AACR,YAAA;AACF,QAAA;AACA,QAAA,MAAM4J,SAAmB,EAAE;QAC3BzL,GAAAA,CAAI+G,EAAE,CAAC,MAAA,EAAQ,CAAC4E,KAAAA,GAAAA;YACdF,MAAAA,CAAOlG,IAAI,CAACsE,MAAAA,CAAO4L,QAAQ,CAAC9J,KAAAA,CAAAA,GAASA,KAAAA,GAAQ9B,MAAAA,CAAOC,IAAI,CAAC6B,KAAAA,CAAAA,CAAAA;AAC3D,QAAA,CAAA,CAAA;QACA3L,GAAAA,CAAI+G,EAAE,CAAC,KAAA,EAAO,IACZtC,OAAAA,CAAQgH,MAAAA,CAAOnC,MAAM,GAAGO,MAAAA,CAAOkC,MAAM,CAACN,MAAAA,CAAAA,GAAU5J,SAAAA,CAAAA,CAAAA;QAElD7B,GAAAA,CAAI+G,EAAE,CAAC,OAAA,EAASyE,MAAAA,CAAAA;AAClB,IAAA,CAAA,CAAA;AACF;AAEe,eAAe9G,SAAAA,CAC5B1E,GAAmB,EACnB2E,GAAoB,EAAA;AAEpB,IAAA,MAAM+Q,UAAAA,GAAa9W,OAAAA,CAAQC,GAAG,CAAC8W,mBAAmB;AAElD,IAAA,IAAI,CAACD,UAAAA,EAAY;AACf/Q,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAAwC,SAAA,CAAA;AACtE,QAAA;AACF,IAAA;AAEA,IAAA,MAAM4S,WAAAA,GAAcF,UAAAA,CAAWxU,OAAO,CAAC,MAAA,EAAQ,EAAA,CAAA;AAE/C,IAAA,MAAM0N,iBAAiB1O,KAAAA,CAAMC,OAAO,CAACH,GAAAA,CAAI8E,KAAK,CAACkM,MAAM,CAAA,GACjDhR,GAAAA,CAAI8E,KAAK,CAACkM,MAAM,GAChBhR,IAAI8E,KAAK,CAACkM,MAAM,GACd;QAAChR,GAAAA,CAAI8E,KAAK,CAACkM;AAAO,KAAA,GAClB,EAAE;IAER,IAAI6E,YAAAA;IACJ,IAAI;AACFA,QAAAA,YAAAA,GAAejB,iBAAAA,CAAkBhG,cAAAA,CAAAA;AACnC,IAAA,CAAA,CAAE,OAAM;AACNjK,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAAe,SAAA,CAAA;AAC7C,QAAA;AACF,IAAA;IAEA,IAAI,CAAC+R,cAAcc,YAAAA,CAAAA,EAAe;AAChClR,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAAiB,SAAA,CAAA;AAC/C,QAAA;AACF,IAAA;AAEA,IAAA,MAAM8S,WAAAA,GAAcb,gBAAAA,CAAiBjV,GAAAA,CAAI+V,GAAG,EAAE,QAAA,CAAA;AAC9C,IAAA,MAAM9L,SAAAA,GAAY,CAAA,EAAG2L,WAAAA,CAAAA,EAAcC,YAAAA,CAAAA,EAAeC,WAAAA,CAAAA,CAAa;AAE/D,IAAA,MAAME,iBAAiB,IAAIC,OAAAA,EAAAA;IAC3B,KAAK,MAAM,CAACvN,GAAAA,EAAKC,KAAAA,CAAM,IAAIkD,OAAOqK,OAAO,CAAClW,GAAAA,CAAII,OAAO,CAAA,CAAG;AACtD,QAAA,IAAI,CAACuI,KAAAA,EAAO;QACZ,MAAMwN,KAAAA,GAAQzN,IAAI3C,WAAW,EAAA;AAC7B,QAAA,IACEoQ,KAAAA,KAAU,MAAA,IACVA,KAAAA,KAAU,gBAAA,IACVA,UAAU,mBAAA,EAEV;QACFH,cAAAA,CAAepS,GAAG,CAAC8E,GAAAA,EAAKxI,KAAAA,CAAMC,OAAO,CAACwI,KAAAA,CAAAA,GAASA,KAAAA,CAAM9I,IAAI,CAAC,GAAA,CAAA,GAAO8I,KAAAA,CAAAA;AACnE,IAAA;;;AAIA,IAAA,IAAI/J,OAAAA,CAAQC,GAAG,CAACiD,QAAQ,KAAK,aAAA,EAAe;;;AAG1C,QAAA,MAAMF,cAAcG,qBAAAA,CAAU,mBAAA,CAAA;AAC9B,QAAA,IAAIH,WAAAA,EAAa;AACfoU,YAAAA,cAAAA,CAAepS,GAAG,CAAC,eAAA,EAAiB,CAAC,OAAO,EAAEhC,WAAAA,CAAAA,CAAa,CAAA;AAC7D,QAAA;AACF,IAAA;IAEA,IAAIyI,IAAAA;IACJ,IAAI;AACFA,QAAAA,IAAAA,GAAO,MAAM2D,QAAAA,CAAShO,GAAAA,CAAAA;AACxB,IAAA,CAAA,CAAE,OAAM;AACN2E,QAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;YAAE3H,KAAAA,EAAO;AAA8B,SAAA,CAAA;AAC5D,QAAA;AACF,IAAA;AAEA,IAAA,IAAIqH,IAAAA,EAAM;AACR2L,QAAAA,cAAAA,CAAepS,GAAG,CAAC,gBAAA,EAAkB/C,MAAAA,CAAOwJ,KAAK+L,UAAU,CAAA,CAAA;AAC7D,IAAA;IAEA,IAAIjH,QAAAA;IACJ,IAAI;QACFA,QAAAA,GAAW,MAAMtE,MAAMZ,SAAAA,EAAW;AAChCC,YAAAA,MAAAA,EAAQlK,IAAIkK,MAAM;YAClB9J,OAAAA,EAAS4V,cAAAA;YACT3L,IAAAA,EAAMA,IAAAA,GAAO,IAAIgM,UAAAA,CAAWhM,IAAAA,CAAAA,GAAQxI,SAAAA;YACpCiJ,MAAAA,EAAQC,WAAAA,CAAYC,OAAO,CAAC,MAAA;AAC9B,SAAA,CAAA;AACF,IAAA,CAAA,CAAE,OAAOR,GAAAA,EAAK;AACZ,QAAA,MAAM8L,SAAAA,GAAY9L,GAAAA,YAAevH,KAAAA,IAASuH,GAAAA,CAAItG,IAAI,KAAK,cAAA;AACvDS,QAAAA,GAAAA,CAAIK,MAAM,CAACsR,SAAAA,GAAY,GAAA,GAAM,GAAA,CAAA,CAAK3L,IAAI,CAAC;AACrC3H,YAAAA,KAAAA,EAAOsT,YAAY,iBAAA,GAAoB;AACzC,SAAA,CAAA;AACA,QAAA;AACF,IAAA;IAEA3R,GAAAA,CAAIK,MAAM,CAACmK,QAAAA,CAASnK,MAAM,CAAA;AAC1BmK,IAAAA,QAAAA,CAAS/O,OAAO,CAACmW,OAAO,CAAC,CAAC5N,KAAAA,EAAOD,GAAAA,GAAAA;QAC/B,MAAMyN,KAAAA,GAAQzN,IAAI3C,WAAW,EAAA;AAC7B,QAAA,IACEoQ,KAAAA,KAAU,mBAAA,IACVA,KAAAA,KAAU,cAAA,IACVA,UAAU,yBAAA,EAEV;QACFxR,GAAAA,CAAIuB,SAAS,CAACwC,GAAAA,EAAKC,KAAAA,CAAAA;AACrB,IAAA,CAAA,CAAA;AAEA,IAAA,MAAM6N,sBAAsBrH,QAAAA,CAAS/O,OAAO,CAAC6K,GAAG,CAAC,cAAA,CAAA,IAAmB,EAAA;AACpE,IAAA,MAAMwL,kBAAkB,eAAA,CAAgBnR,IAAI,CAACkR,mBAAAA,CAAAA,GACzC,8BACAA,mBAAAA,IAAuB,0BAAA;IAC3B7R,GAAAA,CAAIuB,SAAS,CAAC,cAAA,EAAgBuQ,eAAAA,CAAAA;IAC9B9R,GAAAA,CAAIuB,SAAS,CAAC,wBAAA,EAA0B,SAAA,CAAA;IACxCvB,GAAAA,CAAIuB,SAAS,CAAC,yBAAA,EAA2B,6BAAA,CAAA;IACzCvB,GAAAA,CAAIuB,SAAS,CAAC,qBAAA,EAAuB,YAAA,CAAA;IAErC,IAAIiJ,QAAAA,CAAS9E,IAAI,EAAE;AACjB,QAAA,MAAMqM,MAAAA,GAASvH,QAAAA,CAAS9E,IAAI,CAACsM,SAAS,EAAA;QACtC,IAAI;AACF,YAAA,MAAO,IAAA,CAAM;gBACX,MAAM,EAAEC,IAAI,EAAEjO,KAAK,EAAE,GAAG,MAAM+N,OAAOG,IAAI,EAAA;AACzC,gBAAA,IAAID,IAAAA,EAAM;AACVjS,gBAAAA,GAAAA,CAAIwH,KAAK,CAACxD,KAAAA,CAAAA;AACZ,YAAA;QACF,CAAA,QAAU;AACR+N,YAAAA,MAAAA,CAAOI,WAAW,EAAA;AACpB,QAAA;AACAnS,QAAAA,GAAAA,CAAIM,GAAG,EAAA;IACT,CAAA,MAAO;AACLN,QAAAA,GAAAA,CAAIM,GAAG,EAAA;AACT,IAAA;AACF;;ACnLA;AACA;AACA;AACA;AAQA,MAAM8R,SAAAA,GAAYjC,OAAAA,CAAQlW,OAAAA,CAAQC,GAAG,CAACmY,uBAAuB,CAAA;AAC7D,MAAMC,mBAAAA,GAAsBF,YACxB9X,eAAAA,GACA,+BAAA;AACJ,MAAMiY,eAAAA,GAAkBH,YAAY3E,uBAAAA,GAAqBC,qBAAAA;AAEzD,MAAMnE,YAAAA,GAAetP,OAAAA,CAAQC,GAAG,CAACI,eAAe,IAAIgY,mBAAAA;AACpD,MAAMxK,QAAAA,GAAWyK,eAAAA;AAEjB,IAAI,CAAChJ,YAAAA,EAAc;AACjBhL,IAAAA,OAAAA,CAAQiU,IAAI,CACV,0GAAA,CAAA;AAEJ;AACA,IAAI,CAAC1K,QAAAA,EAAU;AACbvJ,IAAAA,OAAAA,CAAQiU,IAAI,CACV,4GAAA,CAAA;AAEJ;AAEA,IAAIjK,SAAkC,EAAC;AACvC,IAAItO,OAAAA,CAAQC,GAAG,CAACuY,kBAAkB,EAAE;IAClC,IAAI;AACFlK,QAAAA,MAAAA,GAASxK,KAAKC,KAAK,CAAC/D,OAAAA,CAAQC,GAAG,CAACuY,kBAAkB,CAAA;AACpD,IAAA,CAAA,CAAE,OAAO5M,GAAAA,EAAK;QACZ,MAAM,IAAIvH,MACR,CAAC,yDAAyD,EAAE,GAACuH,CAAcpH,OAAO,CAAA,CAAE,CAAA;AAExF,IAAA;AACF;AAEA,MAAMkQ,oBAAkBf,wBAAAA,CAAyB;AAC/CrE,IAAAA,YAAAA;AACAzB,IAAAA,QAAAA;IACA+C,gBAAAA,EAAkBtC,MAAAA;AAClBuF,IAAAA,UAAAA,EAAY7T,OAAAA,CAAQC,GAAG,CAACwY,UAAU,KAAK,MAAA;AACvCvE,IAAAA,QAAAA,EAAU,CAAC9S,GAAAA,GAAAA;AACT,QAAA,MAAMsX,QAAQC,uBAAAA,CAAevX,GAAAA,CAAII,OAAO,CAAC,QAAA,CAAS,IAAI,EAAA,CAAA,IAAO,IAAA;AAC7D,QAAA,IAAI,CAACkX,KAAAA,EAAO;AACVpU,YAAAA,OAAAA,CAAQiU,IAAI,CACV,6DAAA,CAAA;AAEJ,QAAA;QACA,OAAOG,KAAAA;AACT,IAAA;AACF,CAAA,CAAA;AAEe,eAAe5S,SAAAA,CAC5B1E,GAAmB,EACnB2E,GAAoB,EAAA;AAEpB,IAAA,MAAMqM,MAAAA,GAAS9Q,KAAAA,CAAMC,OAAO,CAACH,IAAI8E,KAAK,CAACkM,MAAM,CAAA,GAAIhR,GAAAA,CAAI8E,KAAK,CAACkM,MAAM,GAAG,EAAE;IACjDA,MAAM,CAAC,CAAA,CAAE,KAAK,KAAA,IAASA,MAAM,CAAC,CAAA,CAAE,KAAK;IAC1D,IAAI;AACF,QAAA,MAAMsC,kBAAgBtT,GAAAA,EAAK2E,GAAAA,CAAAA;AAC7B,IAAA,CAAA,CAAE,OAAO6F,GAAAA,EAAK;QACZtH,OAAAA,CAAQF,KAAK,CAAC,4CAAA,EAA8CwH,GAAAA,CAAAA;QAC5D,IAAI,CAAC7F,GAAAA,CAAI6S,WAAW,EAAE;AACpB7S,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAc,aAAA,CAAA;AAC9C,QAAA;AACA,QAAA;AACF,IAAA;AACF;;ACtBA,MAAMyU,UAAAA,GAAa,+CAAA;AAEnB,SAASC,oBAAAA,CACPxN,MAAc,EACd0E,cAAwB,EAAA;AAExB,IAAA,MAAMoC,MAAAA,GAASpC,cAAc,CAAC,CAAA,CAAE,IAAI,EAAA;AACpC,IAAA,MAAM+I,MAAAA,GAAwC;QAC5C,aAAA,EAAe;YAAEzN,MAAAA,EAAQ,KAAA;YAAOtF,IAAAA,EAAM;AAAW,SAAA;QACjD,YAAA,EAAc;YAAEsF,MAAAA,EAAQ,KAAA;YAAOtF,IAAAA,EAAM;AAAU,SAAA;QAC/C,aAAA,EAAe;YAAEsF,MAAAA,EAAQ,MAAA;YAAQtF,IAAAA,EAAM;AAAU,SAAA;QACjD,gBAAA,EAAkB;YAAEsF,MAAAA,EAAQ,MAAA;YAAQtF,IAAAA,EAAM;AAAa;AACzD,KAAA;IACA,OAAO+S,MAAM,CAAC,CAAA,EAAGzN,MAAAA,CAAO,CAAC,EAAE8G,MAAAA,CAAAA,CAAQ,CAAC,IAAI,IAAA;AAC1C;AAEA,MAAM4G,qBAAAA,GAAwB;AAC5B,IAAA,eAAA;AACA,IAAA;AACD,CAAA;AAEM,SAASC,2BAA2BpQ,MAA2B,EAAA;AACpE,IAAA,OAAO,eAAeqQ,oBAAAA,CACpB9X,GAAmB,EACnB2E,GAAoB,EAAA;QAEpB,MAAMoT,WAAAA,GAActQ,OAAOsQ,WAAW;AAStC,QAAA,IAAI,CAACH,qBAAAA,CAAsB5W,QAAQ,CAAC+W,WAAAA,CAAAA,EAAc;AAChDpT,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAyC,aAAA,CAAA;AACvE,YAAA;AACF,QAAA;QAEA,IAAIgV,iBAAAA;QACJ,IAAI;AACFA,YAAAA,iBAAAA,GAAoB,IAAIjX,GAAAA,CAAIgX,WAAAA,CAAAA;AAC9B,QAAA,CAAA,CAAE,OAAM;AACNpT,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAyC,aAAA,CAAA;AACvE,YAAA;AACF,QAAA;AACA,QAAA,IACEgV,kBAAkB/W,QAAQ,KAAK,WAC/B+W,iBAAAA,CAAkB/W,QAAQ,KAAK,QAAA,EAC/B;AACA0D,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAyC,aAAA,CAAA;AACvE,YAAA;AACF,QAAA;;QAGA,MAAMqG,GAAAA,GAAM5B,OAAOqL,QAAQ,GACvBrL,OAAOqL,QAAQ,CAAC9S,OAChB4I,oBAAAA,CAAqB5I,GAAAA,CAAAA;AACzB,QAAA,IAAI,CAACqJ,GAAAA,EAAK;AACR1E,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAA2B,aAAA,CAAA;AACzD,YAAA;AACF,QAAA;;;AAIA,QAAA,MAAMiV,aAAAA,GAAgB,kDAAA;AACtB,QAAA,IAAI,CAACA,aAAAA,CAAc3S,IAAI,CAAC+D,GAAAA,CAAAA,EAAM;AAC5BnG,YAAAA,OAAAA,CAAQF,KAAK,CAAC,6CAAA,CAAA;AACd2B,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAuC,aAAA,CAAA;AACrE,YAAA;AACF,QAAA;;QAGA,IAAIqG,GAAAA,CAAIC,MAAM,GAAG,IAAA,EAAM;AACrBpG,YAAAA,OAAAA,CAAQF,KAAK,CAAC,4CAAA,CAAA;AACd2B,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAiC,aAAA,CAAA;AAC/D,YAAA;AACF,QAAA;;AAGA,QAAA,MAAM+P,SAAS3J,eAAAA,CAAgBC,GAAAA,CAAAA;AAC/B,QAAA,MAAM2J,WAAAA,GACJD,MAAAA,EAAQE,GAAAA,IAAOF,MAAAA,EAAQG,sBAAsBH,MAAAA,EAAQhC,QAAAA;AACvD,QAAA,MAAMA,QAAAA,GACJ,OAAOiC,WAAAA,KAAgB,QAAA,GAAWA,WAAAA,GAAcnR,SAAAA;AAClD,QAAA,IAAI,CAACkP,QAAAA,EAAU;AACbpM,YAAAA,GAAAA,CACGK,MAAM,CAAC,GAAA,CAAA,CACP2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAA2C,aAAA,CAAA;AAC5D,YAAA;AACF,QAAA;;AAEA,QAAA,MAAMmQ,OAAAA,GAAU9J,GAAAA,CAAInI,OAAO,CAAC,SAAA,EAAW,EAAA,CAAA;AACvC,QAAA,MAAMkS,YAAAA,GAAerC,QAAAA,CAAS7P,OAAO,CAAC,SAAA,EAAW,EAAA,CAAA;;AAGjD,QAAA,MAAM0N,iBAAiB,GAAC5O,CAAI8E,KAAK,CAACkM,MAAM,IAAiB,EAAE;AAC3D,QAAA,MAAMvI,KAAAA,GAAQiP,oBAAAA,CAAqB1X,GAAAA,CAAIkK,MAAM,IAAI,EAAA,EAAI0E,cAAAA,CAAAA;AACrD,QAAA,IAAI,CAACnG,KAAAA,EAAO;AACV9D,YAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;gBAAE3H,KAAAA,EAAO;AAAmB,aAAA,CAAA;AACjD,YAAA;AACF,QAAA;;AAGA,QAAA,IAAI8S,WAAAA,GAAc,EAAA;AAClB,QAAA,IAAIrN,MAAM7D,IAAI,KAAK,aAAa6D,KAAAA,CAAM7D,IAAI,KAAK,YAAA,EAAc;AAC3D,YAAA,MAAM2L,KAAK,GAACvQ,CAAI8E,KAAK,CAACyL,EAAE,IAAe,EAAA;AACvC,YAAA,IAAIA,EAAAA,EAAI;AACN,gBAAA,IAAI,CAACkH,UAAAA,CAAWnS,IAAI,CAACiL,EAAAA,CAAAA,EAAK;AACxB5L,oBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;wBAAE3H,KAAAA,EAAO;AAAgC,qBAAA,CAAA;AAC9D,oBAAA;AACF,gBAAA;AACA8S,gBAAAA,WAAAA,GAAc,CAAC,IAAI,EAAE1P,kBAAAA,CAAmBmK,EAAAA,CAAAA,CAAAA,CAAK;AAC/C,YAAA;QACF,CAAA,MAAO,IAAI9H,MAAM7D,IAAI,KAAK,aAAa6D,KAAAA,CAAM7D,IAAI,KAAK,UAAA,EAAY;;AAEhE,YAAA,MAAM2L,KAAK,GAACvQ,CAAI8E,KAAK,CAACyL,EAAE,IAAe,EAAA;AACvC,YAAA,IAAIA,EAAAA,EAAI;AACN,gBAAA,IAAI,CAACkH,UAAAA,CAAWnS,IAAI,CAACiL,EAAAA,CAAAA,EAAK;AACxB5L,oBAAAA,GAAAA,CAAIK,MAAM,CAAC,GAAA,CAAA,CAAK2F,IAAI,CAAC;wBAAE3H,KAAAA,EAAO;AAAgC,qBAAA,CAAA;AAC9D,oBAAA;AACF,gBAAA;AACA8S,gBAAAA,WAAAA,GAAc,CAAC,IAAI,EAAE1P,kBAAAA,CAAmBmK,EAAAA,CAAAA,CAAAA,CAAK;AAC/C,YAAA;AACF,QAAA;QAEA,MAAM2H,YAAAA,GAAe,CAAA,EAAGF,iBAAAA,CAAkB1J,MAAM,CAAA,EAAG0J,iBAAAA,CAAkBzJ,QAAQ,CAACrN,OAAO,CAAC,KAAA,EAAO,EAAA,CAAA,CAAA,CAAK;AAClG,QAAA,MAAM+I,YAAY,CAAA,EAAGiO,YAAAA,CAAAA,EAAezP,KAAAA,CAAM7D,IAAI,GAAGkR,WAAAA,CAAAA,CAAa;AAE9D,QAAA,MAAM9L,kBAAAA,CAAmB;AACvBhK,YAAAA,GAAAA;AACA2E,YAAAA,GAAAA;AACAsF,YAAAA,SAAAA;AACAC,YAAAA,MAAAA,EAAQzB,MAAMyB,MAAM;YACpBC,YAAAA,EAAc;gBACZ2C,aAAAA,EAAe,CAAC,OAAO,EAAEqG,OAAAA,CAAAA,CAAS;gBAClCE,WAAAA,EAAaD,YAAAA;gBACb+E,WAAAA,EAAa/E;AACf,aAAA;;YAEAhJ,WAAAA,EAAa3B,KAAAA,CAAMyB,MAAM,KAAK;AAChC,SAAA,CAAA;AACF,IAAA,CAAA;AACF;;ACnMA;AACA;AACA;AAKA,MAAMkO,qBAAqBxZ,OAAAA,CAAQC,GAAG,CAACmY,uBAAuB,GAC1D,gDAAA,GACA,eAAA;AAEJ,MAAM1D,kBAAkBuE,0BAAAA,CAA2B;IACjDE,WAAAA,EAAaK,kBAAAA;IACbtF,QAAAA,EAAU,CAAC9S,MAAQuX,uBAAAA,CAAevX,GAAAA,CAAII,OAAO,CAAC,QAAA,CAAS,IAAI,EAAA,CAAA,IAAO;AACpE,CAAA,CAAA;AAiBe,eAAesE,OAAAA,CAC5B1E,GAAmB,EACnB2E,GAAoB,EAAA;AAEpB,IAAe3E,GAAAA,CAAI8E,KAAK,CAACkM,MAAM,GAAG,CAAA;AAIlC,IAAA,MAAMyD,YAAAA,GAAe9P,GAAAA,CAAI6B,IAAI,CAACkO,IAAI,CAAC/P,GAAAA,CAAAA;IACnCA,GAAAA,CAAI6B,IAAI,GAAG,CAAC6D,IAAAA,GAAAA;AACVgO,QAAe,CACb,OAAOhO,IAAAA,KAAS,QAAA,GAAWA,IAAAA,GAAO3H,IAAAA,CAAKI,SAAS,CAACuH,IAAAA,CAAI,EACrDvB,KAAK,CAAC,CAAA,EAAG,GAAA,CAAA;AACX,QAAA,OAAO2L,YAAAA,CAAapK,IAAAA,CAAAA;AACtB,IAAA,CAAA;AAEA,IAAA,MAAMiJ,gBAAgBtT,GAAAA,EAAK2E,GAAAA,CAAAA;AAC7B;;;;;;;;;;;"}
|
|
1
|
+
{"version":3,"file":"server.js","sources":["../../../src/constants.ts","../../../src/server/workspaceAssetsHandler.ts","../../../src/server/withJupyterWorkspaces.ts","../../../src/server/utils.ts","../../../src/server/kernelLifecycleProxy.ts","../../../src/api/workspaceAssetsApi.ts","../../../src/api/workspaceGatewayApiHandler.ts","../../../src/api/kernelApiHandler.ts","../../../src/server/hatcheryProxy.ts","../../../src/api/hatcheryApiHandler.ts"],"sourcesContent":["import { GEN3_API, GEN3_WORKSPACE_API } from '@gen3/core';\n\n// TODO: migrate this to @gen3/core\n\nexport const GEN3_HATCHERY_API =\n GEN3_WORKSPACE_API || '/workspace-api/workspace/hatchery'; // get replaced by revproxy\n\nexport const GEN3_KERNEL_API =\n process.env.GEN3_KERNEL_API || `${GEN3_API}/lw-workspace/proxy/jeg-panel/api`;\n\nexport const GEN3_JEG_GATEWAY_API =\n process.env.JEG_GATEWAY_API || `${GEN3_API}/lw-workspace/proxy/jeg-panel/api`;\n\n// TODO: resolve this with @gen3/core\nexport const GEN3_WORKSPACES_API =\n GEN3_WORKSPACE_API || `${GEN3_API}/lw-workspace`;\n\nexport const JEG_SERVICE_API =\n 'http://jupyter-enterprise-gateway.jupyter-pods.svc.cluster.local:8888';\n","/**\n * Next.js API route handler factory for serving JupyterLite static assets.\n *\n * Usage (consumer's `src/pages/api/workspace-assets/[tier]/[[...path]].ts`):\n *\n * import { createWorkspaceAssetsHandler } from '@gen3/jupyter-workspaces/server';\n * export default createWorkspaceAssetsHandler();\n *\n * Or with custom config:\n *\n * export default createWorkspaceAssetsHandler({\n * gatewayBaseUrl: '/api/workspace/gateway/',\n * });\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport nodePath from 'path';\nimport fs from 'fs';\nimport { getCookie } from 'cookies-next';\n\nconst MAX_FILE_SIZE_BYTES = 67108864; // 64 * 1024 * 1024\n\n// ---------- types ----------\n\nexport interface WorkspaceAssetsHandlerOptions {\n /** Gateway base URL injected into remote tier config (default: env JUPYTER_GATEWAY_BASE_URL or '/api/workspace/gateway/') */\n gatewayBaseUrl?: string;\n /**\n * Root directory containing the JupyterLite assets.\n * Default: `<cwd>/node_modules/@gen3/jupyter-workspaces/assets`\n */\n assetRoot?: string;\n /** Additional JupyterLite extensions to disable for the remote tier */\n additionalDisabledExtensions?: string[];\n /** Application name injected into JupyterLite config data and used as <title> override (opt-in branding). */\n appName?: string;\n /** Favicon URL injected into JupyterLite config data (opt-in branding). */\n faviconUrl?: string;\n}\n\n// ---------- constants ----------\n\nconst ALLOWED_TIERS = new Set(['free', 'remote']);\n\nconst SAFE_SEGMENT_RE = /^@?[A-Za-z0-9._-]+$/;\n\nconst MIME_TYPES: Record<string, string> = {\n '.html': 'text/html; charset=utf-8',\n '.js': 'application/javascript; charset=utf-8',\n '.mjs': 'application/javascript; charset=utf-8',\n '.json': 'application/json; charset=utf-8',\n '.css': 'text/css; charset=utf-8',\n '.wasm': 'application/wasm',\n '.txt': 'text/plain; charset=utf-8',\n '.svg': 'image/svg+xml',\n '.png': 'image/png',\n '.ico': 'image/x-icon',\n '.woff2': 'font/woff2',\n '.woff': 'font/woff',\n '.ttf': 'font/ttf',\n '.map': 'application/json; charset=utf-8',\n '.ipynb': 'application/json; charset=utf-8',\n};\n\nconst REMOTE_DISABLED_EXTENSIONS = [\n '@jupyterlite/services-extension:config-section-manager',\n '@jupyterlite/services-extension:default-drive',\n '@jupyterlite/services-extension:event-manager',\n '@jupyterlite/services-extension:exporters',\n '@jupyterlite/services-extension:kernel-manager',\n '@jupyterlite/services-extension:kernel-client',\n '@jupyterlite/services-extension:kernel-spec-client',\n '@jupyterlite/services-extension:kernel-spec-manager',\n '@jupyterlite/services-extension:kernel-specs',\n '@jupyterlite/services-extension:nbconvert-manager',\n '@jupyterlite/services-extension:session-manager',\n '@jupyterlite/application-extension:service-worker-manager',\n '@jupyterlab/apputils-extension:themes',\n];\n\n// ---------- helpers ----------\n\nconst ASSETS_ROOT_PATH =\n process.env.JUPYTER_ASSETS_ROOT_PATH || '/gen3/jupyter-workspaces/assets';\n\nfunction defaultAssetRoot(): string {\n return ASSETS_ROOT_PATH.startsWith('/')\n ? ASSETS_ROOT_PATH\n : nodePath.join(process.cwd(), ASSETS_ROOT_PATH);\n}\ninterface BrandingConfig {\n appName?: string;\n faviconUrl?: string;\n}\n\n/**\n * Resolve the origin from forwarding headers, with referer fallback.\n * Handles proxies that drop non-standard ports from the Host header.\n */\nfunction resolveOrigin(req: NextApiRequest): { proto: string; host: string } {\n const forwardedProto =\n (Array.isArray(req.headers['x-forwarded-proto'])\n ? req.headers['x-forwarded-proto'][0]\n : req.headers['x-forwarded-proto']) || 'http';\n const forwardedHost = Array.isArray(req.headers['x-forwarded-host'])\n ? req.headers['x-forwarded-host'][0]\n : req.headers['x-forwarded-host'];\n const hostHeader = Array.isArray(req.headers.host)\n ? req.headers.host[0]\n : req.headers.host;\n const refererHeader = Array.isArray(req.headers.referer)\n ? req.headers.referer[0]\n : req.headers.referer;\n\n let resolvedHost = (forwardedHost || hostHeader || '').trim();\n let resolvedProto = String(forwardedProto).trim() || 'http';\n\n if (refererHeader) {\n try {\n const refererUrl = new URL(refererHeader);\n if (!resolvedHost || !resolvedHost.includes(':')) {\n resolvedHost = refererUrl.host;\n }\n if (!resolvedProto) {\n resolvedProto = refererUrl.protocol.replace(':', '');\n }\n } catch {\n // Ignore malformed referer and keep header-derived values.\n }\n }\n\n if (!resolvedHost) {\n resolvedHost = 'localhost:8890';\n }\n\n return { proto: resolvedProto, host: resolvedHost };\n}\n\nfunction injectRemoteConfig(\n html: string,\n req: NextApiRequest,\n gatewayBaseUrl: string,\n disabledExtensions: string[],\n branding = {\n appName: 'JupyterLite',\n faviconUrl: '/favicon2.ico',\n } as BrandingConfig,\n): string {\n const { proto, host } = resolveOrigin(req);\n const absoluteGatewayBase = `${proto}://${host}${gatewayBaseUrl}`;\n\n // Inject server-side JEG token — overrides any client-supplied auth header.\n // This ensures calls from JupyterLite's own serverconnection.js are also authenticated.\n\n let accessToken = undefined;\n if (process.env.NODE_ENV === 'development') {\n // NOTE: This cookie can only be accessed from the client side\n // in development mode. Otherwise, the cookie is set as httpOnly\n accessToken = getCookie('credentials_token');\n }\n\n const configData: Record<string, unknown> = {\n remoteBaseUrl: absoluteGatewayBase,\n remoteToken: accessToken,\n disabledExtensions,\n fullThemesUrl: '/workspace-api/workspace-assets/remote/build/themes',\n };\n\n if (branding?.appName) configData.appName = branding.appName;\n if (branding?.faviconUrl) configData.faviconUrl = branding.faviconUrl;\n\n let result = html.replace(\n /(<script\\s+id=\"jupyter-config-data\"[^>]*>)\\s*(\\{[^]*?\\})\\s*(<\\/script>)/,\n (_match, openTag: string, existingJson: string, closeTag: string) => {\n let existing: Record<string, unknown> = {};\n try {\n existing = JSON.parse(existingJson);\n } catch {\n // empty or malformed — start fresh\n }\n const merged = { ...existing, ...configData };\n if (Array.isArray(existing.disabledExtensions)) {\n const combined = new Set([\n ...(existing.disabledExtensions as string[]),\n ...disabledExtensions,\n ]);\n merged.disabledExtensions = [...combined];\n }\n return `${openTag}${JSON.stringify(merged)}${closeTag}`;\n },\n );\n\n if (branding?.appName) {\n result = result.replace(\n /<title>[^<]*<\\/title>/,\n `<title>${branding.appName}</title>`,\n );\n }\n\n return result;\n}\n\nfunction injectBranding(html: string, branding: BrandingConfig): string {\n let result = html.replace(\n /(<script\\s+id=\"jupyter-config-data\"[^>]*>)\\s*(\\{[^]*?\\})\\s*(<\\/script>)/,\n (_match, openTag: string, existingJson: string, closeTag: string) => {\n let existing: Record<string, unknown> = {};\n try {\n existing = JSON.parse(existingJson);\n } catch (error: unknown) {\n // empty or malformed — start fresh\n if (error instanceof Error) {\n console.log('Failed to parse existing JSON', error.message);\n } else {\n console.log('Failed to parse existing JSON', error);\n }\n }\n if (branding.appName) existing.appName = branding.appName;\n if (branding.faviconUrl) existing.faviconUrl = branding.faviconUrl;\n return `${openTag}${JSON.stringify(existing)}${closeTag}`;\n },\n );\n\n if (branding.appName) {\n result = result.replace(\n /<title>[^<]*<\\/title>/,\n `<title>${branding.appName}</title>`,\n );\n }\n\n return result;\n}\n\n// ---------- factory ----------\n\nexport function createWorkspaceAssetsHandler(\n options?: WorkspaceAssetsHandlerOptions,\n) {\n const gatewayBaseUrl =\n options?.gatewayBaseUrl ??\n process.env.JUPYTER_GATEWAY_BASE_URL ??\n '/api/workspace/gateway/';\n\n const assetRoot = options?.assetRoot ?? defaultAssetRoot();\n\n const disabledExtensions = options?.additionalDisabledExtensions\n ? [...REMOTE_DISABLED_EXTENSIONS, ...options.additionalDisabledExtensions]\n : REMOTE_DISABLED_EXTENSIONS;\n\n const branding: BrandingConfig | undefined =\n options?.appName || options?.faviconUrl\n ? { appName: options.appName, faviconUrl: options.faviconUrl }\n : undefined;\n\n // Build the allowed-file sets once at factory time (not per-request) to\n // avoid unbounded I/O on every incoming request (CWE-770).\n const walkDir = (dir: string, set: Set<string>): void => {\n try {\n for (const entry of fs.readdirSync(dir, { withFileTypes: true })) {\n const full = nodePath.join(dir, entry.name);\n if (entry.isDirectory()) {\n walkDir(full, set);\n } else {\n set.add(full);\n }\n }\n } catch {\n // Tier directory doesn't exist yet — set remains empty and handler will 404.\n }\n };\n\n const allowedFilesByTier: Record<string, Set<string>> = {\n free: new Set<string>(),\n remote: new Set<string>(),\n };\n for (const tier of ALLOWED_TIERS) {\n walkDir(nodePath.resolve(assetRoot, tier), allowedFilesByTier[tier]);\n }\n\n return function handler(req: NextApiRequest, res: NextApiResponse): void {\n const { tier, path: pathSegments } = req.query;\n\n if (typeof tier !== 'string' || !ALLOWED_TIERS.has(tier)) {\n res.status(404).end('Not found');\n return;\n }\n\n const segments: string[] = Array.isArray(pathSegments)\n ? pathSegments\n : pathSegments\n ? [pathSegments]\n : [];\n\n let tierRoot: string;\n if (tier === 'free') {\n tierRoot = nodePath.resolve(assetRoot, 'free');\n } else if (tier === 'remote') {\n tierRoot = nodePath.resolve(assetRoot, 'remote');\n } else {\n res.status(404).end('Not found');\n return;\n }\n\n const safeSegments: string[] = [];\n for (const seg of segments) {\n if (\n typeof seg !== 'string' ||\n !SAFE_SEGMENT_RE.test(seg) ||\n seg === '.' ||\n seg === '..'\n ) {\n res.status(403).end('Forbidden');\n return;\n }\n safeSegments.push(nodePath.basename(seg));\n }\n\n const allowedFiles = allowedFilesByTier[tier];\n\n const candidatePath = nodePath.resolve(tierRoot, ...safeSegments);\n const candidateIndex = nodePath.join(candidatePath, 'index.html');\n\n let filePath: string;\n if (allowedFiles.has(candidatePath)) {\n filePath = candidatePath;\n } else if (allowedFiles.has(candidateIndex)) {\n filePath = candidateIndex;\n } else {\n res.status(404).end('Not found');\n return;\n }\n\n const ext = nodePath.extname(filePath).toLowerCase();\n const contentType = MIME_TYPES[ext] || 'application/octet-stream';\n\n const isBuildAsset =\n filePath.includes(nodePath.join(tier, 'build')) ||\n filePath.includes(nodePath.join(tier, 'extensions'));\n\n res.setHeader('X-Content-Type-Options', 'nosniff');\n res.setHeader('Cross-Origin-Opener-Policy', 'same-origin');\n res.setHeader('Cross-Origin-Embedder-Policy', 'require-corp');\n res.setHeader('Cross-Origin-Resource-Policy', 'cross-origin');\n\n if (process.env.NODE_ENV === 'development') {\n // In dev there is no fence service to plant the access_token cookie, so\n // we derive it from credentials_token (which is NOT httpOnly in dev) and\n // set it here. The browser will then send it automatically with every\n // subsequent request to the same origin — including JupyterLite's direct\n // calls to /lw-workspace/proxy/jeg-proxy/api/kernelspecs (which bypass\n // the Next.js proxy and therefore need the cookie on the wire).\n const accessToken = req.cookies?.['credentials_token'];\n if (accessToken) {\n res.setHeader(\n 'Set-Cookie',\n `access_token=${encodeURIComponent(accessToken)}; Path=/; SameSite=Lax`,\n );\n }\n }\n\n if (nodePath.basename(filePath) === 'service-worker.js') {\n res.setHeader('Service-Worker-Allowed', '/');\n }\n\n const isRemoteLabHtml =\n tier === 'remote' &&\n ext === '.html' &&\n filePath.includes(nodePath.join('lab', 'index.html'));\n\n if (isRemoteLabHtml) {\n res.setHeader('Content-Type', contentType);\n res.setHeader('Cache-Control', 'no-cache, no-store, must-revalidate');\n try {\n const html = fs.readFileSync(filePath, 'utf-8');\n const injected = injectRemoteConfig(\n html,\n req,\n gatewayBaseUrl,\n disabledExtensions,\n branding,\n );\n res.status(200).send(injected);\n } catch {\n res.status(500).end('Internal server error');\n }\n return;\n }\n\n // Non-remote HTML (e.g. free-tier lab) — apply branding if configured\n const isHtmlResponse = ext === '.html';\n if (isHtmlResponse && branding) {\n res.setHeader('Content-Type', contentType);\n res.setHeader('Cache-Control', 'no-cache, no-store, must-revalidate');\n try {\n const html = fs.readFileSync(filePath, 'utf-8');\n res.status(200).send(injectBranding(html, branding));\n } catch {\n res.status(500).end('Internal server error');\n }\n return;\n }\n\n res.setHeader('Content-Type', contentType);\n res.setHeader(\n 'Cache-Control',\n isBuildAsset\n ? 'public, max-age=31536000, immutable'\n : 'public, max-age=3600, must-revalidate',\n );\n\n const stat = fs.statSync(filePath);\n if (stat.size > MAX_FILE_SIZE_BYTES) {\n res.status(413).end('File too large');\n return;\n }\n\n const stream = fs.createReadStream(filePath);\n stream.on('error', () => {\n res.status(500).end('Internal server error');\n });\n stream.pipe(res);\n };\n}\n\n/** Default handler — for one-liner re-exports */\nconst defaultHandler = createWorkspaceAssetsHandler();\nexport default defaultHandler;\n","/**\n * Next.js config wrapper that adds all workspace-related plumbing.\n *\n * Usage (consumer's `next.config.js`):\n *\n * const { withJupyterWorkspaces } = require('@gen3/workspaces/server');\n * module.exports = withJupyterWorkspaces(yourNextConfig);\n */\n\nimport type { NextConfig } from 'next';\nimport nodePath from 'path';\nimport type { WebpackConfigContext } from 'next/dist/server/config-shared';\nimport type { Configuration } from 'webpack';\n\nexport interface WithJupyterWorkspacesOptions {\n /**\n * URL of the gateway proxy for local dev rewrites.\n * Default: env `GATEWAY_PROXY_URL` or `http://localhost:8890`\n */\n gatewayProxyUrl?: string;\n /**\n * Workspace page routes that need COOP/COEP headers.\n * Default: ['/workspaces/jupyter', '/workspaces/jupyter-lite', '/workspaces/jupyter-kernel']\n */\n workspaceRoutes?: string[];\n}\n\nconst DEFAULT_WORKSPACE_ROUTES = ['/Workspaces'];\n\nexport function withJupyterWorkspaces(\n nextConfig: NextConfig,\n options?: WithJupyterWorkspacesOptions,\n): NextConfig {\n const workspaceRoutes = options?.workspaceRoutes ?? DEFAULT_WORKSPACE_ROUTES;\n\n return {\n ...nextConfig,\n\n // Merge transpilePackages\n transpilePackages: [\n ...(nextConfig.transpilePackages ?? []),\n ...['@gen3/workspaces'].filter(\n (pkg) => !(nextConfig.transpilePackages ?? []).includes(pkg),\n ),\n ],\n\n // Merge webpack config — add React dedup alias\n webpack(config: Configuration, ctx: WebpackConfigContext) {\n config.resolve = config.resolve ?? {};\n config.resolve.alias = {\n ...(config.resolve.alias ?? {}),\n react: nodePath.dirname(require.resolve('react/package.json')),\n 'react-dom': nodePath.dirname(\n require.resolve('react-dom/package.json'),\n ),\n };\n\n // Chain the consumer's existing webpack config\n if (typeof nextConfig.webpack === 'function') {\n return nextConfig.webpack(config, ctx);\n }\n return config;\n },\n\n // Merge rewrites — add gateway proxy rewrite in dev mode\n async rewrites() {\n const isDev = process.env.NODE_ENV === 'development';\n\n const existing =\n typeof nextConfig.rewrites === 'function'\n ? await nextConfig.rewrites()\n : [];\n\n if (!isDev) return existing;\n\n const gatewayProxyUrl =\n options?.gatewayProxyUrl ??\n process.env.GATEWAY_PROXY_URL ??\n 'http://localhost:8890';\n\n const gatewayRewrite = {\n source: '/api/workspace/gateway/:path*',\n destination: `${gatewayProxyUrl}/api/workspace/gateway/:path*`,\n };\n\n // rewrites() can return an array or { beforeFiles, afterFiles, fallback }\n if (Array.isArray(existing)) {\n return [gatewayRewrite, ...existing];\n }\n return {\n ...existing,\n beforeFiles: [gatewayRewrite, ...(existing.beforeFiles ?? [])],\n };\n },\n\n // Merge headers — add COOP/COEP for workspace routes\n async headers() {\n const existing =\n typeof nextConfig.headers === 'function'\n ? await nextConfig.headers()\n : [];\n\n const coopCoepHeaders = workspaceRoutes.map((route) => ({\n source: route,\n headers: [\n { key: 'Cross-Origin-Opener-Policy', value: 'same-origin' },\n { key: 'Cross-Origin-Embedder-Policy', value: 'credentialless' },\n ],\n }));\n\n return [...existing, ...coopCoepHeaders];\n },\n };\n}\n","/**\n * Shared HTTP proxy utility for server-side proxy handlers.\n * Streams request body through and forwards response status + body.\n *\n * Also exports two token helpers used by the proxy factories:\n * - extractTokenFallback: minimal cookie/header extraction used when the host\n * app has not injected its own getToken (standalone / test use).\n * - decodeJwtClaims: base64url decode of the JWT payload for REMOTE_USER header.\n * Crypto verification is Ambassador's job — we only need the sub/username claim.\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\n\n/**\n * Minimal JWT extraction fallback — used only when the host app does not inject\n * its own getToken. Prefers Authorization: Bearer, then access_token cookie.\n * In gen3-vectis production this is never reached — getAccessToken is always wired.\n */\nexport function extractTokenFallback(req: NextApiRequest): string | null {\n const auth = req.headers['authorization'];\n if (typeof auth === 'string' && auth.startsWith('Bearer ')) {\n return auth.slice(7).trim() || null;\n }\n const cookie = req.headers['cookie'] ?? '';\n const m = cookie.match(/(?:^|;\\s*)access_token=([^;]+)/);\n return m ? decodeURIComponent(m[1]).trim() || null : null;\n}\n\n/**\n * Decode JWT payload claims without cryptographic verification.\n * Ambassador has already verified the RS256 signature — we just need the sub claim\n * to set the REMOTE_USER header for per-user isolation enforcement downstream.\n */\n// Maximum JWT string length accepted before base64 decoding.\n// GA4GH RAS Passport JWTs embed multiple signed Visa JWTs as claims, so the\n// outer passport can easily exceed 8 KiB (50 visas × ~2 KB each ≈ 136 KB encoded).\n// 512 KiB covers the most complex real-world passports while still guarding against\n// crafted JWTs designed to exhaust server memory. Ambassador has already verified\n// the RS256 signature — this cap only defends the local base64/JSON decode step.\nconst MAX_JWT_LENGTH = 524288; // 512 KiB\n\nexport function decodeJwtClaims(jwt: string): Record<string, unknown> | null {\n if (jwt.length > MAX_JWT_LENGTH) return null;\n try {\n const parts = jwt.split('.');\n if (parts.length < 2) return null;\n const padded = parts[1]\n .replace(/-/g, '+')\n .replace(/_/g, '/')\n .padEnd(Math.ceil(parts[1].length / 4) * 4, '=');\n return JSON.parse(Buffer.from(padded, 'base64').toString('utf8')) as Record<\n string,\n unknown\n >;\n } catch {\n return null;\n }\n}\n\nexport interface ProxyRequestOptions {\n req: NextApiRequest;\n res: NextApiResponse;\n targetUrl: string;\n method: 'GET' | 'POST' | 'DELETE' | 'PUT' | 'PATCH';\n extraHeaders?: Record<string, string>;\n /** Whether to stream the incoming request body to the target. */\n forwardBody?: boolean;\n}\n\nexport async function createProxyRequest({\n req,\n res,\n targetUrl,\n method,\n extraHeaders = {},\n forwardBody = false,\n}: ProxyRequestOptions): Promise<void> {\n const headers: Record<string, string> = {\n ...extraHeaders,\n };\n if (\n forwardBody &&\n (method === 'POST' || method === 'PUT' || method === 'PATCH')\n ) {\n headers['Content-Type'] ??= 'application/json';\n }\n\n let body: BodyInit | undefined;\n if (\n forwardBody &&\n (method === 'POST' || method === 'PUT' || method === 'PATCH')\n ) {\n let buf: Buffer;\n try {\n buf = await bufferBody(req);\n } catch (err) {\n const statusCode = (err as { statusCode?: number }).statusCode ?? 400;\n const msg = err instanceof Error ? err.message : 'Bad request';\n res.status(statusCode).json({ error: msg });\n return;\n }\n // Node.js Buffer is a Uint8Array subclass; cast to silence DOM BodyInit mismatch\n body = buf as unknown as BodyInit;\n if (buf.length > 0) {\n headers['Content-Length'] = String(buf.length);\n }\n }\n\n let upRes: Response;\n try {\n upRes = await fetch(targetUrl, {\n method,\n headers,\n body,\n signal: AbortSignal.timeout(30_000),\n });\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n res.status(502).json({ error: `Upstream unreachable: ${msg}` });\n return;\n }\n\n // Forward status and content-type\n const contentType = upRes.headers.get('content-type') || 'application/json';\n res.setHeader('Content-Type', contentType);\n\n if (upRes.status === 204 || upRes.status === 304) {\n res.status(upRes.status).end();\n return;\n }\n\n // Do not forward raw upstream error bodies — they may contain stack traces or\n // internal hostnames. Log them server-side (CloudWatch) and return a generic message.\n if (upRes.status >= 500) {\n const errBody = await upRes.text().catch(() => '');\n console.error(\n '[proxy] upstream %d from %s: %s',\n upRes.status,\n targetUrl,\n errBody,\n );\n res.status(502).json({ error: 'Upstream service error.' });\n return;\n }\n\n const responseBody = await upRes.text();\n res.status(upRes.status).send(responseBody);\n}\n\n// Maximum request body size accepted by the proxy (1 MiB).\n// Prevents memory exhaustion from oversized payloads before any business logic runs.\nconst MAX_BODY_BYTES = 1 * 1024 * 1024;\n\nfunction bufferBody(req: NextApiRequest): Promise<Buffer> {\n return new Promise((resolve, reject) => {\n const chunks: Buffer[] = [];\n let total = 0;\n req.on('data', (chunk: Buffer) => {\n total += chunk.length;\n if (total > MAX_BODY_BYTES) {\n req.destroy();\n reject(\n Object.assign(new Error('Request body too large'), {\n statusCode: 413,\n }),\n );\n return;\n }\n chunks.push(chunk);\n });\n req.on('end', () => resolve(Buffer.concat(chunks)));\n req.on('error', reject);\n });\n}\n","/**\n * createKernelLifecycleProxyHandler — server-side Next.js API route handler\n * for all kernel control-plane traffic.\n *\n * Security properties:\n * - Billing gate: POST /kernels fetches Fence /credentials/cdis first;\n * if that fails, no kernel is ever launched.\n * - Kernel spec filtering: the browser receives only the names/costs defined in policy.\n * - REMOTE_USER forwarded on every upstream request — JEG enforces per-user isolation.\n * - KERNEL_ID_RE validates all kernel IDs before they reach the upstream URL.\n *\n * Token extraction:\n * Pass getToken to reuse the host app's cookie logic (strongly recommended).\n * In gen3-vectis: `(req) => getAccessToken(req.headers['cookie'] ?? '') ?? null`\n * Ambassador performs RS256 verification before any request reaches Next.js.\n *\n * Usage (src/pages/api/workspace/kernel/[...action].ts — generated by bin/init.mjs):\n * import { createKernelLifecycleProxyHandler } from '@gen3/jupyter-workspaces/server';\n * import { getAccessToken } from '../../lib/auth/getLoginStatus';\n * const policy = process.env.KERNEL_SPEC_POLICY ? JSON.parse(process.env.KERNEL_SPEC_POLICY) : {};\n * export default createKernelLifecycleProxyHandler({\n * gen3Endpoint: process.env.GEN3_ENDPOINT,\n * fenceUrl: process.env.FENCE_URL,\n * kernelSpecPolicy: policy,\n * getToken: (req) => getAccessToken(req.headers['cookie'] ?? '') ?? null,\n * });\n * export const config = { api: { bodyParser: false } };\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport { decodeJwtClaims, extractTokenFallback } from './utils';\nimport { fetchFence, GEN3_FENCE_SERVICE } from '@gen3/core';\nimport { GEN3_FENCE_API } from '@gen3/core/server';\nimport { JEG_SERVICE_API } from '../constants';\n\n/* ------------------------------------------------------------------ */\n/* Types */\n/* ------------------------------------------------------------------ */\n\n/** Kernel spec filtering and cost annotation policy (server-side only). */\nexport interface KernelSpecPolicy {\n /**\n * Raw JEG kernel spec names that are permitted for this deployment.\n * Only these will be returned to the browser.\n */\n allowedSpecs: string[];\n /**\n * Cost per hour for each spec. 0 = included in base subscription.\n * Injected into the spec as `costPerHour` before returning to browser.\n */\n costPerHour: Record<string, number>;\n /**\n * Human-readable display name per spec (replaces raw JEG spec name).\n * e.g. { \"python3_gpu_a100\": \"Python (GPU A100 — $2.40/hr)\" }\n */\n displayNames: Record<string, string>;\n /**\n * Node type label for UI badge.\n * e.g. { \"python3_micro\": \"micro\", \"python3_gpu_a100\": \"gpu\" }\n */\n nodeType: Record<string, string>;\n}\n\nexport interface BillingEvent {\n username: string;\n action: 'launch' | 'terminate';\n kernelSpec?: string;\n kernelId?: string;\n costTier: number;\n timestamp: string;\n}\n\nexport interface KernelLifecycleProxyConfig {\n /**\n * External hostname for Ambassador routing, e.g. \"mycommons.example.com\"\n * or \"localhost:30080\" in local dev.\n * Used to build the upstream URL: https://{gen3Endpoint}/lw-workspace/proxy/...\n */\n gen3Endpoint: string | undefined;\n /** Internal URL of the Fence service, e.g. http://fence.fence.svc:80 */\n fenceUrl: string | undefined;\n /** Kernel spec filtering + billing policy (server-side only). */\n kernelSpecPolicy: Partial<KernelSpecPolicy>;\n /**\n * Set to true when JEG is configured and enabled for this deployment.\n * Controlled by ENABLE_JEG=true env var in gen3-vectis.\n * When false (default), all routes except GET /api/status return 503 silently so\n * the UI fails gracefully without error spam.\n */\n jegEnabled?: boolean;\n /**\n * Number of idle days before a kernel is considered stale (for /api/reap).\n * Defaults to 10. Controlled by JEG_IDLE_KILL_DAYS env var.\n */\n idleKillDays?: number;\n /**\n * Maximum kernel age in days regardless of idle state (for /api/reap).\n * Defaults to 15. Controlled by JEG_MAX_KERNEL_AGE_DAYS env var.\n */\n maxKernelAgeDays?: number;\n /**\n * Optional billing event sink. Defaults to structured JSON to stdout (CloudWatch).\n * Swap for DynamoDB, Stripe, etc. without changing any other code.\n * The function MUST NOT block — fire and forget.\n */\n billingSink?: (event: BillingEvent) => void;\n /**\n * Token extractor injected by the host application.\n * In gen3-vectis: `(req) => getAccessToken(req.headers['cookie'] ?? '') ?? null`\n * When omitted a minimal Bearer-header/cookie fallback is used (dev/standalone only).\n * Ambassador has already done RS256 verification — this is extraction only.\n */\n getToken?: (req: NextApiRequest) => string | null;\n}\n\n/* ------------------------------------------------------------------ */\n/* Default billing sink — structured CloudWatch-compatible JSON log */\n/* ------------------------------------------------------------------ */\n\nfunction defaultBillingSink(event: BillingEvent): void {\n // CloudWatch Logs Insights picks up structured JSON automatically\n process.stdout.write(\n JSON.stringify({ type: 'WORKSPACE_BILLING', ...event }) + '\\n',\n );\n}\n\n/* ------------------------------------------------------------------ */\n/* Fence credential fetch */\n/* ------------------------------------------------------------------ */\n\ninterface FenceCreds {\n key_id: string;\n api_key: string; // pragma: allowlist secret\n}\n\nconst EMPTY_FENCE_CREDS: FenceCreds = {\n key_id: '',\n api_key: '', // pragma: allowlist secret\n};\n\nasync function fetchFenceCreds(\n fenceUrl: string,\n jwt: string,\n): Promise<FenceCreds> {\n let parsedFenceUrl: URL;\n try {\n parsedFenceUrl = new URL(fenceUrl);\n } catch {\n throw new Error('Fence URL is misconfigured.');\n }\n if (\n parsedFenceUrl.protocol !== 'http:' &&\n parsedFenceUrl.protocol !== 'https:'\n ) {\n throw new Error('Fence URL is misconfigured.');\n }\n try {\n const response = await fetchFence<FenceCreds>(\n {\n endpoint: 'credentials/api',\n method: 'GET',\n headers: {\n Authorization: `Bearer ${jwt}`,\n 'Content-Type': 'application/json',\n },\n },\n process.env.NODE_ENV === 'production', // use the FENCE Service if in production\n );\n if (!response?.data?.api_key) {\n console.error('No valid API key found in Fence response');\n return {\n api_key: '', // pragma: allowlist secret\n key_id: '',\n };\n }\n return response.data;\n } catch (error: unknown) {\n if (error instanceof Error) {\n console.error('Error fetching API key from Fence:', error);\n } else {\n console.error('Error fetching API key from Fence');\n }\n return EMPTY_FENCE_CREDS;\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Kernel spec response transformation */\n/* ------------------------------------------------------------------ */\n\ninterface RawKernelSpecsResponse {\n default: string;\n kernelspecs: Record<\n string,\n {\n name: string;\n spec: {\n display_name: string;\n language: string;\n argv?: string[];\n metadata?: Record<string, unknown>;\n };\n resources?: Record<string, string>;\n }\n >;\n}\n\nfunction filterAndAnnotateSpecs(\n raw: RawKernelSpecsResponse,\n policy: Partial<KernelSpecPolicy>,\n): RawKernelSpecsResponse {\n const allowedSpecs = policy.allowedSpecs ?? [];\n const costPerHour = policy.costPerHour ?? {};\n const displayNames = policy.displayNames ?? {};\n const nodeType = policy.nodeType ?? {};\n\n if (allowedSpecs.length === 0) {\n // No policy configured — return everything unannotated (useful during dev bootstrap)\n return raw;\n }\n\n const filteredSpecs: RawKernelSpecsResponse['kernelspecs'] = {};\n\n for (const specName of allowedSpecs) {\n const rawSpec = raw.kernelspecs[specName];\n if (!rawSpec) continue; // JEG doesn't have this spec — skip silently\n\n filteredSpecs[specName] = {\n ...rawSpec,\n spec: {\n ...rawSpec.spec,\n // Override display_name with our curated name if provided\n display_name: displayNames[specName] ?? rawSpec.spec.display_name,\n // Inject billing metadata into spec.metadata (available to browser)\n metadata: {\n ...(rawSpec.spec.metadata ?? {}),\n costPerHour: costPerHour[specName] ?? 0,\n nodeType: nodeType[specName] ?? 'unknown',\n },\n },\n };\n }\n\n // Use first allowed spec as default if original default was filtered out\n const filteredDefault = allowedSpecs.includes(raw.default)\n ? raw.default\n : (allowedSpecs[0] ?? '');\n\n return { default: filteredDefault, kernelspecs: filteredSpecs };\n}\n\n/* ------------------------------------------------------------------ */\n/* Body buffering (Next.js bodyParser: false) */\n/* ------------------------------------------------------------------ */\n\nfunction readBody(req: NextApiRequest): Promise<Buffer> {\n return new Promise((resolve, reject) => {\n const chunks: Buffer[] = [];\n req.on('data', (chunk: Buffer) => chunks.push(chunk));\n req.on('end', () => resolve(Buffer.concat(chunks)));\n req.on('error', reject);\n });\n}\n\n/* ------------------------------------------------------------------ */\n/* Ambassador upstream URL builder */\n/* ------------------------------------------------------------------ */\n\n// function buildAmbassadorUrl(gen3Endpoint: string, kernelPath: string): string {\n// // gen3Endpoint may or may not have a scheme\n// const base = gen3Endpoint.startsWith('http')\n// ? gen3Endpoint\n// : `https://${gen3Endpoint}`;\n// const parsed = new URL(base);\n// if (parsed.protocol !== 'http:' && parsed.protocol !== 'https:') {\n// throw new Error('gen3Endpoint must use http or https protocol.');\n// }\n// return `${parsed.origin}${parsed.pathname.replace(/\\/$/, '')}/lw-workspace/proxy${kernelPath}`;\n// }\n\nfunction buildAmbassadorUrl(gen3Endpoint: string, kernelPath: string): string {\n // gen3Endpoint may or may not have a scheme\n const base = gen3Endpoint.startsWith('http')\n ? gen3Endpoint\n : `https://${gen3Endpoint}`;\n const parsed = new URL(base);\n if (parsed.protocol !== 'http:' && parsed.protocol !== 'https:') {\n throw new Error('gen3Endpoint must use http or https protocol.');\n }\n return `${parsed.origin}${parsed.pathname.replace(/\\/$/, '')}/lw-workspace/proxy${kernelPath}`;\n}\n\n/* ------------------------------------------------------------------ */\n/* Route matching */\n/* ------------------------------------------------------------------ */\n\nconst KERNEL_ID_RE = /^[a-f0-9-]{8,36}$/i;\n\ntype KernelRoute =\n | { type: 'kernelspecs' }\n | { type: 'kernels_list' }\n | { type: 'kernel_launch' }\n | { type: 'kernel_delete'; kernelId: string }\n | { type: 'kernel_passthrough'; kernelPath: string }\n | { type: 'status' }\n | { type: 'reap' };\n\ntype SimpleRoute = Exclude<\n KernelRoute,\n { type: 'kernel_delete' | 'kernel_passthrough' }\n>;\n\n// Table-driven simple routes: all match /api/{resource} with no kernel ID segment.\nconst SIMPLE_ROUTES = new Map<string, SimpleRoute>([\n ['GET:status', { type: 'status' }],\n ['POST:reap', { type: 'reap' }],\n ['GET:kernelspecs', { type: 'kernelspecs' }],\n ['GET:kernels', { type: 'kernels_list' }],\n ['POST:kernels', { type: 'kernel_launch' }],\n]);\n\nfunction resolveKernelRoute(\n method: string,\n actionSegments: string[],\n): KernelRoute | null {\n const [seg1, seg2] = actionSegments;\n\n if (!seg2) {\n return SIMPLE_ROUTES.get(`${method}:${seg1}`) ?? null;\n }\n\n // Routes with a kernel ID segment — validate format before use.\n if (seg1 === 'kernels' && KERNEL_ID_RE.test(seg2)) {\n if (method === 'DELETE') {\n return { type: 'kernel_delete', kernelId: seg2 };\n }\n // GET /api/kernels/{id}/channels or similar (passthrough for WebSocket upgrade info)\n if (method === 'GET') {\n const rest = actionSegments.slice(2).join('/');\n return {\n type: 'kernel_passthrough',\n kernelPath: `/api/kernels/${seg2}/${rest}`,\n };\n }\n }\n\n return null;\n}\n\n/* ------------------------------------------------------------------ */\n/* Main factory — shared types and per-route handlers */\n/* ------------------------------------------------------------------ */\n\nfunction errMsg(err: unknown): string {\n return err instanceof Error ? err.message : String(err);\n}\n\ninterface RouteContext {\n req: NextApiRequest;\n gen3Endpoint: string;\n fenceUrl: string | undefined;\n kernelSpecPolicy: Partial<KernelSpecPolicy>;\n ambassadorHeaders: Record<string, string>;\n /** Unsanitised JWT — use only for non-header contexts (e.g. Fence fetch body). */\n jwt: string;\n username: string;\n sink: (event: BillingEvent) => void;\n idleKillDays: number;\n maxKernelAgeDays: number;\n}\n\n/* -------- GET /api/kernelspecs -------- */\nasync function handleKernelSpecs(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernelspecs');\n try {\n const upRes = await fetch(upstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n if (!upRes.ok) {\n res\n .status(upRes.status)\n .json({ error: `Gateway ${upRes.status}: ${upRes.statusText}` });\n return;\n }\n const rawSpecs = (await upRes.json()) as RawKernelSpecsResponse;\n res\n .status(200)\n .json(filterAndAnnotateSpecs(rawSpecs, ctx.kernelSpecPolicy));\n } catch {\n res.status(502).json({ error: 'Failed to fetch kernel specs.' });\n }\n}\n\n/* -------- GET /api/kernels -------- */\nasync function handleKernelsList(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernels');\n try {\n const upRes = await fetch(upstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n if (!upRes.ok) {\n res\n .status(upRes.status)\n .json({ error: `Gateway ${upRes.status}: ${upRes.statusText}` });\n return;\n }\n res.status(200).json(await upRes.json());\n } catch {\n res.status(502).json({ error: 'Failed to list kernels.' });\n }\n}\n\n/* -------- POST /api/reap — bulk-delete stale/aged kernels -------- */\nasync function handleReap(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n // const listUpstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernels');\n const listUpstream = `${ctx.gen3Endpoint}/api/kernels`;\n let kernelList: Array<{ id: string; name: string; last_activity?: string }> =\n [];\n try {\n const listRes = await fetch(listUpstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n\n if (!listRes.ok) {\n res\n .status(listRes.status)\n .json({ error: `Failed to list kernels: ${listRes.status}` });\n return;\n }\n kernelList = (await listRes.json()) as typeof kernelList;\n } catch (err) {\n res.status(502).json({ error: `Kernel list unavailable: ${errMsg(err)}` });\n return;\n }\n\n const now = Date.now();\n const idleKillMins = ctx.idleKillDays * 24 * 60;\n const maxAgeMins = ctx.maxKernelAgeDays * 24 * 60;\n const reaped: string[] = [];\n const errors: string[] = [];\n\n for (const kernel of kernelList) {\n if (!KERNEL_ID_RE.test(kernel.id)) continue; // skip any malformed IDs from upstream\n const lastActivity = kernel.last_activity\n ? new Date(kernel.last_activity).getTime()\n : 0;\n const idleMins =\n lastActivity > 0 ? (now - lastActivity) / 60_000 : Infinity;\n if (idleMins <= idleKillMins && idleMins <= maxAgeMins) continue;\n\n const deleteUpstream = buildAmbassadorUrl(\n ctx.gen3Endpoint,\n `/api/kernels/${encodeURIComponent(kernel.id)}`,\n );\n try {\n await fetch(deleteUpstream, {\n method: 'DELETE',\n headers: ctx.ambassadorHeaders,\n });\n reaped.push(kernel.id);\n ctx.sink({\n username: ctx.username,\n action: 'terminate',\n kernelId: kernel.id,\n costTier: 0,\n timestamp: new Date().toISOString(),\n });\n } catch {\n errors.push(kernel.id);\n }\n }\n\n res.status(200).json({ reaped, errors });\n}\n\n/* -------- POST /api/kernels — launch with Fence cred injection -------- */\nasync function handleKernelLaunch(\n ctx: RouteContext,\n res: NextApiResponse,\n): Promise<void> {\n if (!ctx.fenceUrl) {\n res.status(503).json({ error: 'FENCE_URL is not configured.' });\n return;\n }\n\n // 1. Fetch per-user S3 credentials from Fence.\n // If this fails, we return 502 and do NOT launch a kernel.\n let fenceCreds: FenceCreds;\n try {\n fenceCreds = await fetchFenceCreds(ctx.fenceUrl, ctx.jwt);\n } catch (err) {\n res\n .status(502)\n .json({ error: `Storage credentials unavailable: ${errMsg(err)}` });\n return;\n }\n\n // 2. Read the original launch body from the client.\n const rawBody = await readBody(ctx.req);\n let launchBody: Record<string, unknown> = {};\n try {\n launchBody = JSON.parse(rawBody.toString('utf8')) as Record<\n string,\n unknown\n >;\n } catch {\n // empty or invalid JSON — proceed with empty body\n }\n\n const kernelSpec = (launchBody.name as string) || '';\n\n // 3. Inject gen3-fuse credential env vars into the kernel launch body.\n // JEG forwards these to the kernel pod → init container writes /.gen3/credentials.json\n // → gen3-fuse sidecar mounts the user's S3 bucket.\n const enrichedBody = {\n ...launchBody,\n env: {\n ...((launchBody.env as Record<string, string>) ?? {}),\n GEN3_API_KEY_ID: fenceCreds.key_id,\n GEN3_API_KEY_SECRET: fenceCreds.api_key, // pragma: allowlist secret\n NAMESPACE: process.env.NAMESPACE || 'jupyter-pods',\n GEN3_ENDPOINT: ctx.gen3Endpoint,\n },\n };\n\n // 4. Non-blocking billing event (launch intent).\n const launchTimestamp = new Date().toISOString();\n const costTier = ctx.kernelSpecPolicy.costPerHour?.[kernelSpec] ?? 0;\n ctx.sink({\n username: ctx.username,\n action: 'launch',\n kernelSpec,\n costTier,\n timestamp: launchTimestamp,\n });\n\n // TODO:\n // BILLING_HOOK: pricing/quota check — runs before kernel is launched.\n // Replace the resolved value below with an async pricing/quota API call.\n // Return false here to block launch with a 402 Payment Required.\n // Example: const approved = await checkQuotaAndPrice({ username, kernelSpec, costTier });\n const billingApproved = true; // TODO: hook pricing gate here\n if (!billingApproved) {\n res\n .status(402)\n .json({ error: 'Kernel launch requires billing authorization.' });\n return;\n }\n\n // 5. Forward to JEG via Ambassador.\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, '/api/kernels');\n let launchRes: Response;\n try {\n launchRes = await fetch(upstream, {\n method: 'POST',\n headers: { ...ctx.ambassadorHeaders, 'Content-Type': 'application/json' },\n body: JSON.stringify(enrichedBody),\n });\n } catch (err) {\n res.status(502).json({ error: `Kernel launch failed: ${errMsg(err)}` });\n return;\n }\n\n if (!launchRes.ok) {\n res.status(launchRes.status).json({\n error: `Kernel launch failed: ${launchRes.status} ${launchRes.statusText}`,\n });\n return;\n }\n\n const kernelData = (await launchRes.json()) as Record<string, unknown>;\n\n // 6. Non-blocking: record kernelId in billing log.\n const kernelId = kernelData?.id as string | undefined;\n if (kernelId) {\n ctx.sink({\n username: ctx.username,\n action: 'launch',\n kernelSpec,\n kernelId,\n costTier,\n timestamp: launchTimestamp,\n });\n }\n\n res.status(201).json(kernelData);\n}\n\n/* -------- DELETE /api/kernels/{id} -------- */\nasync function handleKernelDelete(\n ctx: RouteContext,\n route: Extract<KernelRoute, { type: 'kernel_delete' }>,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(\n ctx.gen3Endpoint,\n `/api/kernels/${encodeURIComponent(route.kernelId)}`,\n );\n try {\n const upRes = await fetch(upstream, {\n method: 'DELETE',\n headers: ctx.ambassadorHeaders,\n });\n // 404 = already gone = success (idempotent terminate)\n if (!upRes.ok && upRes.status !== 404) {\n res.status(upRes.status).json({\n error: `Kernel terminate failed: ${upRes.status} ${upRes.statusText}`,\n });\n return;\n }\n } catch (err) {\n res.status(502).json({ error: `Kernel terminate failed: ${errMsg(err)}` });\n return;\n }\n\n // Non-blocking billing event (terminate)\n ctx.sink({\n username: ctx.username,\n action: 'terminate',\n kernelId: route.kernelId,\n costTier: 0, // actual cost determined from launch event by billing system\n timestamp: new Date().toISOString(),\n });\n\n res.status(204).end();\n}\n\n/* -------- GET /api/kernels/{id}/... passthrough -------- */\nasync function handleKernelPassthrough(\n ctx: RouteContext,\n route: Extract<KernelRoute, { type: 'kernel_passthrough' }>,\n res: NextApiResponse,\n): Promise<void> {\n const upstream = buildAmbassadorUrl(ctx.gen3Endpoint, route.kernelPath);\n try {\n const upRes = await fetch(upstream, {\n method: 'GET',\n headers: ctx.ambassadorHeaders,\n });\n res.status(upRes.status).json(await upRes.json().catch(() => ({})));\n } catch {\n res.status(502).json({ error: 'Upstream unreachable.' });\n }\n}\n\n/* ------------------------------------------------------------------ */\n/* Factory */\n/* ------------------------------------------------------------------ */\n\nconst ALLOWED_FENCE_URLS = [GEN3_FENCE_SERVICE, GEN3_FENCE_API];\n\nconst ALLOWED_JEG_URLS = [JEG_SERVICE_API, '/lw-workspace/proxy/jeg-panel'];\n\nexport function createKernelProxyHandler(config: KernelLifecycleProxyConfig) {\n const sink = config.billingSink ?? defaultBillingSink;\n const jegEnabled = config.jegEnabled === true;\n const idleKillDays = config.idleKillDays ?? 10;\n const maxKernelAgeDays = config.maxKernelAgeDays ?? 15;\n\n return async function kernelLifecycleProxyHandler(\n req: NextApiRequest,\n res: NextApiResponse,\n ): Promise<void> {\n const { gen3Endpoint, fenceUrl, kernelSpecPolicy } = config;\n\n if (fenceUrl && !ALLOWED_FENCE_URLS.includes(fenceUrl)) {\n res.status(503).json({ error: 'Fence service URL is misconfigured.' });\n return;\n }\n\n if (gen3Endpoint && !ALLOWED_JEG_URLS.includes(gen3Endpoint)) {\n res.status(503).json({ error: 'JEG service URL is misconfigured.' });\n return;\n }\n\n // --- Route resolution (done early so /api/status can short-circuit) ---\n const rawAction = req.query.action;\n const actionSegments: string[] = Array.isArray(rawAction)\n ? rawAction.filter((s): s is string => typeof s === 'string')\n : [];\n const route = resolveKernelRoute(req.method || '', actionSegments);\n\n // GET /api/status is the JEG feature-gate probe — always returns 200 with { enabled }.\n // This allows useGatewayConnection to detect whether JEG is configured before polling.\n if (route?.type === 'status') {\n res.setHeader('Cache-Control', 'no-store');\n res.status(200).json({ enabled: jegEnabled });\n return;\n }\n\n // All other routes are gated — silently return 503 so the UI fails gracefully.\n if (!jegEnabled) {\n res.setHeader('Cache-Control', 'no-store');\n res\n .status(503)\n .json({ error: 'JEG not configured for this deployment.' });\n return;\n }\n\n if (!gen3Endpoint) {\n res.status(503).json({ error: 'GEN3_ENDPOINT is not configured.' });\n return;\n }\n\n // --- Auth: host-injected extractor first, minimal fallback for dev/standalone ---\n const jwt = config.getToken\n ? config.getToken(req)\n : extractTokenFallback(req);\n\n if (!jwt) {\n res.status(401).json({ error: 'Authentication required.' });\n return;\n }\n\n if (!route) {\n res.status(404).json({ error: 'Route not found.' });\n return;\n }\n\n // Extract sub claim for REMOTE_USER — Ambassador already verified the signature.\n const claims = decodeJwtClaims(jwt);\n const rawUsername =\n claims?.sub ??\n claims?.preferred_username ??\n claims?.username ??\n 'unknown';\n const username: string =\n typeof rawUsername === 'string' ? rawUsername : 'unknown';\n\n // Strip CRLF to prevent HTTP header injection (defense-in-depth)\n const safeJwt = jwt.replace(/[\\r\\n]/g, '');\n const safeUsername = username.replace(/[\\r\\n]/g, '');\n\n const ambassadorHeaders: Record<string, string> = {\n Authorization: `Bearer ${safeJwt}`,\n REMOTE_USER: safeUsername,\n };\n\n // No-store for all control plane responses\n res.setHeader('Cache-Control', 'no-store');\n\n const ctx: RouteContext = {\n req,\n gen3Endpoint,\n fenceUrl,\n kernelSpecPolicy,\n ambassadorHeaders,\n jwt,\n username,\n sink,\n idleKillDays,\n maxKernelAgeDays,\n };\n\n switch (route.type) {\n case 'kernelspecs':\n return handleKernelSpecs(ctx, res);\n case 'kernels_list':\n return handleKernelsList(ctx, res);\n case 'reap':\n return handleReap(ctx, res);\n case 'kernel_launch':\n return handleKernelLaunch(ctx, res);\n case 'kernel_delete':\n return handleKernelDelete(ctx, route, res);\n case 'kernel_passthrough':\n return handleKernelPassthrough(ctx, route, res);\n default:\n res.status(404).json({ error: 'Route not matched.' });\n }\n };\n}\n","import type { NextApiRequest, NextApiResponse } from 'next';\nimport { createWorkspaceAssetsHandler } from '../server/workspaceAssetsHandler';\nimport { GEN3_COMMONS_NAME } from '@gen3/core';\n\nconst upstreamHandler = createWorkspaceAssetsHandler({\n // Route JupyterLite remote-mode kernel WebSocket traffic through revproxy's\n // /lw-workspace/proxy/ nginx block → ambassador-service (ExternalName → Emissary)\n // → JEG. Next.js API routes cannot handle WebSocket upgrades, so we must\n // bypass them and use the nginx path that has allow_upgrade + long timeouts.\n gatewayBaseUrl: '/lw-workspace/proxy/',\n});\n\nconst VECTIS_WORKSPACE_APP_NAME = 'Vectis Workspaces';\nconst VECTIS_FAVICON_URL = '/icons/Vectis_Logo_Colored_LightTheme.svg';\n\n/** Escape characters that are special inside an HTML text node / attribute. */\nfunction escapeHtml(text: string): string {\n return text\n .replace(/&/g, '&')\n .replace(/</g, '<')\n .replace(/>/g, '>')\n .replace(/\"/g, '"')\n .replace(/'/g, ''');\n}\n\n/**\n * Return the first value of a header that Node.js may (in rare edge cases)\n * expose as an array. `host` and `referer` are always strings in practice,\n * but this keeps the helper safe for any header name.\n */\nfunction firstHeader(value: string | string[] | undefined): string | undefined {\n if (Array.isArray(value)) return value[0];\n return value;\n}\n\nfunction resolveOrigin(req: NextApiRequest): {\n proto: string;\n host: string;\n} {\n const forwardedProto = firstHeader(req.headers['x-forwarded-proto']);\n const forwardedHost = firstHeader(req.headers['x-forwarded-host']);\n // `host` is always a single string per Node.js HTTP spec; firstHeader is\n // used for type-safety only.\n const hostHeader = firstHeader(req.headers.host);\n const refererHeader = firstHeader(req.headers.referer);\n\n let proto = (forwardedProto ?? '').trim();\n let host = (forwardedHost || hostHeader || '').trim();\n\n if (refererHeader) {\n try {\n const refererUrl = new URL(refererHeader);\n // Prefer referer origin when the host header dropped a non-default port.\n if (!host || !host.includes(':')) {\n host = refererUrl.host;\n }\n // Only fall back to referer protocol when nothing better is available.\n if (!proto) {\n proto = refererUrl.protocol.replace(':', '');\n }\n } catch {\n // Ignore malformed referer; keep header-derived values.\n }\n }\n\n return {\n proto: proto || 'http',\n host: host || 'localhost:30080',\n };\n}\n\nfunction injectVectisBranding(html: string, req: NextApiRequest): string {\n const isRemoteTierRequest =\n (Array.isArray(req.query.tier) ? req.query.tier[0] : req.query.tier) ===\n 'remote';\n\n // Resolve origin only when needed (remote tier).\n const absoluteRemoteBaseUrl = isRemoteTierRequest\n ? (() => {\n const { proto, host } = resolveOrigin(req);\n return { base: `${proto}://${host}/lw-workspace/proxy/`, proto, host };\n })()\n : null;\n\n const withConfig = html.replace(\n /(<script\\s+id=\"jupyter-config-data\"[^>]*>)([\\s\\S]*?)(<\\/script>)/,\n (_match, openTag: string, rawContent: string, closeTag: string) => {\n // Strip leading/trailing whitespace left by the template.\n const trimmed = rawContent.trim();\n // Verify the captured content looks like a JSON object before parsing.\n if (!trimmed.startsWith('{') || !trimmed.endsWith('}')) {\n console.error(\n '[vectis-branding] jupyter-config-data content is not a JSON object; skipping merge.',\n );\n return _match;\n }\n\n let existing: Record<string, unknown> = {};\n try {\n existing = JSON.parse(trimmed) as Record<string, unknown>;\n } catch (err) {\n console.error(\n '[vectis-branding] Failed to parse jupyter-config-data JSON; skipping merge.',\n err,\n );\n return _match;\n }\n\n const existingDisabled = Array.isArray(existing.disabledExtensions)\n ? (existing.disabledExtensions as string[])\n : [];\n const remoteDisabledExtensions = isRemoteTierRequest\n ? [...existingDisabled, '@jupyterlite/pyodide-kernel-extension:kernel']\n : existingDisabled;\n\n const merged: Record<string, unknown> = {\n ...existing,\n appName: GEN3_COMMONS_NAME,\n faviconUrl: VECTIS_FAVICON_URL,\n ...(remoteDisabledExtensions.length > 0\n ? {\n disabledExtensions: Array.from(new Set(remoteDisabledExtensions)),\n }\n : {}),\n ...(isRemoteTierRequest && absoluteRemoteBaseUrl\n ? {\n // Use an absolute URL so JupyterLite does not resolve WS endpoints\n // relative to /workspace-api/workspace-assets/remote/.\n remoteBaseUrl: absoluteRemoteBaseUrl.base,\n // Route all kernel ops through jeg-proxy so JupyterLite sees merged\n // Python3 (container) + JEG GPU kernelspecs. The handler routes\n // Python3 kernel launches/channels to the container; GPU kernel\n // launches are gated (403) with a message to use the Kernel Panel.\n remoteKernelsBaseUrl: `${absoluteRemoteBaseUrl.proto}://${absoluteRemoteBaseUrl.host}/lw-workspace/proxy/jeg-proxy`,\n fullThemesUrl:\n '/workspace-api/workspace-assets/remote/build/themes',\n }\n : {}),\n };\n return `${openTag}${JSON.stringify(merged)}${closeTag}`;\n },\n );\n\n // Escape the app name before placing it into the HTML title element.\n return withConfig.replace(\n /<title>[^<]*<\\/title>/,\n `<title>${escapeHtml(VECTIS_WORKSPACE_APP_NAME)}</title>`,\n );\n}\n\nfunction isHtmlResponse(res: NextApiResponse): boolean {\n const contentType = res.getHeader('content-type');\n if (typeof contentType === 'string') return contentType.includes('text/html');\n if (Array.isArray(contentType))\n return contentType.some((v) => v.includes('text/html'));\n return false;\n}\n\nexport default function handler(req: NextApiRequest, res: NextApiResponse) {\n const originalSend = res.send.bind(res);\n\n res.send = ((body: unknown) => {\n if (\n typeof body === 'string' &&\n isHtmlResponse(res) &&\n body.includes('id=\"jupyter-config-data\"') &&\n body.includes('<title>')\n ) {\n return originalSend(injectVectisBranding(body, req));\n }\n return originalSend(body);\n }) as typeof res.send;\n\n return upstreamHandler(req, res);\n}\n","import type { NextApiRequest, NextApiResponse } from 'next';\nimport { getCookie } from 'cookies-next';\n\n// Allowed path prefixes — keeps proxying scoped to the Jupyter Gateway API surface\nconst ALLOWED_PREFIXES = ['/api/kernels', '/api/sessions', '/api/kernelspecs'];\n\nfunction buildUpstreamPath(segments: string[]): string {\n const clean = segments\n .filter(Boolean)\n .map((s) => s.replace(/^\\/+|\\/+$/g, ''));\n\n if (clean.some((s) => s === '..' || s === '.')) {\n throw new Error('Invalid path segment');\n }\n\n return `/${clean.join('/')}`;\n}\n\nfunction isAllowedPath(path: string): boolean {\n return ALLOWED_PREFIXES.some(\n (prefix) => path === prefix || path.startsWith(`${prefix}/`),\n );\n}\n\nfunction buildQueryString(\n rawUrl: string | undefined,\n excludeKey: string,\n): string {\n if (!rawUrl) return '';\n const queryPart = rawUrl.split('?')[1];\n if (!queryPart) return '';\n\n const params = new URLSearchParams(queryPart);\n params.delete(excludeKey);\n\n const result = params.toString();\n return result ? `?${result}` : '';\n}\n\nfunction readBody(req: NextApiRequest): Promise<Buffer | undefined> {\n return new Promise((resolve, reject) => {\n if (!req.method || ['GET', 'HEAD'].includes(req.method.toUpperCase())) {\n resolve(undefined);\n return;\n }\n const chunks: Buffer[] = [];\n req.on('data', (chunk: Buffer | string) => {\n chunks.push(Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk));\n });\n req.on('end', () =>\n resolve(chunks.length ? Buffer.concat(chunks) : undefined),\n );\n req.on('error', reject);\n });\n}\n\nexport default async function handler(\n req: NextApiRequest,\n res: NextApiResponse,\n) {\n const gatewayUrl = process.env.JUPYTER_GATEWAY_URL;\n\n if (!gatewayUrl) {\n res.status(500).json({ error: 'JUPYTER_GATEWAY_URL is not configured' });\n return;\n }\n\n const gatewayBase = gatewayUrl.replace(/\\/+$/, '');\n\n const actionSegments = Array.isArray(req.query.action)\n ? req.query.action\n : req.query.action\n ? [req.query.action]\n : [];\n\n let upstreamPath: string;\n try {\n upstreamPath = buildUpstreamPath(actionSegments);\n } catch {\n res.status(400).json({ error: 'Invalid path' });\n return;\n }\n\n if (!isAllowedPath(upstreamPath)) {\n res.status(403).json({ error: 'Forbidden path' });\n return;\n }\n\n const queryString = buildQueryString(req.url, 'action');\n const targetUrl = `${gatewayBase}${upstreamPath}${queryString}`;\n\n const forwardHeaders = new Headers();\n for (const [key, value] of Object.entries(req.headers)) {\n if (!value) continue;\n const lower = key.toLowerCase();\n if (\n lower === 'host' ||\n lower === 'content-length' ||\n lower === 'transfer-encoding'\n )\n continue;\n forwardHeaders.set(key, Array.isArray(value) ? value.join(',') : value);\n }\n\n // Inject server-side JEG token — overrides any client-supplied auth header.\n // This ensures calls from JupyterLite's own serverconnection.js are also authenticated.\n if (process.env.NODE_ENV === 'development') {\n // NOTE: This cookie can only be accessed from the client side\n // in development mode. Otherwise, the cookie is set as httpOnly\n const accessToken = getCookie('credentials_token');\n if (accessToken) {\n forwardHeaders.set('Authorization', `Bearer ${accessToken}`);\n }\n }\n\n let body: Buffer | undefined;\n try {\n body = await readBody(req);\n } catch {\n res.status(500).json({ error: 'Failed to read request body' });\n return;\n }\n\n if (body) {\n forwardHeaders.set('content-length', String(body.byteLength));\n }\n\n let upstream: Response;\n try {\n upstream = await fetch(targetUrl, {\n method: req.method,\n headers: forwardHeaders,\n body: body ? new Uint8Array(body) : undefined,\n signal: AbortSignal.timeout(30_000),\n });\n } catch (err) {\n const isTimeout = err instanceof Error && err.name === 'TimeoutError';\n res.status(isTimeout ? 504 : 502).json({\n error: isTimeout ? 'Gateway timeout' : 'Gateway unreachable',\n });\n return;\n }\n\n res.status(upstream.status);\n upstream.headers.forEach((value, key) => {\n const lower = key.toLowerCase();\n if (\n lower === 'transfer-encoding' ||\n lower === 'content-type' ||\n lower === 'content-security-policy'\n )\n return;\n res.setHeader(key, value);\n });\n\n const upstreamContentType = upstream.headers.get('content-type') || '';\n const safeContentType = /html|xml|svg/i.test(upstreamContentType)\n ? 'text/plain; charset=utf-8'\n : upstreamContentType || 'application/octet-stream';\n res.setHeader('Content-Type', safeContentType);\n res.setHeader('X-Content-Type-Options', 'nosniff');\n res.setHeader('Content-Security-Policy', \"default-src 'none'; sandbox\");\n res.setHeader('Content-Disposition', 'attachment');\n\n if (upstream.body) {\n const reader = upstream.body.getReader();\n try {\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n res.write(value);\n }\n } finally {\n reader.releaseLock();\n }\n res.end();\n } else {\n res.end();\n }\n}\n\nexport const config = { api: { bodyParser: false } };\n","// Kernel lifecycle proxy — billing gate + Fence credential injection.\n// Browser never sees JEG URL or raw kernel spec names.\n// POST /kernels calls Fence /credentials/cdis first — if it fails, no kernel is launched.\n// getToken reuses this app's cookie extraction — no JWT reinvention.\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport { createKernelProxyHandler } from '../server/kernelLifecycleProxy';\nimport { getAccessToken } from '@gen3/frontend/server';\nimport { GEN3_FENCE_API } from '@gen3/core/server';\nimport { JEG_SERVICE_API } from '../constants';\nimport { GEN3_FENCE_SERVICE } from '@gen3/core';\n\nconst inCluster = Boolean(process.env.KUBERNETES_SERVICE_HOST);\nconst defaultGen3Endpoint = inCluster\n ? JEG_SERVICE_API\n : '/lw-workspace/proxy/jeg-panel';\nconst defaultFenceUrl = inCluster ? GEN3_FENCE_SERVICE : GEN3_FENCE_API;\n\nconst gen3Endpoint = process.env.JEG_SERVICE_API ?? defaultGen3Endpoint;\nconst fenceUrl = defaultFenceUrl;\n\nif (!gen3Endpoint) {\n console.warn(\n '[workspace-kernel] JEG_SERVICE_API is not set and not running in-cluster — kernel proxy will likely fail',\n );\n}\nif (!fenceUrl) {\n console.warn(\n '[workspace-kernel] FENCE_URL is not set and not running in-cluster — credential injection will likely fail',\n );\n}\n\nlet policy: Record<string, unknown> = {};\nif (process.env.KERNEL_SPEC_POLICY) {\n try {\n policy = JSON.parse(process.env.KERNEL_SPEC_POLICY);\n } catch (err) {\n throw new Error(\n `[workspace-kernel] KERNEL_SPEC_POLICY is not valid JSON: ${(err as Error).message}`,\n );\n }\n}\n\nconst upstreamHandler = createKernelProxyHandler({\n gen3Endpoint,\n fenceUrl,\n kernelSpecPolicy: policy,\n jegEnabled: process.env.ENABLE_JEG === 'true',\n getToken: (req) => {\n const token = getAccessToken(req.headers['cookie'] ?? '') ?? null;\n if (!token) {\n console.warn(\n '[workspace-kernel] No access token found in request cookies',\n );\n }\n return token;\n },\n});\n\nexport default async function handler(\n req: NextApiRequest,\n res: NextApiResponse,\n) {\n const action = Array.isArray(req.query.action) ? req.query.action : [];\n const isStatusPath = action[0] === 'api' && action[1] === 'status';\n try {\n await upstreamHandler(req, res);\n } catch (err) {\n console.error('[workspace-kernel] Upstream handler threw:', err);\n if (!res.headersSent) {\n res.status(502).json({ error: 'Bad gateway' });\n }\n return;\n }\n}\n\nexport const config = { api: { bodyParser: false } };\n","/**\n * createHatcheryProxyHandler — server-side Next.js API route handler for Hatchery\n * micro-container lifecycle (launch, terminate, status, options).\n *\n * Security properties:\n * - Strict allowlist: only /options, /status, /launch, /terminate are proxied.\n * - All other paths return 404 — Hatchery internals are never reachable.\n * - JWT forwarded as Bearer; user identity set as REMOTE_USER for server-side isolation.\n * - `id` query param sanitized against SAFE_ID_RE (SSRF and injection prevention).\n *\n * Token extraction:\n * Pass getToken to reuse the host app's existing cookie logic (strongly recommended).\n * In gen3-vectis this is getAccessToken from lib/auth/getLoginStatus.\n * Without getToken, a minimal Bearer/cookie fallback is used (dev/standalone only).\n * Ambassador performs RS256 verification before any request reaches Next.js.\n *\n * Usage (src/pages/api/workspace/hatchery/[...action].ts — generated by bin/init.mjs):\n * import { createHatcheryProxyHandler } from '@gen3/jupyter-workspaces/server';\n * import { getAccessToken } from '../../lib/auth/getLoginStatus';\n * export default createHatcheryProxyHandler({\n * hatcheryUrl: process.env.HATCHERY_URL,\n * getToken: (req) => getAccessToken(req.headers['cookie'] ?? '') ?? null,\n * });\n * export const config = { api: { bodyParser: false } };\n */\n\nimport type { NextApiRequest, NextApiResponse } from 'next';\nimport {\n createProxyRequest,\n decodeJwtClaims,\n extractTokenFallback,\n} from './utils';\n\nexport interface HatcheryProxyConfig {\n /** Internal URL of the Hatchery service, e.g. http://hatchery.hatchery.svc:8000 */\n hatcheryUrl: string | undefined;\n /**\n * Token extractor injected by the host application.\n * In gen3-vectis: `(req) => getAccessToken(req.headers['cookie'] ?? '') ?? null`\n * When omitted, a minimal Bearer-header/cookie fallback is used (dev/standalone only).\n * Ambassador has already done RS256 verification — this is extraction only.\n */\n getToken?: (req: NextApiRequest) => string | null;\n}\n\ntype HatcheryRoute =\n | { method: 'GET'; path: '/options' }\n | { method: 'GET'; path: '/status' }\n | { method: 'POST'; path: '/launch' }\n | { method: 'POST'; path: '/terminate' };\n\nconst SAFE_ID_RE = /^[a-zA-Z0-9]([a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?$/;\n\nfunction resolveHatcheryRoute(\n method: string,\n actionSegments: string[],\n): HatcheryRoute | null {\n const action = actionSegments[0] || '';\n const routes: Record<string, HatcheryRoute> = {\n 'GET:options': { method: 'GET', path: '/options' },\n 'GET:status': { method: 'GET', path: '/status' },\n 'POST:launch': { method: 'POST', path: '/launch' },\n 'POST:terminate': { method: 'POST', path: '/terminate' },\n };\n return routes[`${method}:${action}`] ?? null;\n}\n\nconst ALLOWED_HATCHERY_URLS = [\n '/lw-workspace',\n 'http://hatchery-service.gen3.svc.cluster.local',\n];\n\nexport function createHatcheryProxyHandler(config: HatcheryProxyConfig) {\n return async function hatcheryProxyHandler(\n req: NextApiRequest,\n res: NextApiResponse,\n ): Promise<void> {\n const hatcheryUrl = config.hatcheryUrl;\n\n if (!hatcheryUrl) {\n res.status(503).json({\n error: 'Hatchery service is not configured (HATCHERY_URL missing).',\n });\n return;\n }\n\n if (!ALLOWED_HATCHERY_URLS.includes(hatcheryUrl)) {\n res.status(503).json({ error: 'Hatchery service URL is misconfigured.' });\n return;\n }\n\n let parsedHatcheryUrl: URL;\n try {\n parsedHatcheryUrl = new URL(hatcheryUrl);\n } catch {\n res.status(503).json({ error: 'Hatchery service URL is misconfigured.' });\n return;\n }\n if (\n parsedHatcheryUrl.protocol !== 'http:' &&\n parsedHatcheryUrl.protocol !== 'https:'\n ) {\n res.status(503).json({ error: 'Hatchery service URL is misconfigured.' });\n return;\n }\n\n // --- Auth: host-injected extractor first, minimal fallback for dev/standalone ---\n const jwt = config.getToken\n ? config.getToken(req)\n : extractTokenFallback(req);\n if (!jwt) {\n res.status(401).json({ error: 'Authentication required.' });\n return;\n }\n\n // Validate JWT format to prevent injection attacks\n // JWT should be three base64url-encoded segments separated by dots\n const JWT_FORMAT_RE = /^[A-Za-z0-9_-]+\\.[A-Za-z0-9_-]+\\.[A-Za-z0-9_-]+$/;\n if (!JWT_FORMAT_RE.test(jwt)) {\n console.error('[hatcheryProxy] Invalid JWT format detected');\n res.status(401).json({ error: 'Invalid authentication token format.' });\n return;\n }\n\n // Additional length check to prevent extremely long tokens\n if (jwt.length > 8192) {\n console.error('[hatcheryProxy] JWT exceeds maximum length');\n res.status(401).json({ error: 'Authentication token too long.' });\n return;\n }\n\n // Extract sub claim for REMOTE_USER — Ambassador already verified the signature.\n const claims = decodeJwtClaims(jwt);\n const rawUsername =\n claims?.sub ?? claims?.preferred_username ?? claims?.username;\n const username: string | undefined =\n typeof rawUsername === 'string' ? rawUsername : undefined;\n if (!username) {\n res\n .status(401)\n .json({ error: 'Unable to determine username from token.' });\n return;\n }\n // Strip CRLF to prevent HTTP header injection (defense-in-depth)\n const safeJwt = jwt.replace(/[\\r\\n]/g, '');\n const safeUsername = username.replace(/[\\r\\n]/g, '');\n\n // --- Route resolution ---\n const actionSegments = (req.query.action as string[]) || [];\n const route = resolveHatcheryRoute(req.method || '', actionSegments);\n if (!route) {\n res.status(404).json({ error: 'Route not found.' });\n return;\n }\n\n // --- Sanitize launch/terminate id param (SSRF prevention) ---\n let queryString = '';\n if (route.path === '/launch' || route.path === '/terminate') {\n const id = (req.query.id as string) || '';\n if (id) {\n if (!SAFE_ID_RE.test(id)) {\n res.status(400).json({ error: 'Invalid container identifier.' });\n return;\n }\n queryString = `?id=${encodeURIComponent(id)}`;\n }\n } else if (route.path === '/status' || route.path === '/options') {\n // Pass id through safely for status/options\n const id = (req.query.id as string) || '';\n if (id) {\n if (!SAFE_ID_RE.test(id)) {\n res.status(400).json({ error: 'Invalid container identifier.' });\n return;\n }\n queryString = `?id=${encodeURIComponent(id)}`;\n }\n }\n\n const hatcheryBase = `${parsedHatcheryUrl.origin}${parsedHatcheryUrl.pathname.replace(/\\/$/, '')}`;\n const targetUrl = `${hatcheryBase}${route.path}${queryString}`;\n\n await createProxyRequest({\n req,\n res,\n targetUrl,\n method: route.method,\n extraHeaders: {\n Authorization: `Bearer ${safeJwt}`,\n REMOTE_USER: safeUsername,\n remote_user: safeUsername,\n },\n // Hatchery doesn't need a body for GET routes\n forwardBody: route.method === 'POST',\n });\n };\n}\n","// Hatchery proxy — strict allowlist: /options, /status, /launch, /terminate\n// Injects Authorization + REMOTE_USER headers; sanitizes id param (SSRF prevention).\n// getToken reuses this app's cookie extraction — no JWT reinvention.\nimport { createHatcheryProxyHandler } from '../server/hatcheryProxy';\nimport { getAccessToken } from '@gen3/frontend/server';\nimport type { NextApiRequest, NextApiResponse } from 'next';\n\nconst defaultHatcheryUrl = process.env.KUBERNETES_SERVICE_HOST\n ? 'http://hatchery-service.gen3.svc.cluster.local'\n : '/lw-workspace';\n\nconst upstreamHandler = createHatcheryProxyHandler({\n hatcheryUrl: defaultHatcheryUrl,\n getToken: (req) => getAccessToken(req.headers['cookie'] ?? '') ?? null,\n});\n\nfunction decodeJwtUsername(jwt: string): string {\n try {\n const payload = jwt.split('.')[1];\n const claims = JSON.parse(\n Buffer.from(payload, 'base64url').toString('utf8'),\n ) as Record<string, unknown>;\n const raw = claims.sub ?? claims.preferred_username ?? claims.username;\n return typeof raw === 'string'\n ? raw\n : `<non-string:${JSON.stringify(raw)}>`;\n } catch {\n return '<decode-error>';\n }\n}\n\nexport default async function handler(\n req: NextApiRequest,\n res: NextApiResponse,\n) {\n const action = req.query.action?.[0];\n\n // Intercept res.send to capture response body for logging\n let capturedBody = '';\n const originalSend = res.send.bind(res) as typeof res.send;\n res.send = (body: unknown) => {\n capturedBody = (\n typeof body === 'string' ? body : JSON.stringify(body)\n ).slice(0, 300);\n return originalSend(body);\n };\n\n await upstreamHandler(req, res);\n}\n\nexport const config = { api: { bodyParser: false } };\n"],"names":["GEN3_HATCHERY_API","GEN3_WORKSPACE_API","process","env","GEN3_KERNEL_API","GEN3_API","JEG_GATEWAY_API","JEG_SERVICE_API","MAX_FILE_SIZE_BYTES","ALLOWED_TIERS","Set","SAFE_SEGMENT_RE","MIME_TYPES","REMOTE_DISABLED_EXTENSIONS","ASSETS_ROOT_PATH","JUPYTER_ASSETS_ROOT_PATH","defaultAssetRoot","startsWith","nodePath","join","cwd","resolveOrigin","req","forwardedProto","Array","isArray","headers","forwardedHost","hostHeader","host","refererHeader","referer","resolvedHost","trim","resolvedProto","String","refererUrl","URL","includes","protocol","replace","proto","injectRemoteConfig","html","gatewayBaseUrl","disabledExtensions","branding","appName","faviconUrl","absoluteGatewayBase","accessToken","undefined","NODE_ENV","getCookie","configData","remoteBaseUrl","remoteToken","fullThemesUrl","result","_match","openTag","existingJson","closeTag","existing","JSON","parse","merged","combined","stringify","injectBranding","error","Error","console","log","message","createWorkspaceAssetsHandler","options","JUPYTER_GATEWAY_BASE_URL","assetRoot","additionalDisabledExtensions","walkDir","dir","set","entry","fs","readdirSync","withFileTypes","full","name","isDirectory","add","allowedFilesByTier","free","remote","tier","resolve","handler","res","path","pathSegments","query","has","status","end","segments","tierRoot","safeSegments","seg","test","push","basename","allowedFiles","candidatePath","candidateIndex","filePath","ext","extname","toLowerCase","contentType","isBuildAsset","setHeader","cookies","encodeURIComponent","isRemoteLabHtml","readFileSync","injected","send","isHtmlResponse","stat","statSync","size","stream","createReadStream","on","pipe","DEFAULT_WORKSPACE_ROUTES","withJupyterWorkspaces","nextConfig","workspaceRoutes","transpilePackages","filter","pkg","webpack","config","ctx","alias","react","dirname","require","rewrites","isDev","gatewayProxyUrl","GATEWAY_PROXY_URL","gatewayRewrite","source","destination","beforeFiles","coopCoepHeaders","map","route","key","value","extractTokenFallback","auth","slice","cookie","m","match","decodeURIComponent","MAX_JWT_LENGTH","decodeJwtClaims","jwt","length","parts","split","padded","padEnd","Math","ceil","Buffer","from","toString","createProxyRequest","targetUrl","method","extraHeaders","forwardBody","body","buf","bufferBody","err","statusCode","msg","json","upRes","fetch","signal","AbortSignal","timeout","get","errBody","text","catch","responseBody","MAX_BODY_BYTES","Promise","reject","chunks","total","chunk","destroy","Object","assign","concat","defaultBillingSink","event","stdout","write","type","EMPTY_FENCE_CREDS","key_id","api_key","fetchFenceCreds","fenceUrl","parsedFenceUrl","response","fetchFence","endpoint","Authorization","data","filterAndAnnotateSpecs","raw","policy","allowedSpecs","costPerHour","displayNames","nodeType","filteredSpecs","specName","rawSpec","kernelspecs","spec","display_name","metadata","filteredDefault","default","readBody","buildAmbassadorUrl","gen3Endpoint","kernelPath","base","parsed","origin","pathname","KERNEL_ID_RE","SIMPLE_ROUTES","Map","resolveKernelRoute","actionSegments","seg1","seg2","kernelId","rest","errMsg","handleKernelSpecs","upstream","ambassadorHeaders","ok","statusText","rawSpecs","kernelSpecPolicy","handleKernelsList","handleReap","listUpstream","kernelList","listRes","now","Date","idleKillMins","idleKillDays","maxAgeMins","maxKernelAgeDays","reaped","errors","kernel","id","lastActivity","last_activity","getTime","idleMins","Infinity","deleteUpstream","sink","username","action","costTier","timestamp","toISOString","handleKernelLaunch","fenceCreds","rawBody","launchBody","kernelSpec","enrichedBody","GEN3_API_KEY_ID","GEN3_API_KEY_SECRET","NAMESPACE","GEN3_ENDPOINT","launchTimestamp","launchRes","kernelData","handleKernelDelete","handleKernelPassthrough","ALLOWED_FENCE_URLS","GEN3_FENCE_SERVICE","GEN3_FENCE_API","ALLOWED_JEG_URLS","createKernelProxyHandler","billingSink","jegEnabled","kernelLifecycleProxyHandler","rawAction","s","enabled","getToken","claims","rawUsername","sub","preferred_username","safeJwt","safeUsername","REMOTE_USER","upstreamHandler","VECTIS_WORKSPACE_APP_NAME","VECTIS_FAVICON_URL","escapeHtml","firstHeader","injectVectisBranding","isRemoteTierRequest","absoluteRemoteBaseUrl","withConfig","rawContent","trimmed","endsWith","existingDisabled","remoteDisabledExtensions","GEN3_COMMONS_NAME","remoteKernelsBaseUrl","getHeader","some","v","originalSend","bind","ALLOWED_PREFIXES","buildUpstreamPath","clean","Boolean","isAllowedPath","prefix","buildQueryString","rawUrl","excludeKey","queryPart","params","URLSearchParams","delete","toUpperCase","isBuffer","gatewayUrl","JUPYTER_GATEWAY_URL","gatewayBase","upstreamPath","queryString","url","forwardHeaders","Headers","entries","lower","byteLength","Uint8Array","isTimeout","forEach","upstreamContentType","safeContentType","reader","getReader","done","read","releaseLock","inCluster","KUBERNETES_SERVICE_HOST","defaultGen3Endpoint","defaultFenceUrl","warn","KERNEL_SPEC_POLICY","ENABLE_JEG","token","getAccessToken","headersSent","SAFE_ID_RE","resolveHatcheryRoute","routes","ALLOWED_HATCHERY_URLS","createHatcheryProxyHandler","hatcheryProxyHandler","hatcheryUrl","parsedHatcheryUrl","JWT_FORMAT_RE","hatcheryBase","remote_user","defaultHatcheryUrl","capturedBody"],"mappings":"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"}
|