From 2f58ed384c42ce60fd0b7ab945ffffe3578021be Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Fri, 20 Jun 2025 14:28:56 -0700 Subject: [PATCH 01/32] stagehand migration v1 --- stagehand/cli.js | 2 + stagehand/config.d.ts | 85 ++++++ stagehand/index.d.ts | 6 + stagehand/index.js | 2 + stagehand/package-lock.json | 152 ++++++++++- stagehand/package.json | 6 +- stagehand/src/config.ts | 161 ++++++++++++ stagehand/src/context.ts | 70 +++++ stagehand/src/index.ts | 151 +++++++++-- stagehand/src/program.ts | 59 +++++ stagehand/src/server.ts | 329 ++--------------------- stagehand/src/sessionManager.ts | 409 +++++++++++++++++++++++++++++ stagehand/src/{ => tools}/tools.ts | 4 +- stagehand/src/tools/utils.ts | 3 + stagehand/src/transport.ts | 118 +++++++++ 15 files changed, 1202 insertions(+), 355 deletions(-) create mode 100755 stagehand/cli.js create mode 100644 stagehand/config.d.ts create mode 100644 stagehand/index.d.ts create mode 100644 stagehand/index.js create mode 100644 stagehand/src/config.ts create mode 100644 stagehand/src/context.ts create mode 100644 stagehand/src/program.ts create mode 100644 stagehand/src/sessionManager.ts rename stagehand/src/{ => tools}/tools.ts (98%) create mode 100644 stagehand/src/tools/utils.ts create mode 100644 stagehand/src/transport.ts diff --git a/stagehand/cli.js b/stagehand/cli.js new file mode 100755 index 0000000..9610f3e --- /dev/null +++ b/stagehand/cli.js @@ -0,0 +1,2 @@ +#!/usr/bin/env node +import './dist/program.js'; \ No newline at end of file diff --git a/stagehand/config.d.ts b/stagehand/config.d.ts new file mode 100644 index 0000000..4950123 --- /dev/null +++ b/stagehand/config.d.ts @@ -0,0 +1,85 @@ +import type { Cookie } from "playwright-core"; + +export type Config = { + /** + * The Browserbase API Key to use + */ + browserbaseApiKey?: string; + /** + * The Browserbase Project ID to use + */ + browserbaseProjectId?: string; + /** + * Whether or not to use Browserbase proxies + * https://docs.browserbase.com/features/proxies + * + * @default false + */ + proxies?: boolean; + /** + * Use advanced stealth mode. Only available to Browserbase Scale Plan users. + * + * @default false + */ + advancedStealth?: boolean; + /** + * Potential Browserbase Context to use + * Would be a context ID + */ + context?: { + /** + * The ID of the context to use + */ + contextId?: string; + /** + * Whether or not to persist the context + * + * @default true + */ + persist?: boolean; + }; + /** + * + */ + viewPort?: { + /** + * The width of the browser + */ + browserWidth?: number; + /** + * The height of the browser + */ + browserHeight?: number; + }; + /** + * Cookies to inject into the Browserbase context + * Format: Array of cookie objects with name, value, domain, and optional path, expires, httpOnly, secure, sameSite + */ + cookies?: Cookie[]; + /** + * Whether or not to port to a server + * + */ + server?: { + /** + * The port to listen on for SSE or MCP transport. + */ + port?: number; + /** + * The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces. + */ + host?: string; + }; + tools?: { + /** + * Configuration for the browser_take_screenshot tool. + */ + browserbase_take_screenshot?: { + /** + * Whether to disable base64-encoded image responses to the clients that + * don't support binary data or prefer to save on tokens. + */ + omitBase64?: boolean; + } + } +}; \ No newline at end of file diff --git a/stagehand/index.d.ts b/stagehand/index.d.ts new file mode 100644 index 0000000..f499530 --- /dev/null +++ b/stagehand/index.d.ts @@ -0,0 +1,6 @@ +import type { Server } from '@modelcontextprotocol/sdk/server/index.js'; + +import type { Config } from './config'; + +export declare function createServer(config?: Config): Promise; +export {}; \ No newline at end of file diff --git a/stagehand/index.js b/stagehand/index.js new file mode 100644 index 0000000..cecbc9e --- /dev/null +++ b/stagehand/index.js @@ -0,0 +1,2 @@ +import { createServer } from './dist/index.js'; +export default { createServer }; \ No newline at end of file diff --git a/stagehand/package-lock.json b/stagehand/package-lock.json index e5b1dab..cc0ac3a 100644 --- a/stagehand/package-lock.json +++ b/stagehand/package-lock.json @@ -11,9 +11,9 @@ "dependencies": { "@browserbasehq/sdk": "^2.0.0", "@browserbasehq/stagehand": "^2.0.0", - "@modelcontextprotocol/sdk": "^1.0.3", - "@modelcontextprotocol/server-stagehand": "file:", - "@playwright/test": "^1.49.0" + "@modelcontextprotocol/sdk": "^1.13.0", + "@playwright/test": "^1.49.0", + "commander": "^14.0.0" }, "bin": { "mcp-server-stagehand": "dist/index.js" @@ -75,17 +75,19 @@ } }, "node_modules/@modelcontextprotocol/sdk": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.6.1.tgz", - "integrity": "sha512-oxzMzYCkZHMntzuyerehK3fV6A2Kwh5BD6CGEJSVDU2QNEhfLOptf2X7esQgaHZXHZY0oHmMsOtIDLP71UJXgA==", + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.13.0.tgz", + "integrity": "sha512-P5FZsXU0kY881F6Hbk9GhsYx02/KgWK1DYf7/tyE/1lcFKhDYPQR9iYjhQXJn+Sg6hQleMo3DB7h7+p4wgp2Lw==", "license": "MIT", "dependencies": { + "ajv": "^6.12.6", "content-type": "^1.0.5", "cors": "^2.8.5", + "cross-spawn": "^7.0.5", "eventsource": "^3.0.2", "express": "^5.0.1", "express-rate-limit": "^7.5.0", - "pkce-challenge": "^4.1.0", + "pkce-challenge": "^5.0.0", "raw-body": "^3.0.0", "zod": "^3.23.8", "zod-to-json-schema": "^3.24.1" @@ -94,10 +96,6 @@ "node": ">=18" } }, - "node_modules/@modelcontextprotocol/server-stagehand": { - "resolved": "", - "link": true - }, "node_modules/@playwright/test": { "version": "1.51.0", "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.51.0.tgz", @@ -169,6 +167,22 @@ "node": ">= 8.0.0" } }, + "node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "license": "MIT", + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, "node_modules/asynckit": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", @@ -318,6 +332,15 @@ "node": ">= 0.8" } }, + "node_modules/commander": { + "version": "14.0.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-14.0.0.tgz", + "integrity": "sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==", + "license": "MIT", + "engines": { + "node": ">=20" + } + }, "node_modules/concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -377,6 +400,20 @@ "node": ">= 0.10" } }, + "node_modules/cross-spawn": { + "version": "7.0.6", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", + "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", + "license": "MIT", + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, "node_modules/dateformat": { "version": "4.6.3", "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-4.6.3.tgz", @@ -649,6 +686,18 @@ "license": "MIT", "peer": true }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "license": "MIT" + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "license": "MIT" + }, "node_modules/fast-redact": { "version": "3.5.0", "resolved": "https://registry.npmjs.org/fast-redact/-/fast-redact-3.5.0.tgz", @@ -1022,6 +1071,12 @@ "integrity": "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==", "license": "MIT" }, + "node_modules/isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", + "license": "ISC" + }, "node_modules/joycon": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/joycon/-/joycon-3.1.1.tgz", @@ -1032,6 +1087,12 @@ "node": ">=10" } }, + "node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "license": "MIT" + }, "node_modules/math-intrinsics": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", @@ -1270,6 +1331,15 @@ "node": ">=0.10.0" } }, + "node_modules/path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/path-parse": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", @@ -1352,9 +1422,9 @@ "peer": true }, "node_modules/pkce-challenge": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/pkce-challenge/-/pkce-challenge-4.1.0.tgz", - "integrity": "sha512-ZBmhE1C9LcPoH9XZSdwiPtbPHZROwAnMy+kIFQVrnMCxY4Cudlz3gBOpzilgc0jOgRaiT3sIWfpMomW2ar2orQ==", + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/pkce-challenge/-/pkce-challenge-5.0.0.tgz", + "integrity": "sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==", "license": "MIT", "engines": { "node": ">=16.20.0" @@ -1431,6 +1501,15 @@ "once": "^1.3.1" } }, + "node_modules/punycode": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", + "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/qs": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/qs/-/qs-6.13.0.tgz", @@ -1669,6 +1748,27 @@ "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", "license": "ISC" }, + "node_modules/shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "license": "MIT", + "dependencies": { + "shebang-regex": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/shelljs": { "version": "0.8.5", "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.5.tgz", @@ -1899,6 +1999,15 @@ "node": ">= 0.8" } }, + "node_modules/uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "license": "BSD-2-Clause", + "dependencies": { + "punycode": "^2.1.0" + } + }, "node_modules/utils-merge": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", @@ -1942,6 +2051,21 @@ "webidl-conversions": "^3.0.0" } }, + "node_modules/which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "license": "ISC", + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "node-which": "bin/node-which" + }, + "engines": { + "node": ">= 8" + } + }, "node_modules/wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", diff --git a/stagehand/package.json b/stagehand/package.json index 9b8f327..94b69f8 100644 --- a/stagehand/package.json +++ b/stagehand/package.json @@ -21,9 +21,9 @@ "dependencies": { "@browserbasehq/sdk": "^2.0.0", "@browserbasehq/stagehand": "^2.0.0", - "@modelcontextprotocol/sdk": "^1.0.3", - "@modelcontextprotocol/server-stagehand": "file:", - "@playwright/test": "^1.49.0" + "@modelcontextprotocol/sdk": "^1.13.0", + "@playwright/test": "^1.49.0", + "commander": "^14.0.0" }, "devDependencies": { "shx": "^0.3.4", diff --git a/stagehand/src/config.ts b/stagehand/src/config.ts new file mode 100644 index 0000000..be94737 --- /dev/null +++ b/stagehand/src/config.ts @@ -0,0 +1,161 @@ +import os from 'os'; +import fs from 'fs'; +import path from 'path'; +import { sanitizeForFilePath } from './tools/utils.js'; +import type { Cookie } from "playwright-core"; + +export type ToolCapability = 'core' | string; + +export interface Config { + browserbaseApiKey?: string; + browserbaseProjectId?: string; + server?: { + port?: number; + host?: string; + }; + proxies?: boolean; + advancedStealth?: boolean; + context?: { + contextId?: string; + persist?: boolean; + }; + viewPort?: { + browserWidth?: number; + browserHeight?: number; + }; + cookies?: Cookie[]; +} + +// Define Command Line Options Structure +export type CLIOptions = { + browserbaseApiKey?: string; + browserbaseProjectId?: string; + proxies?: boolean; + advancedStealth?: boolean; + contextId?: string; + persist?: boolean; + port?: number; + host?: string; + cookies?: Cookie[]; + browserWidth?: number; + browserHeight?: number; +}; + +// Default Configuration Values +const defaultConfig: Config = { + browserbaseApiKey: process.env.BROWSERBASE_API_KEY, + browserbaseProjectId: process.env.BROWSERBASE_PROJECT_ID, + proxies: false, + server: { + port: undefined, + host: undefined, + }, + viewPort: { + browserWidth: 1024, + browserHeight: 768, + }, + cookies: undefined, +}; + +// Resolve final configuration by merging defaults, file config, and CLI options +export async function resolveConfig(cliOptions: CLIOptions): Promise { + const cliConfig = await configFromCLIOptions(cliOptions); + // Order: Defaults < File Config < CLI Overrides + const mergedConfig = mergeConfig(defaultConfig, cliConfig); + + // --- Add Browserbase Env Vars --- + // Ensure env vars are read *after* dotenv potentially runs (in index.ts) + if (!mergedConfig.browserbaseApiKey) { + mergedConfig.browserbaseApiKey = process.env.BROWSERBASE_API_KEY; + } + if (!mergedConfig.browserbaseProjectId) { + mergedConfig.browserbaseProjectId = process.env.BROWSERBASE_PROJECT_ID; + } + // -------------------------------- + + // Basic validation for Browserbase keys + if (!mergedConfig.browserbaseApiKey) { + console.warn("Warning: BROWSERBASE_API_KEY environment variable not set."); + } + if (!mergedConfig.browserbaseProjectId) { + console.warn("Warning: BROWSERBASE_PROJECT_ID environment variable not set."); + } + + return mergedConfig; +} + +// Create Config structure based on CLI options +export async function configFromCLIOptions(cliOptions: CLIOptions): Promise { + return { + browserbaseApiKey: cliOptions.browserbaseApiKey, + browserbaseProjectId: cliOptions.browserbaseProjectId, + server: { + port: cliOptions.port, + host: cliOptions.host, + }, + proxies: cliOptions.proxies, + context: { + contextId: cliOptions.contextId, + persist: cliOptions.persist, + }, + viewPort: { + browserWidth: cliOptions.browserWidth, + browserHeight: cliOptions.browserHeight, + }, + advancedStealth: cliOptions.advancedStealth, + cookies: cliOptions.cookies, + }; +} + +// Create an output file path within the configured output directory +export async function outputFile(config: Config, name: string): Promise { + const outputDir = os.tmpdir(); + await fs.promises.mkdir(outputDir, { recursive: true }); + const sanitizedName = sanitizeForFilePath(name); + return path.join(outputDir, sanitizedName); +} + +// Helper function to merge config objects, excluding undefined values +function pickDefined(obj: T | undefined): Partial { + if (!obj) return {}; + return Object.fromEntries( + Object.entries(obj).filter(([_, v]) => v !== undefined) + ) as Partial; +} + +// Merge two configuration objects (overrides takes precedence) +function mergeConfig(base: Config, overrides: Config): Config { + const baseFiltered = pickDefined(base); + const overridesFiltered = pickDefined(overrides); + + // Create the result object + const result = { ...baseFiltered } as Config; + + // For each property in overrides + for (const [key, value] of Object.entries(overridesFiltered)) { + if (key === 'context' && value && result.context) { + // Special handling for context object to ensure deep merge + result.context = { + ...result.context, + ...(value as Config['context']) + }; + } else if ( + value && + typeof value === 'object' && + !Array.isArray(value) && + result[key as keyof Config] && + typeof result[key as keyof Config] === 'object' + ) { + // Deep merge for other nested objects + result[key as keyof Config] = { + ...(result[key as keyof Config] as object), + ...value + } as any; + } else { + // Simple override for primitives, arrays, etc. + result[key as keyof Config] = value as any; + } + } + + return result; +} \ No newline at end of file diff --git a/stagehand/src/context.ts b/stagehand/src/context.ts new file mode 100644 index 0000000..01631af --- /dev/null +++ b/stagehand/src/context.ts @@ -0,0 +1,70 @@ +import { Stagehand } from "@browserbasehq/stagehand"; +import { Server } from "@modelcontextprotocol/sdk/server/index.js"; +import type { Config } from "../config.js"; +import { CallToolResult } from "@modelcontextprotocol/sdk/types.js"; +import { handleToolCall } from "./tools/tools.js"; +import { listResources, readResource } from "./resources.js"; +import { + ensureLogDirectory, + setupLogRotation, + registerExitHandlers, + scheduleLogRotation, + setServerInstance, + log +} from "./logging.js"; + +export class Context { + private stagehand: Stagehand; + private server: Server; + private config: Config; + + constructor(server: Server, config: Config) { + this.server = server; + this.config = config; + + // Initialize logging system + setServerInstance(server); + ensureLogDirectory(); + setupLogRotation(); + registerExitHandlers(); + scheduleLogRotation(); + + // Initialize Stagehand + this.stagehand = new Stagehand({ + env: "BROWSERBASE", + logger: (logLine) => { + log(`Stagehand: ${logLine.message}`, 'info'); + }, + }); + } + + async run(tool: any, args: any): Promise { + try { + log(`Executing tool: ${tool.name} with args: ${JSON.stringify(args)}`, 'info'); + const result = await handleToolCall(tool.name, args, this.stagehand); + log(`Tool ${tool.name} completed successfully`, 'info'); + return result; + } catch (error) { + const errorMessage = error instanceof Error ? error.message : String(error); + log(`Tool ${tool.name} failed: ${errorMessage}`, 'error'); + throw error; + } + } + + listResources() { + return listResources(); + } + + readResource(uri: string) { + return readResource(uri); + } + + async close() { + try { + await this.stagehand.close(); + log('Stagehand context closed successfully', 'info'); + } catch (error) { + log(`Error closing Stagehand context: ${error}`, 'error'); + } + } +} \ No newline at end of file diff --git a/stagehand/src/index.ts b/stagehand/src/index.ts index 74a35fe..f7e977e 100644 --- a/stagehand/src/index.ts +++ b/stagehand/src/index.ts @@ -1,27 +1,128 @@ -#!/usr/bin/env node - -import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js"; -import { createServer } from "./server.js"; -import { ensureLogDirectory, registerExitHandlers, scheduleLogRotation, setupLogRotation } from "./logging.js"; - -// Run setup for logging -ensureLogDirectory(); -setupLogRotation(); -scheduleLogRotation(); -registerExitHandlers(); - -// Run the server -async function runServer() { - const server = createServer(); - const transport = new StdioServerTransport(); - await server.connect(transport); - server.sendLoggingMessage({ - level: "info", - data: "Stagehand MCP server is ready to accept requests", - }); -} +import dotenv from "dotenv"; +dotenv.config(); + +import { Config } from "../config.js"; + +import { Server } from "@modelcontextprotocol/sdk/server/index.js"; +import { CallToolRequestSchema, ListResourcesRequestSchema, ListToolsRequestSchema, ReadResourceRequestSchema } from "@modelcontextprotocol/sdk/types.js"; +import { z } from "zod"; +import { zodToJsonSchema } from "zod-to-json-schema"; +import { Context } from "./context.js"; +import { TOOLS } from "./tools/tools.js"; -runServer().catch((error) => { - const errorMsg = error instanceof Error ? error.message : String(error); - console.error(errorMsg); +// Environment variables configuration +const requiredEnvVars = { + BROWSERBASE_API_KEY: process.env.BROWSERBASE_API_KEY, + BROWSERBASE_PROJECT_ID: process.env.BROWSERBASE_PROJECT_ID, +}; + +// Validate required environment variables +Object.entries(requiredEnvVars).forEach(([name, value]) => { + if (!value) throw new Error(`${name} environment variable is required`); }); + +export async function createServer(config: Config): Promise { + // Create the server + const server = new Server( + { name: "mcp-server-browserbase", version: "0.5.1" }, + { + capabilities: { + resources: { list: true, read: true }, + tools: { list: true, call: true }, + prompts: { list: true, get: true }, + notifications: { resources: { list_changed: true } }, + }, + } + ); + + // Create the context, passing server instance and config + const context = new Context(server, config); + + const tools: any[] = [ + ...TOOLS, + ]; + + const toolsMap = new Map(tools.map(tool => [tool.schema.name, tool])); + // --- Setup Request Handlers --- + + server.setRequestHandler(ListResourcesRequestSchema, async () => { + return { resources: context.listResources() }; + }); + + server.setRequestHandler(ReadResourceRequestSchema, async (request) => { + try { + const resourceContent = context.readResource(request.params.uri.toString()); + return { contents: [resourceContent] }; + } catch (error) { + // Keep this error log + console.error(`Error reading resource via context: ${error}`); + throw error; + } + }); + + server.setRequestHandler(ListToolsRequestSchema, async () => { + return { + tools: tools.map(tool => { + let finalInputSchema; + // Check if inputSchema is a Zod schema before converting + if (tool.schema.inputSchema instanceof z.Schema) { + // Add type assertion to help compiler + finalInputSchema = zodToJsonSchema(tool.schema.inputSchema as any); + } else if (typeof tool.schema.inputSchema === 'object' && tool.schema.inputSchema !== null) { + // Assume it's already a valid JSON schema object + finalInputSchema = tool.schema.inputSchema; + } else { + // Fallback or error handling if schema is neither + // Keep this error log + console.error(`Warning: Tool '${tool.schema.name}' has an unexpected inputSchema type.`); + finalInputSchema = { type: "object" }; // Default to empty object schema + } + + return { + name: tool.schema.name, + description: tool.schema.description, + inputSchema: finalInputSchema, + }; + }), + }; + }); + + server.setRequestHandler(CallToolRequestSchema, async (request) => { + const logError = (message: string) => { + // Ensure error logs definitely go to stderr + process.stderr.write(`[server.ts Error] ${new Date().toISOString()} ${message}\\n`); + }; + + // Use the map built from the passed-in tools + const tool = toolsMap.get(request.params.name); + + if (!tool) { + // Use the explicit error logger + logError(`Tool "${request.params.name}" not found.`); + // Return a simplified error object + return { content: [{ type: 'text', text: `Tool "${request.params.name}" not found` }], isError: true }; + } + + try { + // Delegate execution to the context + const result = await context.run(tool, request.params.arguments ?? {}); + return result; + } catch (error) { + // Use the explicit error logger + const errorMessage = error instanceof Error ? error.message : String(error); + logError(`Error running tool ${request.params.name} via context: ${errorMessage}`); + logError(`Original error stack (if available): ${error instanceof Error ? error.stack : 'N/A'}`); // Log stack trace + // Return a simplified error object + return { content: [{ type: 'text', text: `Failed to run tool '${request.params.name}': ${errorMessage}` }], isError: true }; + } + }); + + // Wrap server close to also close context + const originalClose = server.close.bind(server); + server.close = async () => { + await originalClose(); + }; + + // Return the configured server instance + return server; +} \ No newline at end of file diff --git a/stagehand/src/program.ts b/stagehand/src/program.ts new file mode 100644 index 0000000..6b65ec0 --- /dev/null +++ b/stagehand/src/program.ts @@ -0,0 +1,59 @@ +import { program } from 'commander'; +import * as fs from 'fs'; +import * as path from 'path'; +import { fileURLToPath } from 'url'; + +import { createServer } from './index.js'; +import { ServerList } from './server.js'; + +import { startHttpTransport, startStdioTransport } from './transport.js'; + +import { resolveConfig } from './config.js'; + +// Determine the directory of the current module +const __filename = fileURLToPath(import.meta.url); +const __dirname = path.dirname(__filename); + +// Load package.json using fs +const packageJSONPath = path.resolve(__dirname, '../package.json'); +const packageJSONBuffer = fs.readFileSync(packageJSONPath); +const packageJSON = JSON.parse(packageJSONBuffer.toString()); + +program + .version('Version ' + packageJSON.version) + .name(packageJSON.name) + .option('--browserbaseApiKey ', 'The Browserbase API Key to use') + .option('--browserbaseProjectId ', 'The Browserbase Project ID to use') + .option('--proxies', 'Use Browserbase proxies.') + .option('--advancedStealth', 'Use advanced stealth mode. Only available to Browserbase Scale Plan users.') + .option('--contextId ', 'Browserbase Context ID to use.') + .option('--persist [boolean]', 'Whether to persist the Browserbase context', true) + .option('--port ', 'Port to listen on for SSE transport.') + .option('--host ', 'Host to bind server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces.') + .option('--cookies [json]', 'JSON array of cookies to inject into the browser. Format: [{"name":"cookie1","value":"val1","domain":"example.com"}, ...]') + .option('--browserWidth ', 'Browser width to use for the browser.') + .option('--browserHeight ', 'Browser height to use for the browser.') + .action(async options => { + const config = await resolveConfig(options); + const serverList = new ServerList(async() => createServer(config)); + setupExitWatchdog(serverList); + + if (options.port) + startHttpTransport(+options.port, options.host, serverList); + else + await startStdioTransport(serverList); + }); + +function setupExitWatchdog(serverList: ServerList) { + const handleExit = async () => { + setTimeout(() => process.exit(0), 15000); + await serverList.closeAll(); + process.exit(0); + }; + + process.stdin.on('close', handleExit); + process.on('SIGINT', handleExit); + process.on('SIGTERM', handleExit); +} + +program.parse(process.argv); \ No newline at end of file diff --git a/stagehand/src/server.ts b/stagehand/src/server.ts index b05a7e9..be2cf13 100644 --- a/stagehand/src/server.ts +++ b/stagehand/src/server.ts @@ -1,320 +1,27 @@ import { Server } from "@modelcontextprotocol/sdk/server/index.js"; -import { - CallToolRequestSchema, - ListToolsRequestSchema, - ListResourcesRequestSchema, - ListResourceTemplatesRequestSchema, - ListPromptsRequestSchema, - GetPromptRequestSchema, - ReadResourceRequestSchema, -} from "@modelcontextprotocol/sdk/types.js"; -import { Stagehand } from "@browserbasehq/stagehand"; -import type { ConstructorParams } from "@browserbasehq/stagehand"; -import { sanitizeMessage } from "./utils.js"; -import { - log, - logRequest, - logResponse, - operationLogs, - setServerInstance, -} from "./logging.js"; -import { TOOLS, handleToolCall } from "./tools.js"; -import { PROMPTS, getPrompt } from "./prompts.js"; -import { - listResources, - listResourceTemplates, - readResource, -} from "./resources.js"; +export class ServerList { + private _servers: Server[] = []; + private _serverFactory: () => Promise; -// Define Stagehand configuration -export const stagehandConfig: ConstructorParams = { - env: - process.env.BROWSERBASE_API_KEY && process.env.BROWSERBASE_PROJECT_ID - ? "BROWSERBASE" - : "LOCAL", - apiKey: process.env.BROWSERBASE_API_KEY /* API key for authentication */, - projectId: process.env.BROWSERBASE_PROJECT_ID /* Project identifier */, - logger: (message) => - console.error( - logLineToString(message) - ) /* Custom logging function to stderr */, - domSettleTimeoutMs: 30_000 /* Timeout for DOM to settle in milliseconds */, - browserbaseSessionCreateParams: - process.env.BROWSERBASE_API_KEY && process.env.BROWSERBASE_PROJECT_ID - ? { - projectId: process.env.BROWSERBASE_PROJECT_ID!, - browserSettings: process.env.CONTEXT_ID - ? { - context: { - id: process.env.CONTEXT_ID, - persist: true, - }, - } - : undefined, - } - : undefined, - localBrowserLaunchOptions: process.env.LOCAL_CDP_URL - ? { - cdpUrl: process.env.LOCAL_CDP_URL, - } - : undefined, - enableCaching: true /* Enable caching functionality */, - browserbaseSessionID: - undefined /* Session ID for resuming Browserbase sessions */, - modelName: "gpt-4o" /* Name of the model to use */, - modelClientOptions: { - apiKey: process.env.OPENAI_API_KEY, - } /* Configuration options for the model client */, - useAPI: false, -}; - -// Global state -let stagehand: Stagehand | undefined; - -// Ensure Stagehand is initialized -export async function ensureStagehand() { - if ( - stagehandConfig.env === "LOCAL" && - !stagehandConfig.localBrowserLaunchOptions?.cdpUrl - ) { - throw new Error( - 'Using a local browser without providing a CDP URL is not supported. Please provide a CDP URL using the LOCAL_CDP_URL environment variable.\n\nTo launch your browser in "debug", see our documentation.\n\nhttps://docs.stagehand.dev/examples/customize_browser#use-your-personal-browser' - ); + constructor(serverFactory: () => Promise) { + this._serverFactory = serverFactory; } - try { - if (!stagehand) { - stagehand = new Stagehand(stagehandConfig); - await stagehand.init(); - return stagehand; - } - - // Try to perform a simple operation to check if the session is still valid - try { - await stagehand.page.evaluate(() => document.title); - return stagehand; - } catch (error) { - // If we get an error indicating the session is invalid, reinitialize - if ( - error instanceof Error && - (error.message.includes( - "Target page, context or browser has been closed" - ) || - error.message.includes("Session expired") || - error.message.includes("context destroyed")) - ) { - log("Browser session expired, reinitializing Stagehand...", "info"); - stagehand = new Stagehand(stagehandConfig); - await stagehand.init(); - return stagehand; - } - throw error; // Re-throw if it's a different type of error - } - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - log(`Failed to initialize/reinitialize Stagehand: ${errorMsg}`, "error"); - throw error; + async create() { + const server = await this._serverFactory(); + this._servers.push(server); + return server; } -} - -// Create the server -export function createServer() { - const server = new Server( - { - name: "stagehand", - version: "0.1.0", - }, - { - capabilities: { - resources: {}, - tools: {}, - logging: {}, - prompts: {}, - }, - } - ); - - // Store server instance for logging - setServerInstance(server); - - // Setup request handlers - server.setRequestHandler(ListToolsRequestSchema, async (request) => { - try { - logRequest("ListTools", request.params); - const response = { tools: TOOLS }; - const sanitizedResponse = sanitizeMessage(response); - logResponse("ListTools", JSON.parse(sanitizedResponse)); - return JSON.parse(sanitizedResponse); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - }); - - server.setRequestHandler(CallToolRequestSchema, async (request) => { - try { - logRequest("CallTool", request.params); - operationLogs.length = 0; // Clear logs for new operation - - if ( - !request.params?.name || - !TOOLS.find((t) => t.name === request.params.name) - ) { - throw new Error(`Invalid tool name: ${request.params?.name}`); - } - - // Ensure Stagehand is initialized - try { - stagehand = await ensureStagehand(); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - content: [ - { - type: "text", - text: `Failed to initialize Stagehand: ${errorMsg}.\n\nConfig: ${JSON.stringify( - stagehandConfig, - null, - 2 - )}`, - }, - { - type: "text", - text: `Operation logs:\n${operationLogs.join("\n")}`, - }, - ], - isError: true, - }; - } - const result = await handleToolCall( - request.params.name, - request.params.arguments ?? {}, - stagehand - ); - - const sanitizedResult = sanitizeMessage(result); - logResponse("CallTool", JSON.parse(sanitizedResult)); - return JSON.parse(sanitizedResult); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - }); - - server.setRequestHandler(ListResourcesRequestSchema, async (request) => { - try { - logRequest("ListResources", request.params); - const response = listResources(); - const sanitizedResponse = sanitizeMessage(response); - logResponse("ListResources", JSON.parse(sanitizedResponse)); - return JSON.parse(sanitizedResponse); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - }); - - server.setRequestHandler( - ListResourceTemplatesRequestSchema, - async (request) => { - try { - logRequest("ListResourceTemplates", request.params); - const response = listResourceTemplates(); - const sanitizedResponse = sanitizeMessage(response); - logResponse("ListResourceTemplates", JSON.parse(sanitizedResponse)); - return JSON.parse(sanitizedResponse); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - } - ); - - server.setRequestHandler(ReadResourceRequestSchema, async (request) => { - try { - logRequest("ReadResource", request.params); - const uri = request.params.uri.toString(); - const response = readResource(uri); - const sanitizedResponse = sanitizeMessage(response); - logResponse("ReadResource", JSON.parse(sanitizedResponse)); - return JSON.parse(sanitizedResponse); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - }); - - server.setRequestHandler(ListPromptsRequestSchema, async (request) => { - try { - logRequest("ListPrompts", request.params); - const response = { prompts: PROMPTS }; - const sanitizedResponse = sanitizeMessage(response); - logResponse("ListPrompts", JSON.parse(sanitizedResponse)); - return JSON.parse(sanitizedResponse); - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - }); - - server.setRequestHandler(GetPromptRequestSchema, async (request) => { - try { - logRequest("GetPrompt", request.params); - - // Check if prompt name is valid and get the prompt - try { - const prompt = getPrompt(request.params?.name || ""); - const sanitizedResponse = sanitizeMessage(prompt); - logResponse("GetPrompt", JSON.parse(sanitizedResponse)); - return JSON.parse(sanitizedResponse); - } catch (error) { - throw new Error(`Invalid prompt name: ${request.params?.name}`); - } - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - error: { - code: -32603, - message: `Internal error: ${errorMsg}`, - }, - }; - } - }); + async close(server: Server) { + const index = this._servers.indexOf(server); + if (index !== -1) + this._servers.splice(index, 1); + await server.close(); + } - return server; + async closeAll() { + await Promise.all(this._servers.map(server => server.close())); + } } - -// Import missing function from logging -import { formatLogResponse, logLineToString } from "./logging.js"; diff --git a/stagehand/src/sessionManager.ts b/stagehand/src/sessionManager.ts new file mode 100644 index 0000000..25439e6 --- /dev/null +++ b/stagehand/src/sessionManager.ts @@ -0,0 +1,409 @@ +import { + chromium, + Browser, + Page, +} from "playwright-core"; +import { Browserbase } from "@browserbasehq/sdk"; +import type { Config } from "../config.js"; +import { SessionCreateParams } from "@browserbasehq/sdk/src/resources/sessions/sessions.js"; +import type { Cookie } from "playwright-core"; + +// Define the type for a session object +export type BrowserSession = { + browser: Browser; + page: Page; + sessionId: string; +}; + +// Global state for managing browser sessions +const browsers = new Map(); + +// Keep track of the default session explicitly +let defaultBrowserSession: BrowserSession | null = null; + +// Define a specific ID for the default session +export const defaultSessionId = "browserbase_session_main"; + +// Keep track of the active session ID. Defaults to the main session. +let activeSessionId: string = defaultSessionId; + +/** + * Sets the active session ID. + * @param id The ID of the session to set as active. + */ +export function setActiveSessionId(id: string): void { + if (browsers.has(id) || id === defaultSessionId) { + activeSessionId = id; + } else { + process.stderr.write( + `[SessionManager] WARN - Set active session failed for non-existent ID: ${id}\n` + ); + } +} + +/** + * Gets the active session ID. + * @returns The active session ID. + */ +export function getActiveSessionId(): string { + return activeSessionId; +} + +/** + * Adds cookies to a browser context + * @param context Playwright browser context + * @param cookies Array of cookies to add + */ +export async function addCookiesToContext(context: any, cookies: Cookie[]): Promise { + if (!cookies || cookies.length === 0) { + return; + } + + try { + process.stderr.write(`[SessionManager] Adding ${cookies.length} cookies to browser context\n`); + await context.addCookies(cookies); + process.stderr.write(`[SessionManager] Successfully added cookies to browser context\n`); + } catch (error) { + process.stderr.write( + `[SessionManager] Error adding cookies to browser context: ${ + error instanceof Error ? error.message : String(error) + }\n` + ); + } +} + +// Function to create a new Browserbase session and connect Playwright +export async function createNewBrowserSession( + newSessionId: string, + config: Config, +): Promise { + if (!config.browserbaseApiKey) { + throw new Error("Browserbase API Key is missing in the configuration."); + } + if (!config.browserbaseProjectId) { + throw new Error("Browserbase Project ID is missing in the configuration."); + } + + const bb = new Browserbase({ + apiKey: config.browserbaseApiKey, + }); + + // Prepare session creation options + const sessionOptions: SessionCreateParams = { + // Use non-null assertion after check + projectId: config.browserbaseProjectId!, + proxies: config.proxies, + browserSettings: { + viewport: { + width: config.viewPort?.browserWidth ?? 1024, + height: config.viewPort?.browserHeight ?? 768, + }, + context: config.context?.contextId ? { + id: config.context?.contextId, + persist: config.context?.persist ?? true, + } : undefined, + advancedStealth: config.advancedStealth ?? undefined, + } + }; + + try { + process.stderr.write( + `[SessionManager] Creating session ${newSessionId}...\n` + ); + const bbSession = await bb.sessions.create(sessionOptions); + process.stderr.write( + `[SessionManager] Browserbase session created: ${bbSession.id}\n` + ); + + const browser = await chromium.connectOverCDP(bbSession.connectUrl); + process.stderr.write( + `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${bbSession.id}\n` + ); + + browser.on("disconnected", () => { + process.stderr.write(`[SessionManager] Disconnected: ${newSessionId}\n`); + browsers.delete(newSessionId); + if (defaultBrowserSession && defaultBrowserSession.browser === browser) { + process.stderr.write( + `[SessionManager] Disconnected (default): ${newSessionId}\n` + ); + defaultBrowserSession = null; + } + if ( + activeSessionId === newSessionId && + newSessionId !== defaultSessionId + ) { + process.stderr.write( + `[SessionManager] WARN - Active session disconnected, resetting to default: ${newSessionId}\n` + ); + setActiveSessionId(defaultSessionId); + } + }); + + let context = browser.contexts()[0]; + if (!context) { + context = await browser.newContext(); + } + + // Add cookies to the context if they are provided in the config + if (config.cookies && Array.isArray(config.cookies) && config.cookies.length > 0) { + await addCookiesToContext(context, config.cookies); + } + + let page = context.pages()[0]; + if (!page) { + page = await context.newPage(); + } + + const sessionObj: BrowserSession = { + browser, + page, + sessionId: bbSession.id, + }; + + browsers.set(newSessionId, sessionObj); + + if (newSessionId === defaultSessionId) { + defaultBrowserSession = sessionObj; + } + + setActiveSessionId(newSessionId); + process.stderr.write( + `[SessionManager] Session created and active: ${newSessionId}\n` + ); + + return sessionObj; + } catch (creationError) { + const errorMessage = + creationError instanceof Error + ? creationError.message + : String(creationError); + process.stderr.write( + `[SessionManager] Creating session ${newSessionId} failed: ${ + creationError instanceof Error + ? creationError.message + : String(creationError) + }` + ); + throw new Error( + `Failed to create/connect session ${newSessionId}: ${errorMessage}` + ); + } +} + +async function closeBrowserGracefully( + session: BrowserSession | undefined | null, + sessionIdToLog: string +): Promise { + if (session?.browser?.isConnected()) { + process.stderr.write( + `[SessionManager] Closing browser for session: ${sessionIdToLog}\n` + ); + try { + await session.browser.close(); + } catch (closeError) { + process.stderr.write( + `[SessionManager] WARN - Error closing browser for session ${sessionIdToLog}: ${ + closeError instanceof Error ? closeError.message : String(closeError) + }\n` + ); + } + } +} + +// Internal function to ensure default session +export async function ensureDefaultSessionInternal( + config: Config +): Promise { + const sessionId = defaultSessionId; + let needsRecreation = false; + + if (!defaultBrowserSession) { + needsRecreation = true; + process.stderr.write( + `[SessionManager] Default session ${sessionId} not found, creating.\n` + ); + } else if ( + !defaultBrowserSession.browser.isConnected() || + defaultBrowserSession.page.isClosed() + ) { + needsRecreation = true; + process.stderr.write( + `[SessionManager] Default session ${sessionId} is stale, recreating.\n` + ); + await closeBrowserGracefully(defaultBrowserSession, sessionId); + defaultBrowserSession = null; + browsers.delete(sessionId); + } + + if (needsRecreation) { + try { + defaultBrowserSession = await createNewBrowserSession(sessionId, config); + return defaultBrowserSession; + } catch (error) { + // Error during initial creation or recreation + process.stderr.write( + `[SessionManager] Initial/Recreation attempt for default session ${sessionId} failed. Error: ${ + error instanceof Error ? error.message : String(error) + }\n` + ); + // Attempt one more time after a failure + process.stderr.write( + `[SessionManager] Retrying creation of default session ${sessionId} after error...\n` + ); + try { + defaultBrowserSession = await createNewBrowserSession(sessionId, config); + return defaultBrowserSession; + } catch (retryError) { + const finalErrorMessage = + retryError instanceof Error + ? retryError.message + : String(retryError); + process.stderr.write( + `[SessionManager] Failed to recreate default session ${sessionId} after retry: ${finalErrorMessage}\n` + ); + throw new Error( + `Failed to ensure default session ${sessionId} after initial error and retry: ${finalErrorMessage}` + ); + } + } + } + + // If we reached here, the existing default session is considered okay. + setActiveSessionId(sessionId); // Ensure default is marked active + return defaultBrowserSession!; // Non-null assertion: logic ensures it's not null here +} + +// Get a specific session by ID +export async function getSession( + sessionId: string, + config: Config +): Promise { + if (sessionId === defaultSessionId) { + try { + return await ensureDefaultSessionInternal(config); + } catch (error) { + // ensureDefaultSessionInternal already logs extensively + process.stderr.write( + `[SessionManager] Failed to get default session due to error in ensureDefaultSessionInternal for ${sessionId}. See previous messages for details.\n` + ); + return null; // Or rethrow if getSession failing for default is critical + } + } + + // For non-default sessions + process.stderr.write(`[SessionManager] Getting session: ${sessionId}\n`); + let sessionObj = browsers.get(sessionId); + + if (!sessionObj) { + process.stderr.write( + `[SessionManager] WARN - Session not found in map: ${sessionId}\n` + ); + return null; + } + + // Validate the found session + if (!sessionObj.browser.isConnected() || sessionObj.page.isClosed()) { + process.stderr.write( + `[SessionManager] WARN - Found session ${sessionId} is stale, removing.\n` + ); + await closeBrowserGracefully(sessionObj, sessionId); + browsers.delete(sessionId); + if (activeSessionId === sessionId) { + process.stderr.write( + `[SessionManager] WARN - Invalidated active session ${sessionId}, resetting to default.\n` + ); + setActiveSessionId(defaultSessionId); + } + return null; + } + + // Session appears valid, make it active + setActiveSessionId(sessionId); + process.stderr.write(`[SessionManager] Using valid session: ${sessionId}\n`); + return sessionObj; +} + +/** + * Get a session by ID without creating new sessions. + * This is a read-only operation that never triggers session creation. + * Used for operations like closing sessions where we don't want side effects. + * @param sessionId The session ID to retrieve + * @returns The session if it exists and is valid, null otherwise + */ +export function getSessionReadOnly(sessionId: string): BrowserSession | null { + // Check if it's the default session + if (sessionId === defaultSessionId && defaultBrowserSession) { + // Only return if it's actually connected and valid + if (defaultBrowserSession.browser.isConnected() && !defaultBrowserSession.page.isClosed()) { + return defaultBrowserSession; + } + return null; + } + + // For non-default sessions, check the browsers map + const sessionObj = browsers.get(sessionId); + if (!sessionObj) { + return null; + } + + // Validate the session is still active + if (!sessionObj.browser.isConnected() || sessionObj.page.isClosed()) { + return null; + } + + return sessionObj; +} + +/** + * Clean up a session by removing it from tracking. + * This is called after a browser is closed to ensure proper cleanup. + * @param sessionId The session ID to clean up + */ +export function cleanupSession(sessionId: string): void { + process.stderr.write( + `[SessionManager] Cleaning up session: ${sessionId}\n` + ); + + // Remove from browsers map + browsers.delete(sessionId); + + // Clear default session reference if this was the default + if (sessionId === defaultSessionId && defaultBrowserSession) { + defaultBrowserSession = null; + } + + // Reset active session to default if this was the active one + if (activeSessionId === sessionId) { + process.stderr.write( + `[SessionManager] Cleaned up active session ${sessionId}, resetting to default.\n` + ); + setActiveSessionId(defaultSessionId); + } +} + +// Function to close all managed browser sessions gracefully +export async function closeAllSessions(): Promise { + process.stderr.write(`[SessionManager] Closing all sessions...\n`); + const closePromises: Promise[] = []; + for (const [id, session] of browsers.entries()) { + process.stderr.write(`[SessionManager] Closing session: ${id}\n`); + closePromises.push( + // Use the helper for consistent logging/error handling + closeBrowserGracefully(session, id) + ); + } + try { + await Promise.all(closePromises); + } catch(e) { + // Individual errors are caught and logged by closeBrowserGracefully + process.stderr.write( + `[SessionManager] WARN - Some errors occurred during batch session closing. See individual messages.\n` + ); + } + + browsers.clear(); + defaultBrowserSession = null; + setActiveSessionId(defaultSessionId); // Reset active session to default + process.stderr.write(`[SessionManager] All sessions closed and cleared.\n`); +} diff --git a/stagehand/src/tools.ts b/stagehand/src/tools/tools.ts similarity index 98% rename from stagehand/src/tools.ts rename to stagehand/src/tools/tools.ts index e04a39e..d92c6e7 100644 --- a/stagehand/src/tools.ts +++ b/stagehand/src/tools/tools.ts @@ -1,7 +1,7 @@ import { Stagehand } from "@browserbasehq/stagehand"; import { CallToolResult, Tool } from "@modelcontextprotocol/sdk/types.js"; -import { getServerInstance, operationLogs } from "./logging.js"; -import { screenshots } from "./resources.js"; +import { getServerInstance, operationLogs } from "../logging.js"; +import { screenshots } from "../resources.js"; // Define the Stagehand tools export const TOOLS: Tool[] = [ diff --git a/stagehand/src/tools/utils.ts b/stagehand/src/tools/utils.ts new file mode 100644 index 0000000..3f72c64 --- /dev/null +++ b/stagehand/src/tools/utils.ts @@ -0,0 +1,3 @@ +export function sanitizeForFilePath(s: string) { + return s.replace(/[^a-zA-Z0-9_.-]/g, '_'); // More robust sanitization +} \ No newline at end of file diff --git a/stagehand/src/transport.ts b/stagehand/src/transport.ts new file mode 100644 index 0000000..82a703a --- /dev/null +++ b/stagehand/src/transport.ts @@ -0,0 +1,118 @@ +import http from 'node:http'; +import assert from 'node:assert'; +import crypto from 'node:crypto'; + +import { ServerList } from './server.js'; +import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js'; +import { SSEServerTransport } from '@modelcontextprotocol/sdk/server/sse.js'; +import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js'; + +export async function startStdioTransport(serverList: ServerList) { + const server = await serverList.create(); + await server.connect(new StdioServerTransport()); +} + +async function handleSSE(req: http.IncomingMessage, res: http.ServerResponse, url: URL, serverList: ServerList, sessions: Map) { + if (req.method === 'POST') { + const sessionId = url.searchParams.get('sessionId'); + if (!sessionId) { + res.statusCode = 400; + return res.end('Missing sessionId'); + } + + const transport = sessions.get(sessionId); + if (!transport) { + res.statusCode = 404; + return res.end('Session not found'); + } + + return await transport.handlePostMessage(req, res); + } else if (req.method === 'GET') { + const transport = new SSEServerTransport('/sse', res); + sessions.set(transport.sessionId, transport); + const server = await serverList.create(); + res.on('close', () => { + sessions.delete(transport.sessionId); + serverList.close(server).catch(e => { + // eslint-disable-next-line no-console + // console.error(e); + }); + }); + return await server.connect(transport); + } + + res.statusCode = 405; + res.end('Method not allowed'); +} + +async function handleStreamable(req: http.IncomingMessage, res: http.ServerResponse, serverList: ServerList, sessions: Map) { + const sessionId = req.headers['mcp-session-id'] as string | undefined; + if (sessionId) { + const transport = sessions.get(sessionId); + if (!transport) { + res.statusCode = 404; + res.end('Session not found'); + return; + } + return await transport.handleRequest(req, res); + } + + if (req.method === 'POST') { + const transport = new StreamableHTTPServerTransport({ + sessionIdGenerator: () => crypto.randomUUID(), + onsessioninitialized: sessionId => { + sessions.set(sessionId, transport); + } + }); + transport.onclose = () => { + if (transport.sessionId) + sessions.delete(transport.sessionId); + }; + const server = await serverList.create(); + await server.connect(transport); + return await transport.handleRequest(req, res); + } + + res.statusCode = 400; + res.end('Invalid request'); +} + +export function startHttpTransport(port: number, hostname: string | undefined, serverList: ServerList) { + const sseSessions = new Map(); + const streamableSessions = new Map(); + const httpServer = http.createServer(async (req, res) => { + const url = new URL(`http://localhost${req.url}`); + if (url.pathname.startsWith('/mcp')) + await handleStreamable(req, res, serverList, streamableSessions); + else + await handleSSE(req, res, url, serverList, sseSessions); + }); + httpServer.listen(port, hostname, () => { + const address = httpServer.address(); + assert(address, 'Could not bind server socket'); + let url: string; + if (typeof address === 'string') { + url = address; + } else { + const resolvedPort = address.port; + let resolvedHost = address.family === 'IPv4' ? address.address : `[${address.address}]`; + if (resolvedHost === '0.0.0.0' || resolvedHost === '[::]') + resolvedHost = 'localhost'; + url = `http://${resolvedHost}:${resolvedPort}`; + } + const message = [ + `Listening on ${url}`, + 'Put this in your client config:', + JSON.stringify({ + 'mcpServers': { + 'browserbase': { + 'url': `${url}/sse` + } + } + }, undefined, 2), + 'If your client supports streamable HTTP, you can use the /mcp endpoint instead.', + ].join('\n'); + // eslint-disable-next-line no-console + console.log(message); + }); +} \ No newline at end of file From e9e1e78bce016d7c7e5226e0b5446e8b43da95e9 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Fri, 20 Jun 2025 17:24:57 -0700 Subject: [PATCH 02/32] stagehand tools using browser context similar to browserbase + stagehand init issues fixed --- stagehand/package.json | 9 +- stagehand/src/config.ts | 21 +-- stagehand/src/context.ts | 204 ++++++++++++++++++++++++++--- stagehand/src/index.ts | 12 +- stagehand/src/server.ts | 2 +- stagehand/src/tools/session.ts | 232 +++++++++++++++++++++++++++++++++ stagehand/src/tools/tool.ts | 47 +++++++ stagehand/src/tools/tools.ts | 120 ++++++++++------- 8 files changed, 548 insertions(+), 99 deletions(-) create mode 100644 stagehand/src/tools/session.ts create mode 100644 stagehand/src/tools/tool.ts diff --git a/stagehand/package.json b/stagehand/package.json index 94b69f8..2c40f9f 100644 --- a/stagehand/package.json +++ b/stagehand/package.json @@ -7,11 +7,16 @@ "homepage": "https://modelcontextprotocol.io", "bugs": "https://github.com/modelcontextprotocol/servers/issues", "type": "module", + "main": "./cli.js", "bin": { - "mcp-server-stagehand": "dist/index.js" + "mcp-server-stagehand": "cli.js" }, "files": [ - "dist" + "dist", + "cli.js", + "index.d.ts", + "index.js", + "config.d.ts" ], "scripts": { "build": "tsc && shx chmod +x dist/*.js", diff --git a/stagehand/src/config.ts b/stagehand/src/config.ts index be94737..d72f9af 100644 --- a/stagehand/src/config.ts +++ b/stagehand/src/config.ts @@ -3,29 +3,10 @@ import fs from 'fs'; import path from 'path'; import { sanitizeForFilePath } from './tools/utils.js'; import type { Cookie } from "playwright-core"; +import type { Config } from '../config.js'; export type ToolCapability = 'core' | string; -export interface Config { - browserbaseApiKey?: string; - browserbaseProjectId?: string; - server?: { - port?: number; - host?: string; - }; - proxies?: boolean; - advancedStealth?: boolean; - context?: { - contextId?: string; - persist?: boolean; - }; - viewPort?: { - browserWidth?: number; - browserHeight?: number; - }; - cookies?: Cookie[]; -} - // Define Command Line Options Structure export type CLIOptions = { browserbaseApiKey?: string; diff --git a/stagehand/src/context.ts b/stagehand/src/context.ts index 01631af..35d4910 100644 --- a/stagehand/src/context.ts +++ b/stagehand/src/context.ts @@ -1,7 +1,7 @@ import { Stagehand } from "@browserbasehq/stagehand"; import { Server } from "@modelcontextprotocol/sdk/server/index.js"; import type { Config } from "../config.js"; -import { CallToolResult } from "@modelcontextprotocol/sdk/types.js"; +import { CallToolResult, TextContent, ImageContent } from "@modelcontextprotocol/sdk/types.js"; import { handleToolCall } from "./tools/tools.js"; import { listResources, readResource } from "./resources.js"; import { @@ -12,11 +12,23 @@ import { setServerInstance, log } from "./logging.js"; +import { + getSession, + getSessionReadOnly, + defaultSessionId, + type BrowserSession +} from "./sessionManager.js"; + +export type ToolActionResult = + | { content?: (ImageContent | TextContent)[] } + | undefined + | void; export class Context { - private stagehand: Stagehand; + private stagehands = new Map(); + public readonly config: Config; private server: Server; - private config: Config; + public currentSessionId: string = defaultSessionId; constructor(server: Server, config: Config) { this.server = server; @@ -28,26 +40,171 @@ export class Context { setupLogRotation(); registerExitHandlers(); scheduleLogRotation(); + } + + /** + * Gets the Stagehand instance for the current session, creating one if needed + */ + public async getStagehand(sessionId: string = this.currentSessionId): Promise { + let stagehand = this.stagehands.get(sessionId); + + if (!stagehand) { + // Create a new Stagehand instance for this session + stagehand = new Stagehand({ + env: "BROWSERBASE", + logger: (logLine) => { + log(`Stagehand[${sessionId}]: ${logLine.message}`, 'info'); + }, + }); + this.stagehands.set(sessionId, stagehand); + } + + await stagehand.init(); + + return stagehand; + } + + /** + * Sets the Stagehand instance for a specific session + */ + public setStagehand(sessionId: string, stagehand: Stagehand): void { + this.stagehands.set(sessionId, stagehand); + } + + /** + * Removes the Stagehand instance for a specific session + */ + public async removeStagehand(sessionId: string): Promise { + const stagehand = this.stagehands.get(sessionId); + if (stagehand) { + try { + await stagehand.close(); + } catch (error) { + log(`Error closing Stagehand for session ${sessionId}: ${error}`, 'error'); + } + this.stagehands.delete(sessionId); + } + } - // Initialize Stagehand - this.stagehand = new Stagehand({ - env: "BROWSERBASE", - logger: (logLine) => { - log(`Stagehand: ${logLine.message}`, 'info'); - }, - }); + public async getActivePage(): Promise { + // Try to get page from Stagehand first (if available for this session) + const stagehand = this.stagehands.get(this.currentSessionId); + if (stagehand && stagehand.page && !stagehand.page.isClosed()) { + return stagehand.page; + } + + // Fallback to session manager + const session = await getSession(this.currentSessionId, this.config); + if (!session || !session.page || session.page.isClosed()) { + try { + const currentSession = await getSession( + this.currentSessionId, + this.config + ); + if ( + !currentSession || + !currentSession.page || + currentSession.page.isClosed() + ) { + return null; + } + return currentSession.page; + } catch (refreshError) { + return null; + } + } + return session.page; + } + + // Will create a new default session if one doesn't exist + public async getActiveBrowser(): Promise { + const session = await getSession(this.currentSessionId, this.config); + if (!session || !session.browser || !session.browser.isConnected()) { + try { + const currentSession = await getSession( + this.currentSessionId, + this.config + ); + if ( + !currentSession || + !currentSession.browser || + !currentSession.browser.isConnected() + ) { + return null; + } + return currentSession.browser; + } catch (refreshError) { + return null; + } + } + return session.browser; + } + + /** + * Get the active browser without triggering session creation. + * This is a read-only operation used when we need to check for an existing browser + * without side effects (e.g., during close operations). + * @returns The browser if it exists and is connected, null otherwise + */ + public getActiveBrowserReadOnly(): BrowserSession["browser"] | null { + const session = getSessionReadOnly(this.currentSessionId); + if (!session || !session.browser || !session.browser.isConnected()) { + return null; + } + return session.browser; + } + + /** + * Get the active page without triggering session creation. + * This is a read-only operation used when we need to check for an existing page + * without side effects. + * @returns The page if it exists and is not closed, null otherwise + */ + public getActivePageReadOnly(): BrowserSession["page"] | null { + const session = getSessionReadOnly(this.currentSessionId); + if (!session || !session.page || session.page.isClosed()) { + return null; + } + return session.page; } async run(tool: any, args: any): Promise { try { - log(`Executing tool: ${tool.name} with args: ${JSON.stringify(args)}`, 'info'); - const result = await handleToolCall(tool.name, args, this.stagehand); - log(`Tool ${tool.name} completed successfully`, 'info'); - return result; + log(`Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`, 'info'); + + // Check if this tool has a handle method (new session tools) + // Only use handle method for session create and close tools + if ("handle" in tool && typeof tool.handle === "function" && + (tool.schema.name === "browserbase_session_create" || tool.schema.name === "browserbase_session_close")) { + const toolResult = await tool.handle(this as any, args); + + if (toolResult?.action) { + const actionResult = await toolResult.action(); + const content = actionResult?.content || []; + + return { + content: Array.isArray(content) ? content : [{ type: "text", text: "Action completed successfully." }], + isError: false, + }; + } else { + return { + content: [{ type: "text", text: `${tool.schema.name} completed successfully.` }], + isError: false, + }; + } + } else { + const stagehand = await this.getStagehand(); + const result = await handleToolCall(tool.schema.name, args, stagehand); + log(`Tool ${tool.schema.name} completed successfully`, 'info'); + return result; + } } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); - log(`Tool ${tool.name} failed: ${errorMessage}`, 'error'); - throw error; + log(`Tool ${tool.schema?.name || 'unknown'} failed: ${errorMessage}`, 'error'); + return { + content: [{ type: "text", text: `Error: ${errorMessage}` }], + isError: true, + }; } } @@ -61,10 +218,19 @@ export class Context { async close() { try { - await this.stagehand.close(); - log('Stagehand context closed successfully', 'info'); + // Close all Stagehand instances + for (const [sessionId, stagehand] of this.stagehands.entries()) { + try { + await stagehand.close(); + log(`Closed Stagehand for session ${sessionId}`, 'info'); + } catch (error) { + log(`Error closing Stagehand for session ${sessionId}: ${error}`, 'error'); + } + } + this.stagehands.clear(); + log('All Stagehand contexts closed successfully', 'info'); } catch (error) { - log(`Error closing Stagehand context: ${error}`, 'error'); + log(`Error closing Stagehand contexts: ${error}`, 'error'); } } } \ No newline at end of file diff --git a/stagehand/src/index.ts b/stagehand/src/index.ts index f7e977e..500268c 100644 --- a/stagehand/src/index.ts +++ b/stagehand/src/index.ts @@ -10,17 +10,6 @@ import { zodToJsonSchema } from "zod-to-json-schema"; import { Context } from "./context.js"; import { TOOLS } from "./tools/tools.js"; -// Environment variables configuration -const requiredEnvVars = { - BROWSERBASE_API_KEY: process.env.BROWSERBASE_API_KEY, - BROWSERBASE_PROJECT_ID: process.env.BROWSERBASE_PROJECT_ID, -}; - -// Validate required environment variables -Object.entries(requiredEnvVars).forEach(([name, value]) => { - if (!value) throw new Error(`${name} environment variable is required`); -}); - export async function createServer(config: Config): Promise { // Create the server const server = new Server( @@ -31,6 +20,7 @@ export async function createServer(config: Config): Promise { tools: { list: true, call: true }, prompts: { list: true, get: true }, notifications: { resources: { list_changed: true } }, + logging: {}, }, } ); diff --git a/stagehand/src/server.ts b/stagehand/src/server.ts index be2cf13..de86541 100644 --- a/stagehand/src/server.ts +++ b/stagehand/src/server.ts @@ -15,10 +15,10 @@ export class ServerList { } async close(server: Server) { + await server.close(); const index = this._servers.indexOf(server); if (index !== -1) this._servers.splice(index, 1); - await server.close(); } async closeAll() { diff --git a/stagehand/src/tools/session.ts b/stagehand/src/tools/session.ts new file mode 100644 index 0000000..b095a82 --- /dev/null +++ b/stagehand/src/tools/session.ts @@ -0,0 +1,232 @@ +import { z } from "zod"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; + +// Import SessionManager functions +import { + createNewBrowserSession, + defaultSessionId, + ensureDefaultSessionInternal, + cleanupSession, + type BrowserSession, +} from "../sessionManager.js"; + +// --- Tool: Create Session --- +const CreateSessionInputSchema = z.object({ + // Keep sessionId optional, but clarify its role + sessionId: z + .string() + .optional() + .describe( + "Optional session ID to use/reuse. If not provided or invalid, a new session is created." + ), +}); +type CreateSessionInput = z.infer; + +const createSessionSchema: ToolSchema = { + name: "browserbase_session_create", + description: + "Create or reuse a cloud browser session using Browserbase. Updates the active session.", + inputSchema: CreateSessionInputSchema, +}; + + +// Handle function for CreateSession using SessionManager +async function handleCreateSession( + context: Context, + params: CreateSessionInput +): Promise { + const action = async (): Promise => { + try { + const config = context.config; // Get config from context + let targetSessionId: string; + + if (params.sessionId) { + const projectId = config.browserbaseProjectId || ''; + targetSessionId = `${params.sessionId}_${projectId}`; + process.stderr.write( + `[tool.createSession] Attempting to create/assign session with specified ID: ${targetSessionId}` + ); + } else { + targetSessionId = defaultSessionId; + } + + let session: BrowserSession; + if (targetSessionId === defaultSessionId) { + session = await ensureDefaultSessionInternal(config); + } else { + session = await createNewBrowserSession(targetSessionId, config); + } + + if (!session || !session.browser || !session.page || !session.sessionId) { + throw new Error( + `SessionManager failed to return a valid session object with actualSessionId for ID: ${targetSessionId}` + ); + } + + context.currentSessionId = targetSessionId; + process.stderr.write( + `[tool.connected] Successfully connected to Browserbase session. Internal ID: ${targetSessionId}, Actual ID: ${session.sessionId}` + ); + + process.stderr.write(`[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.sessionId}`); + + return { + content: [ + { + type: "text", + text: `https://www.browserbase.com/sessions/${session.sessionId}`, + }, + ], + }; + } catch (error: any) { + process.stderr.write( + `[tool.createSession] Action failed: ${ + error.message || String(error) + }` + ); + // Re-throw to be caught by Context.run's error handling for actions + throw new Error( + `Failed to create Browserbase session: ${ + error.message || String(error) + }` + ); + } + }; + + // Return the ToolResult structure expected by Context.run + return { + action: action, + captureSnapshot: false, + code: [], + waitForNetwork: false, + }; +} + +// Define tool using handle +const createSessionTool: Tool = { + capability: "core", // Add capability + schema: createSessionSchema, + handle: handleCreateSession, +}; + +// --- Tool: Close Session --- +const CloseSessionInputSchema = z.object({ + random_string: z + .string() + .optional() + .describe("Dummy parameter to ensure consistent tool call format."), +}); +type CloseSessionInput = z.infer; + +const closeSessionSchema: ToolSchema = { + name: "browserbase_session_close", + description: + "Closes the current Browserbase session by disconnecting the Playwright browser. This will terminate the recording for the session.", + inputSchema: CloseSessionInputSchema, +}; + +async function handleCloseSession( + context: Context, + _params: CloseSessionInput +): Promise { + const code = [`// Attempting to close the current Browserbase session.`]; + + const action = async (): Promise => { + // Store the current session ID before it's potentially changed. + // This allows us to reference the original session ID later if needed. + const previousSessionId = context.currentSessionId; // Capture the ID before any changes + let browser: BrowserSession["browser"] | null = null; + let browserClosedSuccessfully = false; + let browserCloseErrorMessage = ""; + + // Step 1: Attempt to get the active browser instance WITHOUT creating a new one + try { + // Use read-only version to avoid creating new sessions + browser = context.getActiveBrowserReadOnly(); + } catch (error: any) { + process.stderr.write( + `[tool.closeSession] Error retrieving active browser (session ID was ${previousSessionId || 'default/unknown'}): ${error.message || String(error)}` + ); + // If we can't even get the browser, we can't close it. + // We will still proceed to reset context. + } + + // Step 2: If a browser instance was retrieved, attempt to close it + if (browser) { + try { + process.stderr.write( + `[tool.closeSession] Attempting to close browser for session: ${previousSessionId || 'default (actual might differ)'}` + ); + await browser.close(); + browserClosedSuccessfully = true; + process.stderr.write( + `[tool.closeSession] Browser connection for session (was ${previousSessionId}) closed.` + ); + + // Clean up the session from tracking + cleanupSession(previousSessionId); + + process.stderr.write( + `[tool.closeSession] View session replay at https://www.browserbase.com/sessions/${previousSessionId}` + ); + + } catch (error: any) { + browserCloseErrorMessage = error.message || String(error); + process.stderr.write( + `[tool.closeSession] Error during browser.close() for session (was ${previousSessionId}): ${browserCloseErrorMessage}` + ); + } + } else { + process.stderr.write( + `[tool.closeSession] No active browser instance found to close. (Session ID in context was: ${previousSessionId || 'default/unknown'}).` + ); + } + + // Step 3: Always reset the context's current session ID to default + const oldContextSessionId = context.currentSessionId; // This should effectively be 'previousSessionId' + context.currentSessionId = defaultSessionId; + process.stderr.write( + `[tool.closeSession] Session context reset to default. Previous context session ID was ${oldContextSessionId || 'default/unknown'}.` + ); + + // Step 4: Determine the result message + if (browser && !browserClosedSuccessfully) { // An attempt was made to close, but it failed + throw new Error( + `Failed to close the Browserbase browser (session ID in context was ${previousSessionId || 'default/unknown'}). Error: ${browserCloseErrorMessage}. Session context has been reset to default.` + ); + } + + if (browserClosedSuccessfully) { // Browser was present and closed + let successMessage = `Browserbase session (associated with context ID ${previousSessionId || 'default'}) closed successfully. Context reset to default.`; + if (previousSessionId && previousSessionId !== defaultSessionId) { + successMessage += ` If this was a uniquely named session (${previousSessionId}), view replay (if available) at https://browserbase.com/sessions`; + } + return { content: [{ type: "text", text: successMessage }] }; + } + + // No browser was found, or browser was null initially. + let infoMessage = "No active browser instance was found to close. Session context has been reset to default."; + if (previousSessionId && previousSessionId !== defaultSessionId) { + // This means a specific session was in context, but no browser for it. + infoMessage = `No active browser found for session ID '${previousSessionId}' in context. The context has been reset to default.`; + } + return { content: [{ type: "text", text: infoMessage }] }; + }; + + return { + action: action, + code: code, + captureSnapshot: false, + waitForNetwork: false, + }; +} + +const closeSessionTool: Tool = { + capability: "core", + schema: closeSessionSchema, + handle: handleCloseSession, +}; + +export default [createSessionTool, closeSessionTool]; \ No newline at end of file diff --git a/stagehand/src/tools/tool.ts b/stagehand/src/tools/tool.ts new file mode 100644 index 0000000..7351838 --- /dev/null +++ b/stagehand/src/tools/tool.ts @@ -0,0 +1,47 @@ +import type { ImageContent, TextContent } from '@modelcontextprotocol/sdk/types.js'; +import type { z } from 'zod'; +import type { Context } from '../context.js'; +import type { BrowserSession } from '../sessionManager.js'; +import type { Server } from '@modelcontextprotocol/sdk/server/index.js'; +import type { Config } from '../../config.js'; + +export type ToolSchema = { + name: string; + description: string; + inputSchema: Input; +}; + +// Export InputType +export type InputType = z.Schema; + +export type ToolActionResult = { content?: (ImageContent | TextContent)[] } | undefined | void; + +export type ToolResult = { + code: string[]; + action?: () => Promise; + captureSnapshot: boolean; + waitForNetwork: boolean; + resultOverride?: ToolActionResult; +}; + +export type Tool = { + capability: string; + schema: ToolSchema; + handle: (context: Context, params: z.output) => Promise; +}; + +export function defineTool(tool: Tool): Tool { + return tool; +} + +export {}; // Ensure this is treated as a module + +// Represents the execution context for a tool +export interface ToolContext { + page: BrowserSession['page']; + browser: BrowserSession['browser']; + server: Server; + sessionId: string; + config: Config; + context: Context; // The main context instance +} \ No newline at end of file diff --git a/stagehand/src/tools/tools.ts b/stagehand/src/tools/tools.ts index d92c6e7..a440433 100644 --- a/stagehand/src/tools/tools.ts +++ b/stagehand/src/tools/tools.ts @@ -1,81 +1,109 @@ import { Stagehand } from "@browserbasehq/stagehand"; -import { CallToolResult, Tool } from "@modelcontextprotocol/sdk/types.js"; +import { CallToolResult } from "@modelcontextprotocol/sdk/types.js"; import { getServerInstance, operationLogs } from "../logging.js"; import { screenshots } from "../resources.js"; +import sessionTools from "./session.js"; + +type ToolSchema = { + name: string; + description: string; + inputSchema: Record; // JSON schema object +}; + +export type Tool = { + capability: string; + schema: ToolSchema; +}; // Define the Stagehand tools export const TOOLS: Tool[] = [ + ...sessionTools, { - name: "stagehand_navigate", - description: - "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otheriwse use https://google.com as the starting point", - inputSchema: { - type: "object", - properties: { - url: { type: "string", description: "The URL to navigate to" }, + capability: "core", + schema: { + name: "stagehand_navigate", + description: + "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otheriwse use https://google.com as the starting point", + inputSchema: { + type: "object", + properties: { + url: { type: "string", description: "The URL to navigate to" }, + }, + required: ["url"], }, - required: ["url"], }, }, { - name: "stagehand_act", - description: `Performs an action on a web page element. Act actions should be as atomic and + capability: "core", + schema: { + name: "stagehand_act", + description: `Performs an action on a web page element. Act actions should be as atomic and specific as possible, i.e. "Click the sign in button" or "Type 'hello' into the search input". AVOID actions that are more than one step, i.e. "Order me pizza" or "Send an email to Paul asking him to call me". `, - inputSchema: { - type: "object", - properties: { - action: { - type: "string", - description: `The action to perform. Should be as atomic and specific as possible, + inputSchema: { + type: "object", + properties: { + action: { + type: "string", + description: `The action to perform. Should be as atomic and specific as possible, i.e. 'Click the sign in button' or 'Type 'hello' into the search input'. AVOID actions that are more than one step, i.e. 'Order me pizza' or 'Send an email to Paul asking him to call me'. The instruction should be just as specific as possible, and have a strong correlation to the text on the page. If unsure, use observe before using act."`, - }, - variables: { - type: "object", - additionalProperties: true, - description: `Variables used in the action template. ONLY use variables if you're dealing + }, + variables: { + type: "object", + additionalProperties: true, + description: `Variables used in the action template. ONLY use variables if you're dealing with sensitive data or dynamic content. For example, if you're logging in to a website, you can use a variable for the password. When using variables, you MUST have the variable key in the action template. For example: {"action": "Fill in the password", "variables": {"password": "123456"}}`, + }, }, + required: ["action"], }, - required: ["action"], }, }, { - name: "stagehand_extract", - description: `Extracts all of the text from the current page.`, - inputSchema: { - type: "object", - properties: {}, + capability: "core", + schema: { + name: "stagehand_extract", + description: `Extracts all of the text from the current page.`, + inputSchema: { + type: "object", + properties: {}, + }, }, }, { - name: "stagehand_observe", - description: - "Observes elements on the web page. Use this tool to observe elements that you can later use in an action. Use observe instead of extract when dealing with actionable (interactable) elements rather than text. More often than not, you'll want to use extract instead of observe when dealing with scraping or extracting structured text.", - inputSchema: { - type: "object", - properties: { - instruction: { - type: "string", - description: - "Instruction for observation (e.g., 'find the login button'). This instruction must be extremely specific.", + capability: "core", + schema: { + name: "stagehand_observe", + description: + "Observes elements on the web page. Use this tool to observe elements that you can later use in an action. Use observe instead of extract when dealing with actionable (interactable) elements rather than text. More often than not, you'll want to use extract instead of observe when dealing with scraping or extracting structured text.", + inputSchema: { + type: "object", + properties: { + instruction: { + type: "string", + description: + "Instruction for observation (e.g., 'find the login button'). This instruction must be extremely specific.", + }, }, + required: ["instruction"], }, - required: ["instruction"], }, }, { - name: "screenshot", - description: - "Takes a screenshot of the current page. Use this tool to learn where you are on the page when controlling the browser with Stagehand. Only use this tool when the other tools are not sufficient to get the information you need.", - inputSchema: { - type: "object", - properties: {}, + capability: "core", + schema: { + name: "screenshot", + description: + "Takes a screenshot of the current page. Use this tool to learn where you are on the page when controlling the browser with Stagehand. Only use this tool when the other tools are not sufficient to get the information you need.", + inputSchema: { + type: "object", + properties: {}, + }, }, }, ]; @@ -89,7 +117,7 @@ export async function handleToolCall( switch (name) { case "stagehand_navigate": try { - await stagehand.page.goto(args.url); + await stagehand.page.goto(args.url, { waitUntil: "domcontentloaded" }); return { content: [ { From 022b65a133470fc0358c006fca27ead43b9544f2 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Fri, 20 Jun 2025 17:36:56 -0700 Subject: [PATCH 03/32] rm legacy tool call and separate tools into individual files --- stagehand/src/context.ts | 13 +- stagehand/src/index.ts | 2 +- stagehand/src/tools/act.ts | 73 +++++++ stagehand/src/tools/extract.ts | 80 ++++++++ stagehand/src/tools/index.ts | 36 ++++ stagehand/src/tools/navigate.ts | 64 ++++++ stagehand/src/tools/observe.ts | 61 ++++++ stagehand/src/tools/screenshot.ts | 84 ++++++++ stagehand/src/tools/tools.ts | 331 ------------------------------ 9 files changed, 403 insertions(+), 341 deletions(-) create mode 100644 stagehand/src/tools/act.ts create mode 100644 stagehand/src/tools/extract.ts create mode 100644 stagehand/src/tools/index.ts create mode 100644 stagehand/src/tools/navigate.ts create mode 100644 stagehand/src/tools/observe.ts create mode 100644 stagehand/src/tools/screenshot.ts delete mode 100644 stagehand/src/tools/tools.ts diff --git a/stagehand/src/context.ts b/stagehand/src/context.ts index 35d4910..b87d799 100644 --- a/stagehand/src/context.ts +++ b/stagehand/src/context.ts @@ -2,7 +2,6 @@ import { Stagehand } from "@browserbasehq/stagehand"; import { Server } from "@modelcontextprotocol/sdk/server/index.js"; import type { Config } from "../config.js"; import { CallToolResult, TextContent, ImageContent } from "@modelcontextprotocol/sdk/types.js"; -import { handleToolCall } from "./tools/tools.js"; import { listResources, readResource } from "./resources.js"; import { ensureLogDirectory, @@ -172,10 +171,8 @@ export class Context { try { log(`Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`, 'info'); - // Check if this tool has a handle method (new session tools) - // Only use handle method for session create and close tools - if ("handle" in tool && typeof tool.handle === "function" && - (tool.schema.name === "browserbase_session_create" || tool.schema.name === "browserbase_session_close")) { + // Check if this tool has a handle method (new tool system) + if ("handle" in tool && typeof tool.handle === "function") { const toolResult = await tool.handle(this as any, args); if (toolResult?.action) { @@ -193,10 +190,8 @@ export class Context { }; } } else { - const stagehand = await this.getStagehand(); - const result = await handleToolCall(tool.schema.name, args, stagehand); - log(`Tool ${tool.schema.name} completed successfully`, 'info'); - return result; + // Fallback for any legacy tools without handle method + throw new Error(`Tool ${tool.schema.name} does not have a handle method`); } } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); diff --git a/stagehand/src/index.ts b/stagehand/src/index.ts index 500268c..9821aa9 100644 --- a/stagehand/src/index.ts +++ b/stagehand/src/index.ts @@ -8,7 +8,7 @@ import { CallToolRequestSchema, ListResourcesRequestSchema, ListToolsRequestSche import { z } from "zod"; import { zodToJsonSchema } from "zod-to-json-schema"; import { Context } from "./context.js"; -import { TOOLS } from "./tools/tools.js"; +import { TOOLS } from "./tools/index.js"; export async function createServer(config: Config): Promise { // Create the server diff --git a/stagehand/src/tools/act.ts b/stagehand/src/tools/act.ts new file mode 100644 index 0000000..a5aa808 --- /dev/null +++ b/stagehand/src/tools/act.ts @@ -0,0 +1,73 @@ +import { z } from "zod"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; + +const ActInputSchema = z.object({ + action: z.string().describe( + "The action to perform. Should be as atomic and specific as possible, " + + "i.e. 'Click the sign in button' or 'Type 'hello' into the search input'. AVOID actions that are more than one " + + "step, i.e. 'Order me pizza' or 'Send an email to Paul asking him to call me'. The instruction should be just as specific as possible, " + + "and have a strong correlation to the text on the page. If unsure, use observe before using act." + ), + variables: z.object({}).optional().describe( + "Variables used in the action template. ONLY use variables if you're dealing " + + "with sensitive data or dynamic content. For example, if you're logging in to a website, " + + "you can use a variable for the password. When using variables, you MUST have the variable " + + "key in the action template. For example: {\"action\": \"Fill in the password\", \"variables\": {\"password\": \"123456\"}}" + ), +}); + +type ActInput = z.infer; + +const actSchema: ToolSchema = { + name: "stagehand_act", + description: + "Performs an action on a web page element. Act actions should be as atomic and " + + "specific as possible, i.e. \"Click the sign in button\" or \"Type 'hello' into the search input\". " + + "AVOID actions that are more than one step, i.e. \"Order me pizza\" or \"Send an email to Paul " + + "asking him to call me\".", + inputSchema: ActInputSchema, +}; + +async function handleAct( + context: Context, + params: ActInput +): Promise { + const action = async (): Promise => { + try { + const stagehand = await context.getStagehand(); + await stagehand.page.act({ + action: params.action, + variables: params.variables, + }); + + return { + content: [ + { + type: "text", + text: `Action performed: ${params.action}`, + }, + ], + }; + } catch (error) { + const errorMsg = error instanceof Error ? error.message : String(error); + throw new Error(`Failed to perform action: ${errorMsg}`); + } + }; + + return { + action, + captureSnapshot: false, + code: [], + waitForNetwork: false, + }; +} + +const actTool: Tool = { + capability: "core", + schema: actSchema, + handle: handleAct, +}; + +export default actTool; \ No newline at end of file diff --git a/stagehand/src/tools/extract.ts b/stagehand/src/tools/extract.ts new file mode 100644 index 0000000..0e0daf8 --- /dev/null +++ b/stagehand/src/tools/extract.ts @@ -0,0 +1,80 @@ +import { z } from "zod"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; + +const ExtractInputSchema = z.object({ + random_string: z.string().optional().describe("Dummy parameter for no-parameter tools"), +}); + +type ExtractInput = z.infer; + +const extractSchema: ToolSchema = { + name: "stagehand_extract", + description: "Extracts all of the text from the current page.", + inputSchema: ExtractInputSchema, +}; + +async function handleExtract( + context: Context, + params: ExtractInput +): Promise { + const action = async (): Promise => { + try { + const page = await context.getActivePage(); + if (!page) { + throw new Error("No active page available"); + } + + const bodyText = await page.evaluate(() => document.body.innerText); + const content = bodyText + .split("\n") + .map((line) => line.trim()) + .filter((line) => { + if (!line) return false; + + if ( + (line.includes("{") && line.includes("}")) || + line.includes("@keyframes") || // Remove CSS animations + line.match(/^\.[a-zA-Z0-9_-]+\s*{/) || // Remove CSS lines starting with .className { + line.match(/^[a-zA-Z-]+:[a-zA-Z0-9%\s\(\)\.,-]+;$/) // Remove lines like "color: blue;" or "margin: 10px;" + ) { + return false; + } + return true; + }) + .map((line) => { + return line.replace(/\\u([0-9a-fA-F]{4})/g, (_, hex) => + String.fromCharCode(parseInt(hex, 16)) + ); + }); + + return { + content: [ + { + type: "text", + text: `Extracted content:\n${content.join("\n")}`, + }, + ], + }; + } catch (error) { + const errorMsg = error instanceof Error ? error.message : String(error); + throw new Error(`Failed to extract content: ${errorMsg}`); + } + }; + + return { + action, + captureSnapshot: false, + code: [], + waitForNetwork: false, + }; +} + +const extractTool: Tool = { + capability: "core", + schema: extractSchema, + handle: handleExtract, +}; + +export default extractTool; \ No newline at end of file diff --git a/stagehand/src/tools/index.ts b/stagehand/src/tools/index.ts new file mode 100644 index 0000000..2a98374 --- /dev/null +++ b/stagehand/src/tools/index.ts @@ -0,0 +1,36 @@ +// Import all individual tools +import navigateTool from "./navigate.js"; +import actTool from "./act.js"; +import extractTool from "./extract.js"; +import observeTool from "./observe.js"; +import screenshotTool from "./screenshot.js"; +import sessionTools from "./session.js"; + +// Export individual tools +export { default as navigateTool } from "./navigate.js"; +export { default as actTool } from "./act.js"; +export { default as extractTool } from "./extract.js"; +export { default as observeTool } from "./observe.js"; +export { default as screenshotTool } from "./screenshot.js"; +export { default as sessionTools } from "./session.js"; + +// Export all tools as array +export const TOOLS = [ + ...sessionTools, + navigateTool, + actTool, + extractTool, + observeTool, + screenshotTool, +]; + +// Export tools by category +export const coreTools = [ + navigateTool, + actTool, + extractTool, + observeTool, + screenshotTool, +]; + +export const sessionManagementTools = sessionTools; \ No newline at end of file diff --git a/stagehand/src/tools/navigate.ts b/stagehand/src/tools/navigate.ts new file mode 100644 index 0000000..e663d00 --- /dev/null +++ b/stagehand/src/tools/navigate.ts @@ -0,0 +1,64 @@ +import { z } from "zod"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; +import { operationLogs } from "../logging.js"; + +const NavigateInputSchema = z.object({ + url: z.string().describe("The URL to navigate to"), +}); + +type NavigateInput = z.infer; + +const navigateSchema: ToolSchema = { + name: "stagehand_navigate", + description: + "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otheriwse use https://google.com as the starting point", + inputSchema: NavigateInputSchema, +}; + +async function handleNavigate( + context: Context, + params: NavigateInput +): Promise { + const action = async (): Promise => { + try { + const page = await context.getActivePage(); + if (!page) { + throw new Error("No active page available"); + } + await page.goto(params.url, { waitUntil: "domcontentloaded" }); + + return { + content: [ + { + type: "text", + text: `Navigated to: ${params.url}`, + }, + { + type: "text", + text: `View the live session here: https://browserbase.com/sessions/${context.currentSessionId}`, + }, + ], + }; + } catch (error) { + const errorMsg = error instanceof Error ? error.message : String(error); + throw new Error(`Failed to navigate: ${errorMsg}`); + } + }; + + return { + action, + captureSnapshot: false, + code: [], + waitForNetwork: false, + }; +} + +const navigateTool: Tool = { + capability: "core", + schema: navigateSchema, + handle: handleNavigate, +}; + +export default navigateTool; \ No newline at end of file diff --git a/stagehand/src/tools/observe.ts b/stagehand/src/tools/observe.ts new file mode 100644 index 0000000..cd2adb1 --- /dev/null +++ b/stagehand/src/tools/observe.ts @@ -0,0 +1,61 @@ +import { z } from "zod"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; + +const ObserveInputSchema = z.object({ + instruction: z.string().describe( + "Instruction for observation (e.g., 'find the login button'). This instruction must be extremely specific." + ), +}); + +type ObserveInput = z.infer; + +const observeSchema: ToolSchema = { + name: "stagehand_observe", + description: + "Observes elements on the web page. Use this tool to observe elements that you can later use in an action. Use observe instead of extract when dealing with actionable (interactable) elements rather than text. More often than not, you'll want to use extract instead of observe when dealing with scraping or extracting structured text.", + inputSchema: ObserveInputSchema, +}; + +async function handleObserve( + context: Context, + params: ObserveInput +): Promise { + const action = async (): Promise => { + try { + const stagehand = await context.getStagehand(); + const observations = await stagehand.page.observe({ + instruction: params.instruction, + returnAction: false, + }); + + return { + content: [ + { + type: "text", + text: `Observations: ${JSON.stringify(observations)}`, + }, + ], + }; + } catch (error) { + const errorMsg = error instanceof Error ? error.message : String(error); + throw new Error(`Failed to observe: ${errorMsg}`); + } + }; + + return { + action, + captureSnapshot: false, + code: [], + waitForNetwork: false, + }; +} + +const observeTool: Tool = { + capability: "core", + schema: observeSchema, + handle: handleObserve, +}; + +export default observeTool; \ No newline at end of file diff --git a/stagehand/src/tools/screenshot.ts b/stagehand/src/tools/screenshot.ts new file mode 100644 index 0000000..94e1227 --- /dev/null +++ b/stagehand/src/tools/screenshot.ts @@ -0,0 +1,84 @@ +import { z } from "zod"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; +import { getServerInstance } from "../logging.js"; +import { screenshots } from "../resources.js"; + +const ScreenshotInputSchema = z.object({ + random_string: z.string().optional().describe("Dummy parameter for no-parameter tools"), +}); + +type ScreenshotInput = z.infer; + +const screenshotSchema: ToolSchema = { + name: "screenshot", + description: + "Takes a screenshot of the current page. Use this tool to learn where you are on the page when controlling the browser with Stagehand. Only use this tool when the other tools are not sufficient to get the information you need.", + inputSchema: ScreenshotInputSchema, +}; + +async function handleScreenshot( + context: Context, + params: ScreenshotInput +): Promise { + const action = async (): Promise => { + try { + const page = await context.getActivePage(); + if (!page) { + throw new Error("No active page available"); + } + + const screenshotBuffer = await page.screenshot({ + fullPage: false, + }); + + // Convert buffer to base64 string and store in memory + const screenshotBase64 = screenshotBuffer.toString("base64"); + const name = `screenshot-${new Date() + .toISOString() + .replace(/:/g, "-")}`; + screenshots.set(name, screenshotBase64); + + // Notify the client that the resources changed + const serverInstance = getServerInstance(); + if (serverInstance) { + serverInstance.notification({ + method: "notifications/resources/list_changed", + }); + } + + return { + content: [ + { + type: "text", + text: `Screenshot taken with name: ${name}`, + }, + { + type: "image", + data: screenshotBase64, + mimeType: "image/png", + }, + ], + }; + } catch (error) { + const errorMsg = error instanceof Error ? error.message : String(error); + throw new Error(`Failed to take screenshot: ${errorMsg}`); + } + }; + + return { + action, + captureSnapshot: false, + code: [], + waitForNetwork: false, + }; +} + +const screenshotTool: Tool = { + capability: "core", + schema: screenshotSchema, + handle: handleScreenshot, +}; + +export default screenshotTool; \ No newline at end of file diff --git a/stagehand/src/tools/tools.ts b/stagehand/src/tools/tools.ts deleted file mode 100644 index a440433..0000000 --- a/stagehand/src/tools/tools.ts +++ /dev/null @@ -1,331 +0,0 @@ -import { Stagehand } from "@browserbasehq/stagehand"; -import { CallToolResult } from "@modelcontextprotocol/sdk/types.js"; -import { getServerInstance, operationLogs } from "../logging.js"; -import { screenshots } from "../resources.js"; -import sessionTools from "./session.js"; - -type ToolSchema = { - name: string; - description: string; - inputSchema: Record; // JSON schema object -}; - -export type Tool = { - capability: string; - schema: ToolSchema; -}; - -// Define the Stagehand tools -export const TOOLS: Tool[] = [ - ...sessionTools, - { - capability: "core", - schema: { - name: "stagehand_navigate", - description: - "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otheriwse use https://google.com as the starting point", - inputSchema: { - type: "object", - properties: { - url: { type: "string", description: "The URL to navigate to" }, - }, - required: ["url"], - }, - }, - }, - { - capability: "core", - schema: { - name: "stagehand_act", - description: `Performs an action on a web page element. Act actions should be as atomic and - specific as possible, i.e. "Click the sign in button" or "Type 'hello' into the search input". - AVOID actions that are more than one step, i.e. "Order me pizza" or "Send an email to Paul - asking him to call me". `, - inputSchema: { - type: "object", - properties: { - action: { - type: "string", - description: `The action to perform. Should be as atomic and specific as possible, - i.e. 'Click the sign in button' or 'Type 'hello' into the search input'. AVOID actions that are more than one - step, i.e. 'Order me pizza' or 'Send an email to Paul asking him to call me'. The instruction should be just as specific as possible, - and have a strong correlation to the text on the page. If unsure, use observe before using act."`, - }, - variables: { - type: "object", - additionalProperties: true, - description: `Variables used in the action template. ONLY use variables if you're dealing - with sensitive data or dynamic content. For example, if you're logging in to a website, - you can use a variable for the password. When using variables, you MUST have the variable - key in the action template. For example: {"action": "Fill in the password", "variables": {"password": "123456"}}`, - }, - }, - required: ["action"], - }, - }, - }, - { - capability: "core", - schema: { - name: "stagehand_extract", - description: `Extracts all of the text from the current page.`, - inputSchema: { - type: "object", - properties: {}, - }, - }, - }, - { - capability: "core", - schema: { - name: "stagehand_observe", - description: - "Observes elements on the web page. Use this tool to observe elements that you can later use in an action. Use observe instead of extract when dealing with actionable (interactable) elements rather than text. More often than not, you'll want to use extract instead of observe when dealing with scraping or extracting structured text.", - inputSchema: { - type: "object", - properties: { - instruction: { - type: "string", - description: - "Instruction for observation (e.g., 'find the login button'). This instruction must be extremely specific.", - }, - }, - required: ["instruction"], - }, - }, - }, - { - capability: "core", - schema: { - name: "screenshot", - description: - "Takes a screenshot of the current page. Use this tool to learn where you are on the page when controlling the browser with Stagehand. Only use this tool when the other tools are not sufficient to get the information you need.", - inputSchema: { - type: "object", - properties: {}, - }, - }, - }, -]; - -// Handle tool calls -export async function handleToolCall( - name: string, - args: any, - stagehand: Stagehand -): Promise { - switch (name) { - case "stagehand_navigate": - try { - await stagehand.page.goto(args.url, { waitUntil: "domcontentloaded" }); - return { - content: [ - { - type: "text", - text: `Navigated to: ${args.url}`, - }, - { - type: "text", - text: `View the live session here: https://browserbase.com/sessions/${stagehand.browserbaseSessionID}`, - }, - ], - isError: false, - }; - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - content: [ - { - type: "text", - text: `Failed to navigate: ${errorMsg}`, - }, - { - type: "text", - text: `Operation logs:\n${operationLogs.join("\n")}`, - }, - ], - isError: true, - }; - } - - case "stagehand_act": - try { - await stagehand.page.act({ - action: args.action, - variables: args.variables, - }); - return { - content: [ - { - type: "text", - text: `Action performed: ${args.action}`, - }, - ], - isError: false, - }; - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - content: [ - { - type: "text", - text: `Failed to perform action: ${errorMsg}`, - }, - { - type: "text", - text: `Operation logs:\n${operationLogs.join("\n")}`, - }, - ], - isError: true, - }; - } - - case "stagehand_extract": { - try { - const bodyText = await stagehand.page.evaluate( - () => document.body.innerText - ); - const content = bodyText - .split("\n") - .map((line) => line.trim()) - .filter((line) => { - if (!line) return false; - - if ( - (line.includes("{") && line.includes("}")) || - line.includes("@keyframes") || // Remove CSS animations - line.match(/^\.[a-zA-Z0-9_-]+\s*{/) || // Remove CSS lines starting with .className { - line.match(/^[a-zA-Z-]+:[a-zA-Z0-9%\s\(\)\.,-]+;$/) // Remove lines like "color: blue;" or "margin: 10px;" - ) { - return false; - } - return true; - }) - .map((line) => { - return line.replace(/\\u([0-9a-fA-F]{4})/g, (_, hex) => - String.fromCharCode(parseInt(hex, 16)) - ); - }); - - return { - content: [ - { - type: "text", - text: `Extracted content:\n${content.join("\n")}`, - }, - ], - isError: false, - }; - } catch (error) { - return { - content: [ - { - type: "text", - text: `Failed to extract content: ${(error as Error).message}`, - }, - ], - isError: true, - }; - } - } - - case "stagehand_observe": - try { - const observations = await stagehand.page.observe({ - instruction: args.instruction, - returnAction: false, - }); - return { - content: [ - { - type: "text", - text: `Observations: ${JSON.stringify(observations)}`, - }, - ], - isError: false, - }; - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - content: [ - { - type: "text", - text: `Failed to observe: ${errorMsg}`, - }, - { - type: "text", - text: `Operation logs:\n${operationLogs.join("\n")}`, - }, - ], - isError: true, - }; - } - - case "screenshot": - try { - const screenshotBuffer = await stagehand.page.screenshot({ - fullPage: false, - }); - - // Convert buffer to base64 string and store in memory - const screenshotBase64 = screenshotBuffer.toString("base64"); - const name = `screenshot-${new Date() - .toISOString() - .replace(/:/g, "-")}`; - screenshots.set(name, screenshotBase64); - - // Notify the client that the resources changed - const serverInstance = getServerInstance(); - if (serverInstance) { - serverInstance.notification({ - method: "notifications/resources/list_changed", - }); - } - - return { - content: [ - { - type: "text", - text: `Screenshot taken with name: ${name}`, - }, - { - type: "image", - data: screenshotBase64, - mimeType: "image/png", - }, - ], - isError: false, - }; - } catch (error) { - const errorMsg = error instanceof Error ? error.message : String(error); - return { - content: [ - { - type: "text", - text: `Failed to take screenshot: ${errorMsg}`, - }, - { - type: "text", - text: `Operation logs:\n${operationLogs.join("\n")}`, - }, - ], - isError: true, - }; - } - - default: - return { - content: [ - { - type: "text", - text: `Unknown tool: ${name}`, - }, - { - type: "text", - text: `Operation logs:\n${operationLogs.join("\n")}`, - }, - ], - isError: true, - }; - } -} From e1c8f8013fb112f116724ffc7ee8fa6e6218819c Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 25 Jun 2025 15:03:28 -0700 Subject: [PATCH 04/32] clean up readonly functions --- stagehand/src/context.ts | 76 +++++---------------------------- stagehand/src/sessionManager.ts | 38 ++--------------- stagehand/src/tools/session.ts | 2 +- 3 files changed, 15 insertions(+), 101 deletions(-) diff --git a/stagehand/src/context.ts b/stagehand/src/context.ts index b87d799..be06dd0 100644 --- a/stagehand/src/context.ts +++ b/stagehand/src/context.ts @@ -13,7 +13,6 @@ import { } from "./logging.js"; import { getSession, - getSessionReadOnly, defaultSessionId, type BrowserSession } from "./sessionManager.js"; @@ -84,7 +83,6 @@ export class Context { this.stagehands.delete(sessionId); } } - public async getActivePage(): Promise { // Try to get page from Stagehand first (if available for this session) const stagehand = this.stagehands.get(this.currentSessionId); @@ -94,79 +92,21 @@ export class Context { // Fallback to session manager const session = await getSession(this.currentSessionId, this.config); - if (!session || !session.page || session.page.isClosed()) { - try { - const currentSession = await getSession( - this.currentSessionId, - this.config - ); - if ( - !currentSession || - !currentSession.page || - currentSession.page.isClosed() - ) { - return null; - } - return currentSession.page; - } catch (refreshError) { - return null; - } - } - return session.page; - } - - // Will create a new default session if one doesn't exist - public async getActiveBrowser(): Promise { - const session = await getSession(this.currentSessionId, this.config); - if (!session || !session.browser || !session.browser.isConnected()) { - try { - const currentSession = await getSession( - this.currentSessionId, - this.config - ); - if ( - !currentSession || - !currentSession.browser || - !currentSession.browser.isConnected() - ) { - return null; - } - return currentSession.browser; - } catch (refreshError) { - return null; - } + if (session && session.page && !session.page.isClosed()) { + return session.page; } - return session.browser; + + return null; } - /** - * Get the active browser without triggering session creation. - * This is a read-only operation used when we need to check for an existing browser - * without side effects (e.g., during close operations). - * @returns The browser if it exists and is connected, null otherwise - */ - public getActiveBrowserReadOnly(): BrowserSession["browser"] | null { - const session = getSessionReadOnly(this.currentSessionId); + public async getActiveBrowser(createIfMissing: boolean = true): Promise { + const session = await getSession(this.currentSessionId, this.config, createIfMissing); if (!session || !session.browser || !session.browser.isConnected()) { return null; } return session.browser; } - /** - * Get the active page without triggering session creation. - * This is a read-only operation used when we need to check for an existing page - * without side effects. - * @returns The page if it exists and is not closed, null otherwise - */ - public getActivePageReadOnly(): BrowserSession["page"] | null { - const session = getSessionReadOnly(this.currentSessionId); - if (!session || !session.page || session.page.isClosed()) { - return null; - } - return session.page; - } - async run(tool: any, args: any): Promise { try { log(`Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`, 'info'); @@ -203,6 +143,10 @@ export class Context { } } + /** + * List resources + * Documentation: https://modelcontextprotocol.io/docs/concepts/resources + */ listResources() { return listResources(); } diff --git a/stagehand/src/sessionManager.ts b/stagehand/src/sessionManager.ts index 25439e6..35015d6 100644 --- a/stagehand/src/sessionManager.ts +++ b/stagehand/src/sessionManager.ts @@ -22,7 +22,7 @@ const browsers = new Map(); let defaultBrowserSession: BrowserSession | null = null; // Define a specific ID for the default session -export const defaultSessionId = "browserbase_session_main"; +export const defaultSessionId = `browserbase_session_main_${Date.now()}`; // Keep track of the active session ID. Defaults to the main session. let activeSessionId: string = defaultSessionId; @@ -277,9 +277,10 @@ export async function ensureDefaultSessionInternal( // Get a specific session by ID export async function getSession( sessionId: string, - config: Config + config: Config, + createIfMissing: boolean = true ): Promise { - if (sessionId === defaultSessionId) { + if (sessionId === defaultSessionId && createIfMissing) { try { return await ensureDefaultSessionInternal(config); } catch (error) { @@ -324,37 +325,6 @@ export async function getSession( return sessionObj; } -/** - * Get a session by ID without creating new sessions. - * This is a read-only operation that never triggers session creation. - * Used for operations like closing sessions where we don't want side effects. - * @param sessionId The session ID to retrieve - * @returns The session if it exists and is valid, null otherwise - */ -export function getSessionReadOnly(sessionId: string): BrowserSession | null { - // Check if it's the default session - if (sessionId === defaultSessionId && defaultBrowserSession) { - // Only return if it's actually connected and valid - if (defaultBrowserSession.browser.isConnected() && !defaultBrowserSession.page.isClosed()) { - return defaultBrowserSession; - } - return null; - } - - // For non-default sessions, check the browsers map - const sessionObj = browsers.get(sessionId); - if (!sessionObj) { - return null; - } - - // Validate the session is still active - if (!sessionObj.browser.isConnected() || sessionObj.page.isClosed()) { - return null; - } - - return sessionObj; -} - /** * Clean up a session by removing it from tracking. * This is called after a browser is closed to ensure proper cleanup. diff --git a/stagehand/src/tools/session.ts b/stagehand/src/tools/session.ts index b095a82..19970c1 100644 --- a/stagehand/src/tools/session.ts +++ b/stagehand/src/tools/session.ts @@ -144,7 +144,7 @@ async function handleCloseSession( // Step 1: Attempt to get the active browser instance WITHOUT creating a new one try { // Use read-only version to avoid creating new sessions - browser = context.getActiveBrowserReadOnly(); + browser = await context.getActiveBrowser(false); } catch (error: any) { process.stderr.write( `[tool.closeSession] Error retrieving active browser (session ID was ${previousSessionId || 'default/unknown'}): ${error.message || String(error)}` From e2431edb5a15fd4bdcb2644b45db6a4412489669 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 25 Jun 2025 16:11:30 -0700 Subject: [PATCH 05/32] cleanup tools --- stagehand/config.d.ts | 12 ------------ stagehand/src/config.ts | 1 - stagehand/src/tools/act.ts | 2 -- stagehand/src/tools/extract.ts | 2 -- stagehand/src/tools/navigate.ts | 2 -- stagehand/src/tools/observe.ts | 2 -- stagehand/src/tools/screenshot.ts | 2 -- stagehand/src/tools/session.ts | 6 ------ stagehand/src/tools/tool.ts | 3 --- stagehand/src/transport.ts | 3 +-- 10 files changed, 1 insertion(+), 34 deletions(-) diff --git a/stagehand/config.d.ts b/stagehand/config.d.ts index 4950123..984591c 100644 --- a/stagehand/config.d.ts +++ b/stagehand/config.d.ts @@ -70,16 +70,4 @@ export type Config = { */ host?: string; }; - tools?: { - /** - * Configuration for the browser_take_screenshot tool. - */ - browserbase_take_screenshot?: { - /** - * Whether to disable base64-encoded image responses to the clients that - * don't support binary data or prefer to save on tokens. - */ - omitBase64?: boolean; - } - } }; \ No newline at end of file diff --git a/stagehand/src/config.ts b/stagehand/src/config.ts index d72f9af..5c83467 100644 --- a/stagehand/src/config.ts +++ b/stagehand/src/config.ts @@ -45,7 +45,6 @@ export async function resolveConfig(cliOptions: CLIOptions): Promise { const mergedConfig = mergeConfig(defaultConfig, cliConfig); // --- Add Browserbase Env Vars --- - // Ensure env vars are read *after* dotenv potentially runs (in index.ts) if (!mergedConfig.browserbaseApiKey) { mergedConfig.browserbaseApiKey = process.env.BROWSERBASE_API_KEY; } diff --git a/stagehand/src/tools/act.ts b/stagehand/src/tools/act.ts index a5aa808..a80f5a2 100644 --- a/stagehand/src/tools/act.ts +++ b/stagehand/src/tools/act.ts @@ -58,8 +58,6 @@ async function handleAct( return { action, - captureSnapshot: false, - code: [], waitForNetwork: false, }; } diff --git a/stagehand/src/tools/extract.ts b/stagehand/src/tools/extract.ts index 0e0daf8..b251e46 100644 --- a/stagehand/src/tools/extract.ts +++ b/stagehand/src/tools/extract.ts @@ -65,8 +65,6 @@ async function handleExtract( return { action, - captureSnapshot: false, - code: [], waitForNetwork: false, }; } diff --git a/stagehand/src/tools/navigate.ts b/stagehand/src/tools/navigate.ts index e663d00..7528e97 100644 --- a/stagehand/src/tools/navigate.ts +++ b/stagehand/src/tools/navigate.ts @@ -49,8 +49,6 @@ async function handleNavigate( return { action, - captureSnapshot: false, - code: [], waitForNetwork: false, }; } diff --git a/stagehand/src/tools/observe.ts b/stagehand/src/tools/observe.ts index cd2adb1..3aace9f 100644 --- a/stagehand/src/tools/observe.ts +++ b/stagehand/src/tools/observe.ts @@ -46,8 +46,6 @@ async function handleObserve( return { action, - captureSnapshot: false, - code: [], waitForNetwork: false, }; } diff --git a/stagehand/src/tools/screenshot.ts b/stagehand/src/tools/screenshot.ts index 94e1227..5e7a7f0 100644 --- a/stagehand/src/tools/screenshot.ts +++ b/stagehand/src/tools/screenshot.ts @@ -69,8 +69,6 @@ async function handleScreenshot( return { action, - captureSnapshot: false, - code: [], waitForNetwork: false, }; } diff --git a/stagehand/src/tools/session.ts b/stagehand/src/tools/session.ts index 19970c1..9f0db4d 100644 --- a/stagehand/src/tools/session.ts +++ b/stagehand/src/tools/session.ts @@ -98,8 +98,6 @@ async function handleCreateSession( // Return the ToolResult structure expected by Context.run return { action: action, - captureSnapshot: false, - code: [], waitForNetwork: false, }; } @@ -131,8 +129,6 @@ async function handleCloseSession( context: Context, _params: CloseSessionInput ): Promise { - const code = [`// Attempting to close the current Browserbase session.`]; - const action = async (): Promise => { // Store the current session ID before it's potentially changed. // This allows us to reference the original session ID later if needed. @@ -217,8 +213,6 @@ async function handleCloseSession( return { action: action, - code: code, - captureSnapshot: false, waitForNetwork: false, }; } diff --git a/stagehand/src/tools/tool.ts b/stagehand/src/tools/tool.ts index 7351838..a78f231 100644 --- a/stagehand/src/tools/tool.ts +++ b/stagehand/src/tools/tool.ts @@ -17,11 +17,8 @@ export type InputType = z.Schema; export type ToolActionResult = { content?: (ImageContent | TextContent)[] } | undefined | void; export type ToolResult = { - code: string[]; action?: () => Promise; - captureSnapshot: boolean; waitForNetwork: boolean; - resultOverride?: ToolActionResult; }; export type Tool = { diff --git a/stagehand/src/transport.ts b/stagehand/src/transport.ts index 82a703a..a69177c 100644 --- a/stagehand/src/transport.ts +++ b/stagehand/src/transport.ts @@ -34,8 +34,7 @@ async function handleSSE(req: http.IncomingMessage, res: http.ServerResponse, ur res.on('close', () => { sessions.delete(transport.sessionId); serverList.close(server).catch(e => { - // eslint-disable-next-line no-console - // console.error(e); + console.error(e); }); }); return await server.connect(transport); From c5a8d665ddefedc95006ea20961081e2cb54c1e7 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 25 Jun 2025 17:46:48 -0700 Subject: [PATCH 06/32] remove unnecessary logger, updated readme, converted to smithery, custom models in config, session manager migrated to only use stagehand, rm browserbase SDK, remove unnecessary functions --- stagehand/README.md | 504 ++++++++++++++---- stagehand/config.d.ts | 8 + stagehand/package-lock.json | 843 ++++++++++++++++++++++++++++-- stagehand/package.json | 7 +- stagehand/smithery.config.js | 10 + stagehand/smithery.yaml | 1 + stagehand/src/config.ts | 4 + stagehand/src/context.ts | 93 +--- stagehand/src/index.ts | 180 +++---- stagehand/src/logging.ts | 222 -------- stagehand/src/program.ts | 23 +- stagehand/src/sessionManager.ts | 123 +++-- stagehand/src/tools/act.ts | 1 + stagehand/src/tools/extract.ts | 1 + stagehand/src/tools/index.ts | 9 - stagehand/src/tools/navigate.ts | 1 - stagehand/src/tools/observe.ts | 1 + stagehand/src/tools/screenshot.ts | 4 +- stagehand/src/tools/session.ts | 92 ++-- 19 files changed, 1457 insertions(+), 670 deletions(-) create mode 100644 stagehand/smithery.config.js create mode 100644 stagehand/smithery.yaml delete mode 100644 stagehand/src/logging.ts diff --git a/stagehand/README.md b/stagehand/README.md index 816d287..0b2f8dc 100644 --- a/stagehand/README.md +++ b/stagehand/README.md @@ -1,66 +1,316 @@ -# Stagehand MCP Server +# Browserbase MCP Server -![cover](../assets/stagehand-mcp.png) +![cover](../assets/browserbase-mcp.png) -A Model Context Protocol (MCP) server that provides AI-powered web automation capabilities using [Stagehand](https://github.com/browserbase/stagehand). This server enables LLMs to interact with web pages, perform actions, extract data, and observe possible actions in a real browser environment. +The Model Context Protocol (MCP) is an open protocol that enables seamless integration between LLM applications and external data sources and tools. Whether you're building an AI-powered IDE, enhancing a chat interface, or creating custom AI workflows, MCP provides a standardized way to connect LLMs with the context they need. -## Get Started + + +## How to Setup + +### Quickstarts: + +[![Install MCP Server](https://cursor.com/deeplink/mcp-install-dark.png)](cursor://anysphere.cursor-deeplink/mcp/install?name=browserbase&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyJAYnJvd3NlcmJhc2VocS9tY3AiXSwiZW52Ijp7IkJST1dTRVJCQVNFX0FQSV9LRVkiOiIiLCJCUk9XU0VSQkFTRV9QUk9KRUNUX0lEIjoiIn19) -1. Run `npm install` to install the necessary dependencies, then run `npm run build` to get `dist/index.js`. +You can either use our Server hosted on NPM or run it completely locally by cloning this repo. -2. Set up your Claude Desktop configuration to use the server. +### To run on NPM (Recommended) + +Go into your MCP Config JSON and add the Browserbase Server: ```json { - "mcpServers": { - "stagehand": { - "command": "node", - "args": ["path/to/mcp-server-browserbase/stagehand/dist/index.js"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "", - "OPENAI_API_KEY": "", - "CONTEXT_ID": "" + "mcpServers": { + "browserbase": { + "command": "npx", + "args" : ["@browserbasehq/mcp"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } } - } - } + } } ``` -or, for running locally, first [**open Chrome in debug mode**](https://docs.stagehand.dev/examples/customize_browser#use-your-personal-browser) like so: -`open -a "Google Chrome" --args --remote-debugging-port=9222` +Thats it! Reload your MCP client and Claude will be able to use Browserbase. + +### To run 100% local: + +```bash +# Clone the Repo +git clone https://github.com/browserbase/mcp-server-browserbase.git + +# Install the dependencies in the proper directory and build the project +cd stagehand +npm install && npm run build + +``` + +Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. + +### STDIO: + +To your MCP Config JSON file add the following: + ```json { - "mcpServers": { - "stagehand": { - "command": "node", - "args": ["path/to/mcp-server-browserbase/stagehand/dist/index.js"], +"mcpServers": { + "browserbase": { + "command" : "node", + "args" : ["/path/to/mcp-server-browserbase/stagehand/cli.js"], "env": { - "OPENAI_API_KEY": "", - "LOCAL_CDP_URL": "http://localhost:9222" + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } } - } - } + } } ``` -> 💡 Check out our [documentation](https://docs.stagehand.dev/examples/customize_browser#use-your-personal-browser) for getting your local CDP url! -3. Restart your Claude Desktop app and you should see the tools available clicking the 🔨 icon. +### SSE: -4. Start using the tools! Below is a demo video of Claude doing a Google search for OpenAI using stagehand MCP server and Browserbase for a remote headless browser. +Run the following command in your terminal. You can add any flags (see options below) that you see fit to customize your configuration. - +```bash + node cli.js --port 8931 +``` + +Then in your MCP Config JSON file put the following: + +```json + { + "mcpServers": { + "browserbase": { + "url": "http://localhost:8931/sse", + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } + } +``` + +Then reload your MCP client and you should be good to go! + +## Flags Explained: + +The Browserbase MCP server accepts the following command-line flags: + +| Flag | Description | +|------|-------------| +| `--browserbaseApiKey ` | Your Browserbase API key for authentication | +| `--browserbaseProjectId ` | Your Browserbase project ID | +| `--proxies` | Enable Browserbase proxies for the session | +| `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | +| `--contextId ` | Specify a Browserbase Context ID to use | +| `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | +| `--port ` | Port to listen on for HTTP/SSE transport | +| `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | +| `--cookies [json]` | JSON array of cookies to inject into the browser | +| `--browserWidth ` | Browser viewport width (default: 1024) | +| `--browserHeight ` | Browser viewport height (default: 768) | +| `--modelName ` | The model to use for Stagehand (default: google/gemini-2.0-flash) | + +These flags can be passed directly to the CLI or configured in your MCP configuration file. + +### NOTE: + +Currently, these flags can only be used with the local server (npx @browserbasehq/mcp). + +____ + +## Flags & Example Configs + +### Proxies + +Here are our docs on [Proxies](https://docs.browserbase.com/features/proxies). + +To use proxies in STDIO, set the --proxies flag in your MCP Config: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : ["@browserbasehq/mcp", "--proxies"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` +### Advanced Stealth + +Here are our docs on [Advanced Stealth](https://docs.browserbase.com/features/stealth-mode#advanced-stealth-mode). + +To use proxies in STDIO, set the --advancedStealth flag in your MCP Config: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : ["@browserbasehq/mcp", "--advancedStealth"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Contexts + +Here are our docs on [Contexts](https://docs.browserbase.com/features/contexts) + +To use contexts in STDIO, set the --contextId flag in your MCP Config: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : ["@browserbasehq/mcp", "--contextId", ""], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Cookie Injection + +Why would you need to inject cookies? Our context API currently works on persistent cookies, but not session cookies. So sometimes our persistent auth might not work (we're working hard to add this functionality). + +You can flag cookies into the MCP by adding the cookies.json to your MCP Config. + +To use proxies in STDIO, set the --proxies flag in your MCP Config. Your cookies JSON must be in the type of [Playwright Cookies](https://playwright.dev/docs/api/class-browsercontext#browser-context-cookies) + +```json +{ + "mcpServers": { + "browserbase" { + "command" : "npx", + "args" : [ + "@browserbasehq/mcp", "--cookies", + '{ + "cookies": json, + }' + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Browser Viewport Sizing + +The default viewport sizing for a browser session is 1024 x 768. You can adjust the Browser viewport sizing with browserWidth and browserHeight flags. + +Here's how to use it for custom browser sizing. We recommend to stick with 16:9 aspect ratios (ie: 1920 x 1080, 1280, 720, 1024 x 768) + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : [ + "@browserbasehq/mcp", + "--browserHeight 1080", + "--browserWidth 1920", + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Model Configuration + +Stagehand defaults to using Google's Gemini 2.0 Flash model, but you can configure it to use other models like GPT-4o, Claude, or other providers. + +Here's how to configure different models: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : [ + "@browserbasehq/mcp", + "--modelName", "gpt-4o", + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +Available models include: +- **Gemini**: `google/gemini-2.0-flash` (default), `google/gemini-1.5-pro`, `google/gemini-1.5-flash` +- **OpenAI**: `gpt-4o`, `gpt-4o-mini`, `o1-mini`, `o1-preview`, `o3-mini` +- **Claude**: `claude-3-5-sonnet-latest`, `claude-3-7-sonnet-latest` +- **Other providers**: Cerebras, Groq, and more + +* Note: +The model must be supported in Stagehand. Checkout the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms). + +## Structure + +* `src/`: TypeScript source code + * `index.ts`: Main entry point and Smithery default export function + * `config.ts`: Configuration management and CLI option parsing + * `context.ts`: Context class managing Stagehand instances and tool execution + * `logging.ts`: Comprehensive logging system with file rotation + * `program.ts`: CLI program setup using Commander.js + * `prompts.ts`: Prompt templates for MCP clients + * `resources.ts`: Resource management for screenshots + * `server.ts`: Server list management for multiple server instances + * `sessionManager.ts`: Browserbase session creation and lifecycle management + * `transport.ts`: HTTP/SSE and STDIO transport handlers + * `utils.ts`: Utility functions for message sanitization + * `tools/`: Tool definitions and implementations + * `act.ts`: Stagehand action execution tool + * `extract.ts`: Page content extraction tool + * `navigate.ts`: URL navigation tool + * `observe.ts`: Element observation tool + * `screenshot.ts`: Screenshot capture tool + * `session.ts`: Session management tools (create/close) + * `tool.ts`: Tool type definitions and interfaces + * `utils.ts`: Tool utility functions +* `dist/`: Compiled JavaScript output +* `tests/`: Placeholder for tests (coming soon) +* `cli.js`: Executable entry point for CLI usage +* `config.d.ts`: TypeScript type definitions for configuration +* `index.d.ts` & `index.js`: Module exports for programmatic usage +* `package.json`: Package metadata and dependencies +* `smithery.config.js` & `smithery.yaml`: Smithery configuration files +* `tsconfig.json`: TypeScript compiler configuration +* Configuration files (`.json`, `.ts`, `.mjs`, `.npmignore`) ## Tools -### Stagehand commands +### Stagehand Tools (Browserbase MCP) - **stagehand_navigate** - Navigate to any URL in the browser @@ -74,87 +324,154 @@ or, for running locally, first [**open Chrome in debug mode**](https://docs.stag - `variables` (object, optional): Variables used in the action template - **stagehand_extract** - - Extract data from the web page + - Extract all text content from the current page (filters out CSS and JavaScript) + - No inputs required - **stagehand_observe** - Observe actions that can be performed on the web page - Input: - - `instruction` (string, optional): Instruction for observation + - `instruction` (string): Specific instruction for observation (e.g., "find the login button") -### Resources +- **screenshot** + - Capture a PNG screenshot of the current page + - Output: + - `text`: Friendly confirmation message with the screenshot name + - `image`: Base-64 encoded PNG data + +### Session Management Tools -The server provides access to one resource: +- **browserbase_session_create** + - Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand + - Applies all configuration flags (proxies, stealth, viewport, cookies, etc.) + - Initializes Stagehand instance connected to the browser session + - Input: + - `sessionId` (string, optional): Optional session ID to use/reuse. If not provided, creates new session + - Output: + - Live debugger URL for the Browserbase session -1. **Console Logs** (`console://logs`) +- **browserbase_session_close** + - Close the current Browserbase session, disconnect the browser, and cleanup Stagehand instance + - Input: + - `random_string` (string, optional): Dummy parameter for consistent tool call format + - Output: + - Confirmation message and session replay URL - - Browser console output in text format - - Includes all console messages from the browser +### Resources -2. **Screenshots** (`screenshot://`) +The server provides access to screenshot resources: + +1. **Screenshots** (`screenshot://`) - PNG images of captured screenshots - - Accessible via the screenshot name specified during capture ## File Structure -The codebase is organized into the following modules: - -- **index.ts**: Entry point that initializes and runs the server. -- **server.ts**: Core server logic, including server creation, configuration, and request handling. -- **tools.ts**: Definitions and implementations of tools that can be called by MCP clients. -- **prompts.ts**: Prompt templates that can be used by MCP clients. -- **resources.ts**: Resource definitions and handlers for resource-related requests. -- **logging.ts**: Comprehensive logging system with rotation and formatting capabilities. -- **utils.ts**: Utility functions including JSON Schema to Zod schema conversion and message sanitization. +The Stagehand MCP server codebase is organized into the following key modules: + +- **index.ts**: Smithery default export function that creates and configures the MCP server +- **config.ts**: Configuration management, CLI option parsing, and environment variable handling +- **context.ts**: Context class that manages Stagehand instances, tool execution, and browser sessions +- **program.ts**: CLI program setup using Commander.js with all command-line options +- **server.ts**: Server list management for handling multiple server instances +- **sessionManager.ts**: Browserbase session creation, lifecycle management, and cleanup +- **transport.ts**: HTTP/SSE and STDIO transport handlers for different connection types +- **logging.ts**: Comprehensive logging system with file rotation and in-memory logs +- **prompts.ts**: Prompt templates for MCP clients +- **resources.ts**: Screenshot resource management and URI handling +- **utils.ts**: Message sanitization utilities +- **tools/**: Individual tool implementations with type-safe schemas ## Module Descriptions ### index.ts -The main entry point for the application. It: -- Initializes the logging system -- Creates the server instance -- Connects to the stdio transport to receive and respond to requests +The Smithery default export function that: +- Defines the configuration schema with Zod validation +- Creates the MCP server instance with proper metadata +- Registers all tools with their schemas and handlers +- Returns the configured server for use by Smithery or direct imports + +### config.ts + +Configuration management module that: +- Defines CLI option types and default values +- Resolves configuration from environment variables, CLI args, and defaults +- Provides utility functions for file paths and config merging +- Handles Browserbase API key and project ID validation + +### context.ts + +The main Context class that: +- Manages Stagehand instances per session with lifecycle handling +- Executes tool actions with proper error handling and logging +- Provides access to active browser pages and sessions +- Handles resource listing and reading for screenshots +- Coordinates between tools, sessions, and the MCP server + +### program.ts + +CLI program setup using Commander.js that: +- Defines all command-line options and flags +- Parses arguments and resolves final configuration +- Sets up exit handlers for graceful shutdown +- Starts either HTTP/SSE or STDIO transport based on options ### server.ts -Contains core server functionality: -- Creates and configures the MCP server -- Defines Stagehand configuration -- Sets up request handlers for all MCP operations -- Manages the Stagehand browser instance +Server list management that: +- Maintains multiple server instances for different connections +- Provides factory pattern for server creation +- Handles server lifecycle and cleanup +- Manages concurrent server connections + +### sessionManager.ts -### tools.ts +Browserbase session management that: +- Creates and connects to Browserbase sessions via CDP +- Manages session lifecycle with automatic cleanup +- Handles default and custom session IDs +- Provides cookie injection and context management +- Tracks active sessions and handles disconnections -Implements the tools that can be called by MCP clients: -- `stagehand_navigate`: Navigate to URLs -- `stagehand_act`: Perform actions on web elements -- `stagehand_extract`: Extract structured data from web pages -- `stagehand_observe`: Observe elements on the page -- `screenshot`: Take screenshots of the current page +### transport.ts + +Transport layer implementations for: +- STDIO transport for direct MCP communication +- HTTP/SSE transport for web-based connections +- Streamable HTTP transport for advanced clients +- Session management across different transport types ### prompts.ts -Defines prompt templates for MCP clients: -- `click_search_button`: Template for clicking search buttons +Prompt template definitions: +- Exports available prompts list +- Provides `click_search_button` template +- Handles prompt retrieval by name with validation ### resources.ts -Manages resources in the MCP protocol: -- Currently provides empty resource and resource template lists +Resource management for the MCP protocol: +- Manages screenshot storage in memory +- Provides resource listing for available screenshots +- Handles resource URI resolution and content retrieval +- Returns base64-encoded PNG data for screenshot resources -### logging.ts +### utils.ts -Implements a comprehensive logging system: -- File-based logging with rotation -- In-memory operation logs -- Log formatting and sanitization -- Console logging for debugging +Message sanitization utilities: +- `sanitizeMessage`: Ensures proper JSON formatting for MCP messages +- Error handling for malformed JSON with fallback responses -### utils.ts +### tools/ Directory -Provides utility functions: -- `jsonSchemaToZod`: Converts JSON Schema to Zod schema for validation -- `sanitizeMessage`: Ensures messages are properly formatted JSON +Individual tool implementations with: +- **act.ts**: Stagehand action execution with variable support +- **extract.ts**: Page content extraction with CSS/JS filtering +- **navigate.ts**: URL navigation with network waiting +- **observe.ts**: Element observation with specific instructions +- **screenshot.ts**: Screenshot capture with base64 encoding +- **session.ts**: Session create/close tools with Browserbase integration +- **tool.ts**: Type definitions and interfaces for all tools +- **utils.ts**: Shared utility functions for file path sanitization ## Key Features @@ -169,17 +486,18 @@ Provides utility functions: - `BROWSERBASE_API_KEY`: API key for BrowserBase authentication - `BROWSERBASE_PROJECT_ID`: Project ID for BrowserBase -- `OPENAI_API_KEY`: API key for OpenAI (used by Stagehand) - `DEBUG`: Enable debug logging ## MCP Capabilities This server implements the following MCP capabilities: -- **Tools**: Allows clients to call tools that control a browser instance -- **Prompts**: Provides prompt templates for common operations -- **Resources**: (Currently empty but structured for future expansion) -- **Logging**: Provides detailed logging capabilities +- **Tools**: Provides 7 tools for browser automation: + - Stagehand tools: navigate, act, extract, observe, screenshot + - Session management: create and close Browserbase sessions +- **Prompts**: Provides prompt templates (click_search_button) +- **Resources**: Screenshot resource management with URI-based access +- **Logging**: Comprehensive logging with file rotation and MCP integration For more information about the Model Context Protocol, visit: - [MCP Documentation](https://modelcontextprotocol.io/docs) @@ -189,4 +507,4 @@ For more information about the Model Context Protocol, visit: Licensed under the MIT License. -Copyright 2024 Browserbase, Inc. +Copyright 2025 Browserbase, Inc. \ No newline at end of file diff --git a/stagehand/config.d.ts b/stagehand/config.d.ts index 984591c..f6e1725 100644 --- a/stagehand/config.d.ts +++ b/stagehand/config.d.ts @@ -1,4 +1,5 @@ import type { Cookie } from "playwright-core"; +import type { AvailableModelSchema } from "@browserbasehq/stagehand"; export type Config = { /** @@ -70,4 +71,11 @@ export type Config = { */ host?: string; }; + /** + * The Model that Stagehand uses + * Available models: OpenAI, Claude, Gemini, Cerebras, Groq, and other providers + * + * @default "google/gemini-2.0-flash" + */ + modelName?: AvailableModelSchema; }; \ No newline at end of file diff --git a/stagehand/package-lock.json b/stagehand/package-lock.json index cc0ac3a..dd0977b 100644 --- a/stagehand/package-lock.json +++ b/stagehand/package-lock.json @@ -1,28 +1,306 @@ { - "name": "@browserbasehq/mcp-stagehand", + "name": "@browserbasehq/mcp", "version": "0.5.1", "lockfileVersion": 3, "requires": true, "packages": { "": { - "name": "@browserbasehq/mcp-stagehand", + "name": "@browserbasehq/mcp", "version": "0.5.1", "license": "MIT", "dependencies": { - "@browserbasehq/sdk": "^2.0.0", - "@browserbasehq/stagehand": "^2.0.0", - "@modelcontextprotocol/sdk": "^1.13.0", + "@browserbasehq/stagehand": "^2.4.0", + "@modelcontextprotocol/sdk": "^1.13.1", "@playwright/test": "^1.49.0", "commander": "^14.0.0" }, "bin": { - "mcp-server-stagehand": "dist/index.js" + "mcp-server-stagehand": "cli.js" }, "devDependencies": { "shx": "^0.3.4", "typescript": "^5.6.2" } }, + "node_modules/@ai-sdk/anthropic": { + "version": "1.2.12", + "resolved": "https://registry.npmjs.org/@ai-sdk/anthropic/-/anthropic-1.2.12.tgz", + "integrity": "sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/azure": { + "version": "1.3.23", + "resolved": "https://registry.npmjs.org/@ai-sdk/azure/-/azure-1.3.23.tgz", + "integrity": "sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/openai": "1.3.22", + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/cerebras": { + "version": "0.2.14", + "resolved": "https://registry.npmjs.org/@ai-sdk/cerebras/-/cerebras-0.2.14.tgz", + "integrity": "sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/openai-compatible": "0.2.14", + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/deepseek": { + "version": "0.2.14", + "resolved": "https://registry.npmjs.org/@ai-sdk/deepseek/-/deepseek-0.2.14.tgz", + "integrity": "sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/openai-compatible": "0.2.14", + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/google": { + "version": "1.2.19", + "resolved": "https://registry.npmjs.org/@ai-sdk/google/-/google-1.2.19.tgz", + "integrity": "sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/groq": { + "version": "1.2.9", + "resolved": "https://registry.npmjs.org/@ai-sdk/groq/-/groq-1.2.9.tgz", + "integrity": "sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/mistral": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@ai-sdk/mistral/-/mistral-1.2.8.tgz", + "integrity": "sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/openai": { + "version": "1.3.22", + "resolved": "https://registry.npmjs.org/@ai-sdk/openai/-/openai-1.3.22.tgz", + "integrity": "sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/openai-compatible": { + "version": "0.2.14", + "resolved": "https://registry.npmjs.org/@ai-sdk/openai-compatible/-/openai-compatible-0.2.14.tgz", + "integrity": "sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/perplexity": { + "version": "1.1.9", + "resolved": "https://registry.npmjs.org/@ai-sdk/perplexity/-/perplexity-1.1.9.tgz", + "integrity": "sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/provider": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@ai-sdk/provider/-/provider-1.1.3.tgz", + "integrity": "sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==", + "license": "Apache-2.0", + "dependencies": { + "json-schema": "^0.4.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@ai-sdk/provider-utils": { + "version": "2.2.8", + "resolved": "https://registry.npmjs.org/@ai-sdk/provider-utils/-/provider-utils-2.2.8.tgz", + "integrity": "sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "nanoid": "^3.3.8", + "secure-json-parse": "^2.7.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.23.8" + } + }, + "node_modules/@ai-sdk/react": { + "version": "1.2.12", + "resolved": "https://registry.npmjs.org/@ai-sdk/react/-/react-1.2.12.tgz", + "integrity": "sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider-utils": "2.2.8", + "@ai-sdk/ui-utils": "1.2.11", + "swr": "^2.2.5", + "throttleit": "2.1.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "react": "^18 || ^19 || ^19.0.0-rc", + "zod": "^3.23.8" + }, + "peerDependenciesMeta": { + "zod": { + "optional": true + } + } + }, + "node_modules/@ai-sdk/togetherai": { + "version": "0.2.14", + "resolved": "https://registry.npmjs.org/@ai-sdk/togetherai/-/togetherai-0.2.14.tgz", + "integrity": "sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/openai-compatible": "0.2.14", + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, + "node_modules/@ai-sdk/ui-utils": { + "version": "1.2.11", + "resolved": "https://registry.npmjs.org/@ai-sdk/ui-utils/-/ui-utils-1.2.11.tgz", + "integrity": "sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8", + "zod-to-json-schema": "^3.24.1" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.23.8" + } + }, + "node_modules/@ai-sdk/xai": { + "version": "1.2.16", + "resolved": "https://registry.npmjs.org/@ai-sdk/xai/-/xai-1.2.16.tgz", + "integrity": "sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/openai-compatible": "0.2.14", + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + } + }, "node_modules/@anthropic-ai/sdk": { "version": "0.39.0", "resolved": "https://registry.npmjs.org/@anthropic-ai/sdk/-/sdk-0.39.0.tgz", @@ -54,30 +332,91 @@ } }, "node_modules/@browserbasehq/stagehand": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@browserbasehq/stagehand/-/stagehand-2.0.0.tgz", - "integrity": "sha512-zYSuF/mjq3579ezPWlvMkGTJacSFhz4bEkimstgb6V+ychdFocAMwuF9SrTPmJF5dYUK8FR1nbjZ52+w2sRRoQ==", + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/@browserbasehq/stagehand/-/stagehand-2.4.0.tgz", + "integrity": "sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==", "license": "MIT", "dependencies": { "@anthropic-ai/sdk": "0.39.0", "@browserbasehq/sdk": "^2.4.0", + "@google/genai": "^0.8.0", + "ai": "^4.3.9", + "devtools-protocol": "^0.0.1464554", + "fetch-cookie": "^3.1.0", + "openai": "^4.87.1", + "pino": "^9.6.0", + "pino-pretty": "^13.0.0", + "playwright": "^1.52.0", "ws": "^8.18.0", "zod-to-json-schema": "^3.23.5" }, + "optionalDependencies": { + "@ai-sdk/anthropic": "^1.2.6", + "@ai-sdk/azure": "^1.3.19", + "@ai-sdk/cerebras": "^0.2.6", + "@ai-sdk/deepseek": "^0.2.13", + "@ai-sdk/google": "^1.2.6", + "@ai-sdk/groq": "^1.2.4", + "@ai-sdk/mistral": "^1.2.7", + "@ai-sdk/openai": "^1.0.14", + "@ai-sdk/perplexity": "^1.1.7", + "@ai-sdk/togetherai": "^0.2.6", + "@ai-sdk/xai": "^1.2.15", + "ollama-ai-provider": "^1.2.0" + }, "peerDependencies": { - "@playwright/test": "^1.42.1", "deepmerge": "^4.3.1", "dotenv": "^16.4.5", - "openai": "^4.87.1", - "pino": "^9.6.0", - "pino-pretty": "^13.0.0", "zod": "^3.23.8" } }, + "node_modules/@browserbasehq/stagehand/node_modules/playwright": { + "version": "1.53.1", + "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.53.1.tgz", + "integrity": "sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==", + "license": "Apache-2.0", + "dependencies": { + "playwright-core": "1.53.1" + }, + "bin": { + "playwright": "cli.js" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "fsevents": "2.3.2" + } + }, + "node_modules/@browserbasehq/stagehand/node_modules/playwright-core": { + "version": "1.53.1", + "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.53.1.tgz", + "integrity": "sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==", + "license": "Apache-2.0", + "bin": { + "playwright-core": "cli.js" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@google/genai": { + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/@google/genai/-/genai-0.8.0.tgz", + "integrity": "sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==", + "license": "Apache-2.0", + "dependencies": { + "google-auth-library": "^9.14.2", + "ws": "^8.18.0" + }, + "engines": { + "node": ">=18.0.0" + } + }, "node_modules/@modelcontextprotocol/sdk": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.13.0.tgz", - "integrity": "sha512-P5FZsXU0kY881F6Hbk9GhsYx02/KgWK1DYf7/tyE/1lcFKhDYPQR9iYjhQXJn+Sg6hQleMo3DB7h7+p4wgp2Lw==", + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.13.1.tgz", + "integrity": "sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==", "license": "MIT", "dependencies": { "ajv": "^6.12.6", @@ -96,6 +435,15 @@ "node": ">=18" } }, + "node_modules/@opentelemetry/api": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.0.tgz", + "integrity": "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==", + "license": "Apache-2.0", + "engines": { + "node": ">=8.0.0" + } + }, "node_modules/@playwright/test": { "version": "1.51.0", "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.51.0.tgz", @@ -111,6 +459,12 @@ "node": ">=18" } }, + "node_modules/@types/diff-match-patch": { + "version": "1.0.36", + "resolved": "https://registry.npmjs.org/@types/diff-match-patch/-/diff-match-patch-1.0.36.tgz", + "integrity": "sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==", + "license": "MIT" + }, "node_modules/@types/node": { "version": "18.19.80", "resolved": "https://registry.npmjs.org/@types/node/-/node-18.19.80.tgz", @@ -155,6 +509,15 @@ "node": ">= 0.6" } }, + "node_modules/agent-base": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.3.tgz", + "integrity": "sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==", + "license": "MIT", + "engines": { + "node": ">= 14" + } + }, "node_modules/agentkeepalive": { "version": "4.6.0", "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.6.0.tgz", @@ -167,6 +530,32 @@ "node": ">= 8.0.0" } }, + "node_modules/ai": { + "version": "4.3.16", + "resolved": "https://registry.npmjs.org/ai/-/ai-4.3.16.tgz", + "integrity": "sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==", + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8", + "@ai-sdk/react": "1.2.12", + "@ai-sdk/ui-utils": "1.2.11", + "@opentelemetry/api": "1.9.0", + "jsondiffpatch": "0.6.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "react": "^18 || ^19 || ^19.0.0-rc", + "zod": "^3.23.8" + }, + "peerDependenciesMeta": { + "react": { + "optional": true + } + } + }, "node_modules/ajv": { "version": "6.12.6", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", @@ -194,7 +583,6 @@ "resolved": "https://registry.npmjs.org/atomic-sleep/-/atomic-sleep-1.0.0.tgz", "integrity": "sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==", "license": "MIT", - "peer": true, "engines": { "node": ">=8.0.0" } @@ -206,6 +594,35 @@ "dev": true, "license": "MIT" }, + "node_modules/base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/bignumber.js": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.3.0.tgz", + "integrity": "sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==", + "license": "MIT", + "engines": { + "node": "*" + } + }, "node_modules/body-parser": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.1.0.tgz", @@ -275,6 +692,12 @@ "concat-map": "0.0.1" } }, + "node_modules/buffer-equal-constant-time": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", + "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==", + "license": "BSD-3-Clause" + }, "node_modules/bytes": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", @@ -313,12 +736,23 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/chalk": { + "version": "5.4.1", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", + "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", + "license": "MIT", + "engines": { + "node": "^12.17.0 || ^14.13 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, "node_modules/colorette": { "version": "2.0.20", "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/combined-stream": { "version": "1.0.8", @@ -419,7 +853,6 @@ "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-4.6.3.tgz", "integrity": "sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==", "license": "MIT", - "peer": true, "engines": { "node": "*" } @@ -469,6 +902,15 @@ "node": ">= 0.8" } }, + "node_modules/dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/destroy": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", @@ -479,6 +921,18 @@ "npm": "1.2.8000 || >= 1.4.16" } }, + "node_modules/devtools-protocol": { + "version": "0.0.1464554", + "resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1464554.tgz", + "integrity": "sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==", + "license": "BSD-3-Clause" + }, + "node_modules/diff-match-patch": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/diff-match-patch/-/diff-match-patch-1.0.5.tgz", + "integrity": "sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==", + "license": "Apache-2.0" + }, "node_modules/dotenv": { "version": "16.4.7", "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.4.7.tgz", @@ -506,6 +960,15 @@ "node": ">= 0.4" } }, + "node_modules/ecdsa-sig-formatter": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", + "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", + "license": "Apache-2.0", + "dependencies": { + "safe-buffer": "^5.0.1" + } + }, "node_modules/ee-first": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", @@ -526,7 +989,6 @@ "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", "license": "MIT", - "peer": true, "dependencies": { "once": "^1.4.0" } @@ -679,12 +1141,17 @@ "express": "^4.11 || 5 || ^5.0.0-beta.1" } }, + "node_modules/extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "license": "MIT" + }, "node_modules/fast-copy": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/fast-copy/-/fast-copy-3.0.2.tgz", "integrity": "sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==", - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/fast-deep-equal": { "version": "3.1.3", @@ -703,7 +1170,6 @@ "resolved": "https://registry.npmjs.org/fast-redact/-/fast-redact-3.5.0.tgz", "integrity": "sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==", "license": "MIT", - "peer": true, "engines": { "node": ">=6" } @@ -712,8 +1178,17 @@ "version": "2.1.1", "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==", - "license": "MIT", - "peer": true + "license": "MIT" + }, + "node_modules/fetch-cookie": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/fetch-cookie/-/fetch-cookie-3.1.0.tgz", + "integrity": "sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==", + "license": "Unlicense", + "dependencies": { + "set-cookie-parser": "^2.4.8", + "tough-cookie": "^5.0.0" + } }, "node_modules/finalhandler": { "version": "2.1.0", @@ -858,6 +1333,36 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/gaxios": { + "version": "6.7.1", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-6.7.1.tgz", + "integrity": "sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==", + "license": "Apache-2.0", + "dependencies": { + "extend": "^3.0.2", + "https-proxy-agent": "^7.0.1", + "is-stream": "^2.0.0", + "node-fetch": "^2.6.9", + "uuid": "^9.0.1" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/gcp-metadata": { + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-6.1.1.tgz", + "integrity": "sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==", + "license": "Apache-2.0", + "dependencies": { + "gaxios": "^6.1.1", + "google-logging-utils": "^0.0.2", + "json-bigint": "^1.0.0" + }, + "engines": { + "node": ">=14" + } + }, "node_modules/get-intrinsic": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", @@ -917,6 +1422,32 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/google-auth-library": { + "version": "9.15.1", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-9.15.1.tgz", + "integrity": "sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==", + "license": "Apache-2.0", + "dependencies": { + "base64-js": "^1.3.0", + "ecdsa-sig-formatter": "^1.0.11", + "gaxios": "^6.1.1", + "gcp-metadata": "^6.1.0", + "gtoken": "^7.0.0", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/google-logging-utils": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-0.0.2.tgz", + "integrity": "sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==", + "license": "Apache-2.0", + "engines": { + "node": ">=14" + } + }, "node_modules/gopd": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", @@ -929,6 +1460,19 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/gtoken": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-7.1.0.tgz", + "integrity": "sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==", + "license": "MIT", + "dependencies": { + "gaxios": "^6.0.0", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=14.0.0" + } + }, "node_modules/has-symbols": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", @@ -972,8 +1516,7 @@ "version": "5.0.0", "resolved": "https://registry.npmjs.org/help-me/-/help-me-5.0.0.tgz", "integrity": "sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==", - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/http-errors": { "version": "2.0.0", @@ -991,6 +1534,19 @@ "node": ">= 0.8" } }, + "node_modules/https-proxy-agent": { + "version": "7.0.6", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", + "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", + "license": "MIT", + "dependencies": { + "agent-base": "^7.1.2", + "debug": "4" + }, + "engines": { + "node": ">= 14" + } + }, "node_modules/humanize-ms": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", @@ -1071,6 +1627,18 @@ "integrity": "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==", "license": "MIT" }, + "node_modules/is-stream": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "license": "MIT", + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", @@ -1082,17 +1650,69 @@ "resolved": "https://registry.npmjs.org/joycon/-/joycon-3.1.1.tgz", "integrity": "sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==", "license": "MIT", - "peer": true, "engines": { "node": ">=10" } }, + "node_modules/json-bigint": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", + "integrity": "sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==", + "license": "MIT", + "dependencies": { + "bignumber.js": "^9.0.0" + } + }, + "node_modules/json-schema": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", + "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==", + "license": "(AFL-2.1 OR BSD-3-Clause)" + }, "node_modules/json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", "license": "MIT" }, + "node_modules/jsondiffpatch": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/jsondiffpatch/-/jsondiffpatch-0.6.0.tgz", + "integrity": "sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==", + "license": "MIT", + "dependencies": { + "@types/diff-match-patch": "^1.0.36", + "chalk": "^5.3.0", + "diff-match-patch": "^1.0.5" + }, + "bin": { + "jsondiffpatch": "bin/jsondiffpatch.js" + }, + "engines": { + "node": "^18.0.0 || >=20.0.0" + } + }, + "node_modules/jwa": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.1.tgz", + "integrity": "sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==", + "license": "MIT", + "dependencies": { + "buffer-equal-constant-time": "^1.0.1", + "ecdsa-sig-formatter": "1.0.11", + "safe-buffer": "^5.0.1" + } + }, + "node_modules/jws": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.0.tgz", + "integrity": "sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==", + "license": "MIT", + "dependencies": { + "jwa": "^2.0.0", + "safe-buffer": "^5.0.1" + } + }, "node_modules/math-intrinsics": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", @@ -1181,6 +1801,24 @@ "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", "license": "MIT" }, + "node_modules/nanoid": { + "version": "3.3.11", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.11.tgz", + "integrity": "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "MIT", + "bin": { + "nanoid": "bin/nanoid.cjs" + }, + "engines": { + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" + } + }, "node_modules/negotiator": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-1.0.0.tgz", @@ -1250,12 +1888,34 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/ollama-ai-provider": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/ollama-ai-provider/-/ollama-ai-provider-1.2.0.tgz", + "integrity": "sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==", + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@ai-sdk/provider": "^1.0.0", + "@ai-sdk/provider-utils": "^2.0.0", + "partial-json": "0.1.7" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.0.0" + }, + "peerDependenciesMeta": { + "zod": { + "optional": true + } + } + }, "node_modules/on-exit-leak-free": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/on-exit-leak-free/-/on-exit-leak-free-2.1.2.tgz", "integrity": "sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==", "license": "MIT", - "peer": true, "engines": { "node": ">=14.0.0" } @@ -1286,7 +1946,6 @@ "resolved": "https://registry.npmjs.org/openai/-/openai-4.92.0.tgz", "integrity": "sha512-vLIBP8gygD5M7XIrdBkUFKnfEq3EmaI+lmGjDDAmjahzmdhwdpzDA+GBA4ZZwj7rgu1WMNh9/SqyTysxMulC2g==", "license": "Apache-2.0", - "peer": true, "dependencies": { "@types/node": "^18.11.18", "@types/node-fetch": "^2.6.4", @@ -1321,6 +1980,13 @@ "node": ">= 0.8" } }, + "node_modules/partial-json": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/partial-json/-/partial-json-0.1.7.tgz", + "integrity": "sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==", + "license": "MIT", + "optional": true + }, "node_modules/path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", @@ -1361,7 +2027,6 @@ "resolved": "https://registry.npmjs.org/pino/-/pino-9.6.0.tgz", "integrity": "sha512-i85pKRCt4qMjZ1+L7sy2Ag4t1atFcdbEt76+7iRJn1g2BvsnRMGu9p8pivl9fs63M2kF/A0OacFZhTub+m/qMg==", "license": "MIT", - "peer": true, "dependencies": { "atomic-sleep": "^1.0.0", "fast-redact": "^3.1.1", @@ -1384,7 +2049,6 @@ "resolved": "https://registry.npmjs.org/pino-abstract-transport/-/pino-abstract-transport-2.0.0.tgz", "integrity": "sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==", "license": "MIT", - "peer": true, "dependencies": { "split2": "^4.0.0" } @@ -1394,7 +2058,6 @@ "resolved": "https://registry.npmjs.org/pino-pretty/-/pino-pretty-13.0.0.tgz", "integrity": "sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==", "license": "MIT", - "peer": true, "dependencies": { "colorette": "^2.0.7", "dateformat": "^4.6.3", @@ -1418,8 +2081,7 @@ "version": "7.0.0", "resolved": "https://registry.npmjs.org/pino-std-serializers/-/pino-std-serializers-7.0.0.tgz", "integrity": "sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==", - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/pkce-challenge": { "version": "5.0.0", @@ -1474,8 +2136,7 @@ "url": "https://opencollective.com/fastify" } ], - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/proxy-addr": { "version": "2.0.7", @@ -1495,7 +2156,6 @@ "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.2.tgz", "integrity": "sha512-tUPXtzlGM8FE3P0ZL6DVs/3P58k9nk8/jZeQCurTJylQA8qFYzHFfhBJkuqyE0FifOsQ0uKWekiZ5g8wtr28cw==", "license": "MIT", - "peer": true, "dependencies": { "end-of-stream": "^1.1.0", "once": "^1.3.1" @@ -1529,8 +2189,7 @@ "version": "4.0.4", "resolved": "https://registry.npmjs.org/quick-format-unescaped/-/quick-format-unescaped-4.0.4.tgz", "integrity": "sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==", - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/range-parser": { "version": "1.2.1", @@ -1568,12 +2227,21 @@ "node": ">=0.10.0" } }, + "node_modules/react": { + "version": "19.1.0", + "resolved": "https://registry.npmjs.org/react/-/react-19.1.0.tgz", + "integrity": "sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==", + "license": "MIT", + "peer": true, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/real-require": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/real-require/-/real-require-0.2.0.tgz", "integrity": "sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==", "license": "MIT", - "peer": true, "engines": { "node": ">= 12.13.0" } @@ -1650,7 +2318,6 @@ "resolved": "https://registry.npmjs.org/safe-stable-stringify/-/safe-stable-stringify-2.5.0.tgz", "integrity": "sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==", "license": "MIT", - "peer": true, "engines": { "node": ">=10" } @@ -1665,8 +2332,7 @@ "version": "2.7.0", "resolved": "https://registry.npmjs.org/secure-json-parse/-/secure-json-parse-2.7.0.tgz", "integrity": "sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==", - "license": "BSD-3-Clause", - "peer": true + "license": "BSD-3-Clause" }, "node_modules/send": { "version": "1.1.0", @@ -1742,6 +2408,12 @@ "node": ">= 18" } }, + "node_modules/set-cookie-parser": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/set-cookie-parser/-/set-cookie-parser-2.7.1.tgz", + "integrity": "sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==", + "license": "MIT" + }, "node_modules/setprototypeof": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", @@ -1881,7 +2553,6 @@ "resolved": "https://registry.npmjs.org/sonic-boom/-/sonic-boom-4.2.0.tgz", "integrity": "sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==", "license": "MIT", - "peer": true, "dependencies": { "atomic-sleep": "^1.0.0" } @@ -1891,7 +2562,6 @@ "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", "license": "ISC", - "peer": true, "engines": { "node": ">= 10.x" } @@ -1910,7 +2580,6 @@ "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", "license": "MIT", - "peer": true, "engines": { "node": ">=8" }, @@ -1931,16 +2600,58 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/swr": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/swr/-/swr-2.3.3.tgz", + "integrity": "sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==", + "license": "MIT", + "dependencies": { + "dequal": "^2.0.3", + "use-sync-external-store": "^1.4.0" + }, + "peerDependencies": { + "react": "^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, "node_modules/thread-stream": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/thread-stream/-/thread-stream-3.1.0.tgz", "integrity": "sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==", "license": "MIT", - "peer": true, "dependencies": { "real-require": "^0.2.0" } }, + "node_modules/throttleit": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/throttleit/-/throttleit-2.1.0.tgz", + "integrity": "sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==", + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/tldts": { + "version": "6.1.86", + "resolved": "https://registry.npmjs.org/tldts/-/tldts-6.1.86.tgz", + "integrity": "sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==", + "license": "MIT", + "dependencies": { + "tldts-core": "^6.1.86" + }, + "bin": { + "tldts": "bin/cli.js" + } + }, + "node_modules/tldts-core": { + "version": "6.1.86", + "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-6.1.86.tgz", + "integrity": "sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==", + "license": "MIT" + }, "node_modules/toidentifier": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", @@ -1950,6 +2661,18 @@ "node": ">=0.6" } }, + "node_modules/tough-cookie": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-5.1.2.tgz", + "integrity": "sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==", + "license": "BSD-3-Clause", + "dependencies": { + "tldts": "^6.1.32" + }, + "engines": { + "node": ">=16" + } + }, "node_modules/tr46": { "version": "0.0.3", "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", @@ -2008,6 +2731,15 @@ "punycode": "^2.1.0" } }, + "node_modules/use-sync-external-store": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.5.0.tgz", + "integrity": "sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==", + "license": "MIT", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, "node_modules/utils-merge": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", @@ -2017,6 +2749,19 @@ "node": ">= 0.4.0" } }, + "node_modules/uuid": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", + "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", + "funding": [ + "https://github.com/sponsors/broofa", + "https://github.com/sponsors/ctavan" + ], + "license": "MIT", + "bin": { + "uuid": "dist/bin/uuid" + } + }, "node_modules/vary": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", diff --git a/stagehand/package.json b/stagehand/package.json index 2c40f9f..4979040 100644 --- a/stagehand/package.json +++ b/stagehand/package.json @@ -1,5 +1,5 @@ { - "name": "@browserbasehq/mcp-stagehand", + "name": "@browserbasehq/mcp", "version": "0.5.1", "description": "MCP server for AI web browser automation using Stagehand", "license": "MIT", @@ -24,9 +24,8 @@ "watch": "tsc --watch" }, "dependencies": { - "@browserbasehq/sdk": "^2.0.0", - "@browserbasehq/stagehand": "^2.0.0", - "@modelcontextprotocol/sdk": "^1.13.0", + "@browserbasehq/stagehand": "^2.4.0", + "@modelcontextprotocol/sdk": "^1.13.1", "@playwright/test": "^1.49.0", "commander": "^14.0.0" }, diff --git a/stagehand/smithery.config.js b/stagehand/smithery.config.js new file mode 100644 index 0000000..e2dfe2e --- /dev/null +++ b/stagehand/smithery.config.js @@ -0,0 +1,10 @@ +/** + * @type {import('esbuild').BuildOptions} + */ +export default { + esbuild: { + // Mark playwright-core as external to prevent bundling + // This avoids the relative path resolution issue in Docker + external: ["playwright-core"], + } +} diff --git a/stagehand/smithery.yaml b/stagehand/smithery.yaml new file mode 100644 index 0000000..8fa57d3 --- /dev/null +++ b/stagehand/smithery.yaml @@ -0,0 +1 @@ +runtime: "typescript" \ No newline at end of file diff --git a/stagehand/src/config.ts b/stagehand/src/config.ts index 5c83467..13aad54 100644 --- a/stagehand/src/config.ts +++ b/stagehand/src/config.ts @@ -4,6 +4,7 @@ import path from 'path'; import { sanitizeForFilePath } from './tools/utils.js'; import type { Cookie } from "playwright-core"; import type { Config } from '../config.js'; +import { AvailableModelSchema } from '@browserbasehq/stagehand'; export type ToolCapability = 'core' | string; @@ -20,6 +21,7 @@ export type CLIOptions = { cookies?: Cookie[]; browserWidth?: number; browserHeight?: number; + modelName?: typeof AvailableModelSchema; }; // Default Configuration Values @@ -36,6 +38,7 @@ const defaultConfig: Config = { browserHeight: 768, }, cookies: undefined, + modelName: "google/gemini-2.0-flash", // Default Model }; // Resolve final configuration by merging defaults, file config, and CLI options @@ -84,6 +87,7 @@ export async function configFromCLIOptions(cliOptions: CLIOptions): Promise(); public readonly config: Config; private server: Server; public currentSessionId: string = defaultSessionId; @@ -31,66 +22,25 @@ export class Context { constructor(server: Server, config: Config) { this.server = server; this.config = config; - - // Initialize logging system - setServerInstance(server); - ensureLogDirectory(); - setupLogRotation(); - registerExitHandlers(); - scheduleLogRotation(); - } - - /** - * Gets the Stagehand instance for the current session, creating one if needed - */ - public async getStagehand(sessionId: string = this.currentSessionId): Promise { - let stagehand = this.stagehands.get(sessionId); - - if (!stagehand) { - // Create a new Stagehand instance for this session - stagehand = new Stagehand({ - env: "BROWSERBASE", - logger: (logLine) => { - log(`Stagehand[${sessionId}]: ${logLine.message}`, 'info'); - }, - }); - this.stagehands.set(sessionId, stagehand); - } - - await stagehand.init(); - - return stagehand; } - /** - * Sets the Stagehand instance for a specific session - */ - public setStagehand(sessionId: string, stagehand: Stagehand): void { - this.stagehands.set(sessionId, stagehand); + public getServer(): Server { + return this.server; } /** - * Removes the Stagehand instance for a specific session + * Gets the Stagehand instance for the current session from SessionManager */ - public async removeStagehand(sessionId: string): Promise { - const stagehand = this.stagehands.get(sessionId); - if (stagehand) { - try { - await stagehand.close(); - } catch (error) { - log(`Error closing Stagehand for session ${sessionId}: ${error}`, 'error'); - } - this.stagehands.delete(sessionId); + public async getStagehand(sessionId: string = this.currentSessionId): Promise { + const session = await getSession(sessionId, this.config); + if (!session) { + throw new Error(`No session found for ID: ${sessionId}`); } + return session.stagehand; } + public async getActivePage(): Promise { - // Try to get page from Stagehand first (if available for this session) - const stagehand = this.stagehands.get(this.currentSessionId); - if (stagehand && stagehand.page && !stagehand.page.isClosed()) { - return stagehand.page; - } - - // Fallback to session manager + // Get page from session manager const session = await getSession(this.currentSessionId, this.config); if (session && session.page && !session.page.isClosed()) { return session.page; @@ -109,7 +59,7 @@ export class Context { async run(tool: any, args: any): Promise { try { - log(`Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`, 'info'); + console.error(`Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`); // Check if this tool has a handle method (new tool system) if ("handle" in tool && typeof tool.handle === "function") { @@ -135,7 +85,7 @@ export class Context { } } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); - log(`Tool ${tool.schema?.name || 'unknown'} failed: ${errorMessage}`, 'error'); + console.error(`Tool ${tool.schema?.name || 'unknown'} failed: ${errorMessage}`); return { content: [{ type: "text", text: `Error: ${errorMessage}` }], isError: true, @@ -155,21 +105,4 @@ export class Context { return readResource(uri); } - async close() { - try { - // Close all Stagehand instances - for (const [sessionId, stagehand] of this.stagehands.entries()) { - try { - await stagehand.close(); - log(`Closed Stagehand for session ${sessionId}`, 'info'); - } catch (error) { - log(`Error closing Stagehand for session ${sessionId}: ${error}`, 'error'); - } - } - this.stagehands.clear(); - log('All Stagehand contexts closed successfully', 'info'); - } catch (error) { - log(`Error closing Stagehand contexts: ${error}`, 'error'); - } - } } \ No newline at end of file diff --git a/stagehand/src/index.ts b/stagehand/src/index.ts index 9821aa9..b7233df 100644 --- a/stagehand/src/index.ts +++ b/stagehand/src/index.ts @@ -1,118 +1,98 @@ import dotenv from "dotenv"; dotenv.config(); -import { Config } from "../config.js"; +import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js'; +import { z } from 'zod'; +import type { Tool } from "./tools/tool.js"; -import { Server } from "@modelcontextprotocol/sdk/server/index.js"; -import { CallToolRequestSchema, ListResourcesRequestSchema, ListToolsRequestSchema, ReadResourceRequestSchema } from "@modelcontextprotocol/sdk/types.js"; -import { z } from "zod"; -import { zodToJsonSchema } from "zod-to-json-schema"; import { Context } from "./context.js"; +import type { Config } from "../config.js"; import { TOOLS } from "./tools/index.js"; +import { AvailableModelSchema } from "@browserbasehq/stagehand"; -export async function createServer(config: Config): Promise { - // Create the server - const server = new Server( - { name: "mcp-server-browserbase", version: "0.5.1" }, - { - capabilities: { - resources: { list: true, read: true }, - tools: { list: true, call: true }, - prompts: { list: true, get: true }, - notifications: { resources: { list_changed: true } }, - logging: {}, - }, - } - ); - - // Create the context, passing server instance and config - const context = new Context(server, config); - - const tools: any[] = [ - ...TOOLS, - ]; +// Configuration schema for Smithery - matches existing Config interface +export const configSchema = z.object({ + browserbaseApiKey: z.string().describe("The Browserbase API Key to use"), + browserbaseProjectId: z.string().describe("The Browserbase Project ID to use"), + proxies: z.boolean().optional().describe("Whether or not to use Browserbase proxies"), + advancedStealth: z.boolean().optional().describe("Use advanced stealth mode. Only available to Browserbase Scale Plan users"), + context: z.object({ + contextId: z.string().optional().describe("The ID of the context to use"), + persist: z.boolean().optional().describe("Whether or not to persist the context") + }).optional(), + viewPort: z.object({ + browserWidth: z.number().optional().describe("The width of the browser"), + browserHeight: z.number().optional().describe("The height of the browser") + }).optional(), + cookies: z.array(z.object({ // Playwright Cookies Type in Zod format + name: z.string(), + value: z.string(), + domain: z.string(), + path: z.string().optional(), + expires: z.number().optional(), + httpOnly: z.boolean().optional(), + secure: z.boolean().optional(), + sameSite: z.enum(['Strict', 'Lax', 'None']).optional() + })).optional().describe("Cookies to inject into the Browserbase context"), + server: z.object({ + port: z.number().optional().describe("The port to listen on for SSE or MCP transport"), + host: z.string().optional().describe("The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces") + }).optional(), + modelName: AvailableModelSchema.optional().describe( + "The model to use for Stagehand (default: google/gemini-2.0-flash)" + ), +}); - const toolsMap = new Map(tools.map(tool => [tool.schema.name, tool])); - // --- Setup Request Handlers --- - - server.setRequestHandler(ListResourcesRequestSchema, async () => { - return { resources: context.listResources() }; - }); +// Default function for Smithery +export default function ({ config }: { config: z.infer }) { + if (!config.browserbaseApiKey) { + throw new Error('browserbaseApiKey is required'); + } + if (!config.browserbaseProjectId) { + throw new Error('browserbaseProjectId is required'); + } - server.setRequestHandler(ReadResourceRequestSchema, async (request) => { - try { - const resourceContent = context.readResource(request.params.uri.toString()); - return { contents: [resourceContent] }; - } catch (error) { - // Keep this error log - console.error(`Error reading resource via context: ${error}`); - throw error; + const server = new McpServer({ + name: 'Browserbase MCP Server', + version: '1.0.6', + capabilities: { + logging: {} } }); - server.setRequestHandler(ListToolsRequestSchema, async () => { - return { - tools: tools.map(tool => { - let finalInputSchema; - // Check if inputSchema is a Zod schema before converting - if (tool.schema.inputSchema instanceof z.Schema) { - // Add type assertion to help compiler - finalInputSchema = zodToJsonSchema(tool.schema.inputSchema as any); - } else if (typeof tool.schema.inputSchema === 'object' && tool.schema.inputSchema !== null) { - // Assume it's already a valid JSON schema object - finalInputSchema = tool.schema.inputSchema; - } else { - // Fallback or error handling if schema is neither - // Keep this error log - console.error(`Warning: Tool '${tool.schema.name}' has an unexpected inputSchema type.`); - finalInputSchema = { type: "object" }; // Default to empty object schema - } - - return { - name: tool.schema.name, - description: tool.schema.description, - inputSchema: finalInputSchema, - }; - }), - }; - }); + const internalConfig: Config = config as Config; - server.setRequestHandler(CallToolRequestSchema, async (request) => { - const logError = (message: string) => { - // Ensure error logs definitely go to stderr - process.stderr.write(`[server.ts Error] ${new Date().toISOString()} ${message}\\n`); - }; - - // Use the map built from the passed-in tools - const tool = toolsMap.get(request.params.name); + // Create the context, passing server instance and config + const context = new Context(server.server, internalConfig); - if (!tool) { - // Use the explicit error logger - logError(`Tool "${request.params.name}" not found.`); - // Return a simplified error object - return { content: [{ type: 'text', text: `Tool "${request.params.name}" not found` }], isError: true }; - } + const tools: Tool[] = [ + ...TOOLS, + ]; - try { - // Delegate execution to the context - const result = await context.run(tool, request.params.arguments ?? {}); - return result; - } catch (error) { - // Use the explicit error logger - const errorMessage = error instanceof Error ? error.message : String(error); - logError(`Error running tool ${request.params.name} via context: ${errorMessage}`); - logError(`Original error stack (if available): ${error instanceof Error ? error.stack : 'N/A'}`); // Log stack trace - // Return a simplified error object - return { content: [{ type: 'text', text: `Failed to run tool '${request.params.name}': ${errorMessage}` }], isError: true }; + // Register each tool with the Smithery server + tools.forEach(tool => { + if (tool.schema.inputSchema instanceof z.ZodObject) { + server.tool( + tool.schema.name, + tool.schema.description, + tool.schema.inputSchema.shape, + async (params: z.infer) => { + try { + const result = await context.run(tool, params); + return result; + } catch (error) { + const errorMessage = error instanceof Error ? error.message : String(error); + process.stderr.write(`[Smithery Error] ${new Date().toISOString()} Error running tool ${tool.schema.name}: ${errorMessage}\n`); + throw new Error(`Failed to run tool '${tool.schema.name}': ${errorMessage}`); + } + } + ); + } else { + console.warn( + `Tool "${tool.schema.name}" has an input schema that is not a ZodObject. Schema type: ${tool.schema.inputSchema.constructor.name}` + ); } }); - // Wrap server close to also close context - const originalClose = server.close.bind(server); - server.close = async () => { - await originalClose(); - }; - - // Return the configured server instance - return server; -} \ No newline at end of file + return server.server; +} \ No newline at end of file diff --git a/stagehand/src/logging.ts b/stagehand/src/logging.ts deleted file mode 100644 index f51bfa6..0000000 --- a/stagehand/src/logging.ts +++ /dev/null @@ -1,222 +0,0 @@ -import fs from 'fs'; -import path from 'path'; -import { fileURLToPath } from 'url'; -import type { LogLine } from "@browserbasehq/stagehand"; -import { Server } from "@modelcontextprotocol/sdk/server/index.js"; - -// Get the directory name for the current module -const __dirname = path.dirname(fileURLToPath(import.meta.url)); - -// Configure logging -const LOG_DIR = path.join(__dirname, '../logs'); -const LOG_FILE = path.join(LOG_DIR, `stagehand-${new Date().toISOString().split('T')[0]}.log`); -const MAX_LOG_FILES = 10; // Maximum number of log files to keep -const MAX_LOG_SIZE = 10 * 1024 * 1024; // 10MB max log file size - -// Queue for batching log writes -let logQueue: string[] = []; -let logWriteTimeout: NodeJS.Timeout | null = null; -const LOG_FLUSH_INTERVAL = 1000; // Flush logs every second -const MAX_OPERATION_LOGS = 1000; // Prevent operation logs from growing too large - -// Operation logs stored in memory -export const operationLogs: string[] = []; -export const consoleLogs: string[] = []; - -// Reference to server instance for logging -let serverInstance: Server | undefined; - -// Set server for logging -export function setServerInstance(server: Server) { - serverInstance = server; -} - -// Get server instance for notifications and logging -export function getServerInstance() { - return serverInstance; -} - -// Ensure log directory exists -export function ensureLogDirectory() { - if (!fs.existsSync(LOG_DIR)) { - fs.mkdirSync(LOG_DIR, { recursive: true }); - } -} - -// Setup log rotation management -export function setupLogRotation() { - try { - // Check if current log file exceeds max size - if (fs.existsSync(LOG_FILE) && fs.statSync(LOG_FILE).size > MAX_LOG_SIZE) { - const timestamp = new Date().toISOString().replace(/:/g, '-'); - const rotatedLogFile = path.join(LOG_DIR, `stagehand-${timestamp}.log`); - fs.renameSync(LOG_FILE, rotatedLogFile); - } - - // Clean up old log files if we have too many - const logFiles = fs.readdirSync(LOG_DIR) - .filter(file => file.startsWith('stagehand-') && file.endsWith('.log')) - .map(file => path.join(LOG_DIR, file)) - .sort((a, b) => fs.statSync(b).mtime.getTime() - fs.statSync(a).mtime.getTime()); - - if (logFiles.length > MAX_LOG_FILES) { - logFiles.slice(MAX_LOG_FILES).forEach(file => { - try { - fs.unlinkSync(file); - } catch (err) { - console.error(`Failed to delete old log file ${file}:`, err); - } - }); - } - } catch (err) { - console.error('Error in log rotation:', err); - } -} - -// Flush logs to disk asynchronously -export async function flushLogs() { - if (logQueue.length === 0) return; - - const logsToWrite = logQueue.join('\n') + '\n'; - logQueue = []; - logWriteTimeout = null; - - try { - await fs.promises.appendFile(LOG_FILE, logsToWrite); - - // Check if we need to rotate logs after write - const stats = await fs.promises.stat(LOG_FILE); - if (stats.size > MAX_LOG_SIZE) { - setupLogRotation(); - } - } catch (err) { - console.error('Failed to write logs to file:', err); - // If write fails, try to use sync version as fallback - try { - fs.appendFileSync(LOG_FILE, logsToWrite); - } catch (syncErr) { - console.error('Failed to write logs synchronously:', syncErr); - } - } -} - -// Helper function to convert LogLine to string -export function logLineToString(logLine: LogLine): string { - const timestamp = logLine.timestamp ? new Date(logLine.timestamp).toISOString() : new Date().toISOString(); - const level = logLine.level !== undefined ? - (logLine.level === 0 ? 'DEBUG' : - logLine.level === 1 ? 'INFO' : - logLine.level === 2 ? 'ERROR' : 'UNKNOWN') : 'UNKNOWN'; - return `[${timestamp}] [${level}] ${logLine.message || ''}`; -} - -// Main logging function -export function log(message: string, level: 'info' | 'error' | 'debug' = 'info') { - const timestamp = new Date().toISOString(); - const logMessage = `[${timestamp}] [${level.toUpperCase()}] ${message}`; - - // Manage operation logs with size limit - operationLogs.push(logMessage); - if (operationLogs.length > MAX_OPERATION_LOGS) { - // Keep most recent logs but trim the middle to maintain context - const half = Math.floor(MAX_OPERATION_LOGS / 2); - // Keep first 100 and last (MAX_OPERATION_LOGS - 100) logs - const firstLogs = operationLogs.slice(0, 100); - const lastLogs = operationLogs.slice(operationLogs.length - (MAX_OPERATION_LOGS - 100)); - operationLogs.length = 0; - operationLogs.push(...firstLogs); - operationLogs.push(`[...${operationLogs.length - MAX_OPERATION_LOGS} logs truncated...]`); - operationLogs.push(...lastLogs); - } - - // Queue log for async writing - logQueue.push(logMessage); - - // Setup timer to flush logs if not already scheduled - if (!logWriteTimeout) { - logWriteTimeout = setTimeout(flushLogs, LOG_FLUSH_INTERVAL); - } - - // Console output to stderr for debugging - if (process.env.DEBUG || level === 'error') { - console.error(logMessage); - } - - // Send logging message to client for important events - if (serverInstance && (level === 'info' || level === 'error')) { - serverInstance.sendLoggingMessage({ - level: level, - data: message, - }); - } -} - -// Format logs for response -export function formatLogResponse(logs: string[]): string { - if (logs.length <= 100) { - return logs.join("\n"); - } - - // For very long logs, include first and last parts with truncation notice - const first = logs.slice(0, 50); - const last = logs.slice(-50); - return [ - ...first, - `\n... ${logs.length - 100} more log entries (truncated) ...\n`, - ...last - ].join("\n"); -} - -// Log request -export function logRequest(type: string, params: any) { - const requestLog = { - timestamp: new Date().toISOString(), - type, - params, - }; - log(`REQUEST: ${JSON.stringify(requestLog, null, 2)}`, 'debug'); -} - -// Log response -export function logResponse(type: string, response: any) { - const responseLog = { - timestamp: new Date().toISOString(), - type, - response, - }; - log(`RESPONSE: ${JSON.stringify(responseLog, null, 2)}`, 'debug'); -} - -// Register handlers for process exit -export function registerExitHandlers() { - // Make sure logs are flushed when the process exits - process.on('exit', () => { - if (logQueue.length > 0) { - try { - fs.appendFileSync(LOG_FILE, logQueue.join('\n') + '\n'); - } catch (err) { - console.error('Failed to flush logs on exit:', err); - } - } - }); - - process.on('SIGINT', () => { - // Flush logs and exit - if (logQueue.length > 0) { - try { - fs.appendFileSync(LOG_FILE, logQueue.join('\n') + '\n'); - } catch (err) { - console.error('Failed to flush logs on SIGINT:', err); - } - } - process.exit(0); - }); -} - -// Schedule periodic log rotation -export function scheduleLogRotation() { - // Add log rotation check periodically - setInterval(() => { - setupLogRotation(); - }, 15 * 60 * 1000); // Check every 15 minutes -} \ No newline at end of file diff --git a/stagehand/src/program.ts b/stagehand/src/program.ts index 6b65ec0..c1ac1ec 100644 --- a/stagehand/src/program.ts +++ b/stagehand/src/program.ts @@ -3,16 +3,24 @@ import * as fs from 'fs'; import * as path from 'path'; import { fileURLToPath } from 'url'; -import { createServer } from './index.js'; +import createServerFunction from './index.js'; import { ServerList } from './server.js'; - import { startHttpTransport, startStdioTransport } from './transport.js'; import { resolveConfig } from './config.js'; -// Determine the directory of the current module -const __filename = fileURLToPath(import.meta.url); -const __dirname = path.dirname(__filename); +let __filename: string; +let __dirname: string; + +try { + // Try ES modules first + __filename = fileURLToPath(import.meta.url); + __dirname = path.dirname(__filename); +} catch { + // Fallback for CommonJS or when import.meta is not available + __filename = (globalThis as any).__filename || process.cwd() + '/dist/program.js'; + __dirname = path.dirname(__filename); +} // Load package.json using fs const packageJSONPath = path.resolve(__dirname, '../package.json'); @@ -33,9 +41,12 @@ program .option('--cookies [json]', 'JSON array of cookies to inject into the browser. Format: [{"name":"cookie1","value":"val1","domain":"example.com"}, ...]') .option('--browserWidth ', 'Browser width to use for the browser.') .option('--browserHeight ', 'Browser height to use for the browser.') + .option('--modelName ', 'The model to use for Stagehand (default: google/gemini-2.0-flash)') .action(async options => { const config = await resolveConfig(options); - const serverList = new ServerList(async() => createServer(config)); + const serverList = new ServerList(async() => createServerFunction( + { config: config as Required> & typeof config } + )); setupExitWatchdog(serverList); if (options.port) diff --git a/stagehand/src/sessionManager.ts b/stagehand/src/sessionManager.ts index 35015d6..2b366a6 100644 --- a/stagehand/src/sessionManager.ts +++ b/stagehand/src/sessionManager.ts @@ -1,11 +1,9 @@ import { - chromium, Browser, Page, } from "playwright-core"; -import { Browserbase } from "@browserbasehq/sdk"; +import { AvailableModel, Stagehand } from "@browserbasehq/stagehand"; import type { Config } from "../config.js"; -import { SessionCreateParams } from "@browserbasehq/sdk/src/resources/sessions/sessions.js"; import type { Cookie } from "playwright-core"; // Define the type for a session object @@ -13,6 +11,7 @@ export type BrowserSession = { browser: Browser; page: Page; sessionId: string; + stagehand: Stagehand; }; // Global state for managing browser sessions @@ -72,10 +71,11 @@ export async function addCookiesToContext(context: any, cookies: Cookie[]): Prom } } -// Function to create a new Browserbase session and connect Playwright +// Function to create a new Browserbase session using Stagehand export async function createNewBrowserSession( newSessionId: string, - config: Config, + config: Config, + resumeSessionId?: string ): Promise { if (!config.browserbaseApiKey) { throw new Error("Browserbase API Key is missing in the configuration."); @@ -84,42 +84,61 @@ export async function createNewBrowserSession( throw new Error("Browserbase Project ID is missing in the configuration."); } - const bb = new Browserbase({ - apiKey: config.browserbaseApiKey, - }); - - // Prepare session creation options - const sessionOptions: SessionCreateParams = { - // Use non-null assertion after check - projectId: config.browserbaseProjectId!, - proxies: config.proxies, - browserSettings: { - viewport: { - width: config.viewPort?.browserWidth ?? 1024, - height: config.viewPort?.browserHeight ?? 768, - }, - context: config.context?.contextId ? { - id: config.context?.contextId, - persist: config.context?.persist ?? true, - } : undefined, - advancedStealth: config.advancedStealth ?? undefined, - } - }; - try { process.stderr.write( - `[SessionManager] Creating session ${newSessionId}...\n` + `[SessionManager] ${resumeSessionId ? 'Resuming' : 'Creating'} Stagehand session ${newSessionId}...\n` ); - const bbSession = await bb.sessions.create(sessionOptions); + + // Create and initialize Stagehand instance + const stagehand = new Stagehand({ + env: "BROWSERBASE", + apiKey: config.browserbaseApiKey, + projectId: config.browserbaseProjectId, + modelName: (config.modelName || "google/gemini-2.0-flash") as AvailableModel, + modelClientOptions: { + apiKey: process.env.GEMINI_API_KEY, // TODO: change this in prod to just use our key + }, + ...(resumeSessionId && { browserbaseSessionID: resumeSessionId }), + browserbaseSessionCreateParams: { + projectId: config.browserbaseProjectId!, + proxies: config.proxies, + browserSettings: { + viewport: { + width: config.viewPort?.browserWidth ?? 1024, + height: config.viewPort?.browserHeight ?? 768, + }, + context: config.context?.contextId ? { + id: config.context?.contextId, + persist: config.context?.persist ?? true, + } : undefined, + advancedStealth: config.advancedStealth ?? undefined, + }, + }, + logger: (logLine) => { + console.error(`Stagehand[${newSessionId}]: ${logLine.message}`); + }, + }); + + await stagehand.init(); + + // Get the page and browser from Stagehand + const page = stagehand.page as unknown as Page; + const browser = page.context().browser(); + + if (!browser) { + throw new Error("Failed to get browser from Stagehand page context"); + } + + const browserbaseSessionId = stagehand.browserbaseSessionID; + process.stderr.write( - `[SessionManager] Browserbase session created: ${bbSession.id}\n` + `[SessionManager] Stagehand initialized with Browserbase session: ${browserbaseSessionId}\n` ); - - const browser = await chromium.connectOverCDP(bbSession.connectUrl); process.stderr.write( - `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${bbSession.id}\n` + `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${browserbaseSessionId}\n` ); + // Set up disconnect handler browser.on("disconnected", () => { process.stderr.write(`[SessionManager] Disconnected: ${newSessionId}\n`); browsers.delete(newSessionId); @@ -139,26 +158,17 @@ export async function createNewBrowserSession( setActiveSessionId(defaultSessionId); } }); - - let context = browser.contexts()[0]; - if (!context) { - context = await browser.newContext(); - } // Add cookies to the context if they are provided in the config if (config.cookies && Array.isArray(config.cookies) && config.cookies.length > 0) { - await addCookiesToContext(context, config.cookies); - } - - let page = context.pages()[0]; - if (!page) { - page = await context.newPage(); + await addCookiesToContext(page.context(), config.cookies); } const sessionObj: BrowserSession = { browser, page, - sessionId: bbSession.id, + sessionId: browserbaseSessionId!, + stagehand, }; browsers.set(newSessionId, sessionObj); @@ -179,11 +189,7 @@ export async function createNewBrowserSession( ? creationError.message : String(creationError); process.stderr.write( - `[SessionManager] Creating session ${newSessionId} failed: ${ - creationError instanceof Error - ? creationError.message - : String(creationError) - }` + `[SessionManager] Creating session ${newSessionId} failed: ${errorMessage}\n` ); throw new Error( `Failed to create/connect session ${newSessionId}: ${errorMessage}` @@ -195,15 +201,19 @@ async function closeBrowserGracefully( session: BrowserSession | undefined | null, sessionIdToLog: string ): Promise { - if (session?.browser?.isConnected()) { - process.stderr.write( - `[SessionManager] Closing browser for session: ${sessionIdToLog}\n` - ); + // Close Stagehand instance which handles browser cleanup + if (session?.stagehand) { try { - await session.browser.close(); + process.stderr.write( + `[SessionManager] Closing Stagehand for session: ${sessionIdToLog}\n` + ); + await session.stagehand.close(); + process.stderr.write( + `[SessionManager] Successfully closed Stagehand and browser for session: ${sessionIdToLog}\n` + ); } catch (closeError) { process.stderr.write( - `[SessionManager] WARN - Error closing browser for session ${sessionIdToLog}: ${ + `[SessionManager] WARN - Error closing Stagehand for session ${sessionIdToLog}: ${ closeError instanceof Error ? closeError.message : String(closeError) }\n` ); @@ -284,7 +294,6 @@ export async function getSession( try { return await ensureDefaultSessionInternal(config); } catch (error) { - // ensureDefaultSessionInternal already logs extensively process.stderr.write( `[SessionManager] Failed to get default session due to error in ensureDefaultSessionInternal for ${sessionId}. See previous messages for details.\n` ); diff --git a/stagehand/src/tools/act.ts b/stagehand/src/tools/act.ts index a80f5a2..66cb399 100644 --- a/stagehand/src/tools/act.ts +++ b/stagehand/src/tools/act.ts @@ -37,6 +37,7 @@ async function handleAct( const action = async (): Promise => { try { const stagehand = await context.getStagehand(); + await stagehand.page.act({ action: params.action, variables: params.variables, diff --git a/stagehand/src/tools/extract.ts b/stagehand/src/tools/extract.ts index b251e46..79f9f12 100644 --- a/stagehand/src/tools/extract.ts +++ b/stagehand/src/tools/extract.ts @@ -27,6 +27,7 @@ async function handleExtract( } const bodyText = await page.evaluate(() => document.body.innerText); + const content = bodyText .split("\n") .map((line) => line.trim()) diff --git a/stagehand/src/tools/index.ts b/stagehand/src/tools/index.ts index 2a98374..c1d911f 100644 --- a/stagehand/src/tools/index.ts +++ b/stagehand/src/tools/index.ts @@ -24,13 +24,4 @@ export const TOOLS = [ screenshotTool, ]; -// Export tools by category -export const coreTools = [ - navigateTool, - actTool, - extractTool, - observeTool, - screenshotTool, -]; - export const sessionManagementTools = sessionTools; \ No newline at end of file diff --git a/stagehand/src/tools/navigate.ts b/stagehand/src/tools/navigate.ts index 7528e97..fa97c02 100644 --- a/stagehand/src/tools/navigate.ts +++ b/stagehand/src/tools/navigate.ts @@ -2,7 +2,6 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; -import { operationLogs } from "../logging.js"; const NavigateInputSchema = z.object({ url: z.string().describe("The URL to navigate to"), diff --git a/stagehand/src/tools/observe.ts b/stagehand/src/tools/observe.ts index 3aace9f..cd876b7 100644 --- a/stagehand/src/tools/observe.ts +++ b/stagehand/src/tools/observe.ts @@ -25,6 +25,7 @@ async function handleObserve( const action = async (): Promise => { try { const stagehand = await context.getStagehand(); + const observations = await stagehand.page.observe({ instruction: params.instruction, returnAction: false, diff --git a/stagehand/src/tools/screenshot.ts b/stagehand/src/tools/screenshot.ts index 5e7a7f0..0b66074 100644 --- a/stagehand/src/tools/screenshot.ts +++ b/stagehand/src/tools/screenshot.ts @@ -2,7 +2,6 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; -import { getServerInstance } from "../logging.js"; import { screenshots } from "../resources.js"; const ScreenshotInputSchema = z.object({ @@ -41,7 +40,8 @@ async function handleScreenshot( screenshots.set(name, screenshotBase64); // Notify the client that the resources changed - const serverInstance = getServerInstance(); + const serverInstance = context.getServer(); + if (serverInstance) { serverInstance.notification({ method: "notifications/resources/list_changed", diff --git a/stagehand/src/tools/session.ts b/stagehand/src/tools/session.ts index 9f0db4d..aa0fb70 100644 --- a/stagehand/src/tools/session.ts +++ b/stagehand/src/tools/session.ts @@ -9,6 +9,7 @@ import { defaultSessionId, ensureDefaultSessionInternal, cleanupSession, + getSession, type BrowserSession, } from "../sessionManager.js"; @@ -27,7 +28,7 @@ type CreateSessionInput = z.infer; const createSessionSchema: ToolSchema = { name: "browserbase_session_create", description: - "Create or reuse a cloud browser session using Browserbase. Updates the active session.", + "Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand. This creates the browser session with all configuration flags (proxies, stealth, viewport, cookies, etc.) and initializes Stagehand to work with that session. Updates the active session.", inputSchema: CreateSessionInputSchema, }; @@ -56,7 +57,8 @@ async function handleCreateSession( if (targetSessionId === defaultSessionId) { session = await ensureDefaultSessionInternal(config); } else { - session = await createNewBrowserSession(targetSessionId, config); + // When user provides a sessionId, we want to resume that Browserbase session + session = await createNewBrowserSession(targetSessionId, config, params.sessionId); } if (!session || !session.browser || !session.page || !session.sessionId) { @@ -121,7 +123,7 @@ type CloseSessionInput = z.infer; const closeSessionSchema: ToolSchema = { name: "browserbase_session_close", description: - "Closes the current Browserbase session by disconnecting the Playwright browser. This will terminate the recording for the session.", + "Closes the current Browserbase session by properly shutting down the Stagehand instance, which handles browser cleanup and terminates the session recording.", inputSchema: CloseSessionInputSchema, }; @@ -131,82 +133,78 @@ async function handleCloseSession( ): Promise { const action = async (): Promise => { // Store the current session ID before it's potentially changed. - // This allows us to reference the original session ID later if needed. - const previousSessionId = context.currentSessionId; // Capture the ID before any changes - let browser: BrowserSession["browser"] | null = null; - let browserClosedSuccessfully = false; - let browserCloseErrorMessage = ""; + const previousSessionId = context.currentSessionId; + let stagehandClosedSuccessfully = false; + let stagehandCloseErrorMessage = ""; - // Step 1: Attempt to get the active browser instance WITHOUT creating a new one + // Step 1: Attempt to get the session and close Stagehand + let browserbaseSessionId: string | undefined; try { - // Use read-only version to avoid creating new sessions - browser = await context.getActiveBrowser(false); - } catch (error: any) { - process.stderr.write( - `[tool.closeSession] Error retrieving active browser (session ID was ${previousSessionId || 'default/unknown'}): ${error.message || String(error)}` - ); - // If we can't even get the browser, we can't close it. - // We will still proceed to reset context. - } - - // Step 2: If a browser instance was retrieved, attempt to close it - if (browser) { - try { + const session = await getSession(previousSessionId, context.config, false); + + if (session && session.stagehand) { + // Store the actual Browserbase session ID for the replay URL + browserbaseSessionId = session.sessionId; + process.stderr.write( - `[tool.closeSession] Attempting to close browser for session: ${previousSessionId || 'default (actual might differ)'}` + `[tool.closeSession] Attempting to close Stagehand for session: ${previousSessionId || 'default'} (Browserbase ID: ${browserbaseSessionId})` ); - await browser.close(); - browserClosedSuccessfully = true; + + // Use Stagehand's close method which handles browser cleanup properly + await session.stagehand.close(); + stagehandClosedSuccessfully = true; + process.stderr.write( - `[tool.closeSession] Browser connection for session (was ${previousSessionId}) closed.` + `[tool.closeSession] Stagehand and browser connection for session (${previousSessionId}) closed successfully.` ); // Clean up the session from tracking cleanupSession(previousSessionId); - process.stderr.write( - `[tool.closeSession] View session replay at https://www.browserbase.com/sessions/${previousSessionId}` - ); + if (browserbaseSessionId) { + process.stderr.write( + `[tool.closeSession] View session replay at https://www.browserbase.com/sessions/${browserbaseSessionId}` + ); + } - } catch (error: any) { - browserCloseErrorMessage = error.message || String(error); + } else { process.stderr.write( - `[tool.closeSession] Error during browser.close() for session (was ${previousSessionId}): ${browserCloseErrorMessage}` + `[tool.closeSession] No Stagehand instance found for session: ${previousSessionId || 'default/unknown'}` ); } - } else { + } catch (error: any) { + stagehandCloseErrorMessage = error.message || String(error); process.stderr.write( - `[tool.closeSession] No active browser instance found to close. (Session ID in context was: ${previousSessionId || 'default/unknown'}).` + `[tool.closeSession] Error retrieving or closing Stagehand (session ID was ${previousSessionId || 'default/unknown'}): ${stagehandCloseErrorMessage}` ); } - // Step 3: Always reset the context's current session ID to default - const oldContextSessionId = context.currentSessionId; // This should effectively be 'previousSessionId' + // Step 2: Always reset the context's current session ID to default + const oldContextSessionId = context.currentSessionId; context.currentSessionId = defaultSessionId; process.stderr.write( `[tool.closeSession] Session context reset to default. Previous context session ID was ${oldContextSessionId || 'default/unknown'}.` ); - // Step 4: Determine the result message - if (browser && !browserClosedSuccessfully) { // An attempt was made to close, but it failed + // Step 3: Determine the result message + if (stagehandCloseErrorMessage && !stagehandClosedSuccessfully) { throw new Error( - `Failed to close the Browserbase browser (session ID in context was ${previousSessionId || 'default/unknown'}). Error: ${browserCloseErrorMessage}. Session context has been reset to default.` + `Failed to close the Stagehand session (session ID in context was ${previousSessionId || 'default/unknown'}). Error: ${stagehandCloseErrorMessage}. Session context has been reset to default.` ); } - if (browserClosedSuccessfully) { // Browser was present and closed - let successMessage = `Browserbase session (associated with context ID ${previousSessionId || 'default'}) closed successfully. Context reset to default.`; - if (previousSessionId && previousSessionId !== defaultSessionId) { - successMessage += ` If this was a uniquely named session (${previousSessionId}), view replay (if available) at https://browserbase.com/sessions`; + if (stagehandClosedSuccessfully) { + let successMessage = `Browserbase session (${previousSessionId || 'default'}) closed successfully via Stagehand. Context reset to default.`; + if (browserbaseSessionId && previousSessionId !== defaultSessionId) { + successMessage += ` View replay at https://browserbase.com/sessions/${browserbaseSessionId}`; } return { content: [{ type: "text", text: successMessage }] }; } - // No browser was found, or browser was null initially. - let infoMessage = "No active browser instance was found to close. Session context has been reset to default."; + // No Stagehand instance was found + let infoMessage = "No active Stagehand session found to close. Session context has been reset to default."; if (previousSessionId && previousSessionId !== defaultSessionId) { - // This means a specific session was in context, but no browser for it. - infoMessage = `No active browser found for session ID '${previousSessionId}' in context. The context has been reset to default.`; + infoMessage = `No active Stagehand session found for session ID '${previousSessionId}'. The context has been reset to default.`; } return { content: [{ type: "text", text: infoMessage }] }; }; From 352b9c277db06415212f998107e8348659c0b5e0 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 25 Jun 2025 18:01:57 -0700 Subject: [PATCH 07/32] migration to just one mcp server in the repo + readme updates --- README.md | 450 ++- assets/stagehand-mcp.png | Bin 575806 -> 0 bytes browserbase/.npmignore | 15 - browserbase/README.md | 316 -- browserbase/config.d.ts | 85 - browserbase/package-lock.json | 2911 ----------------- browserbase/package.json | 61 - browserbase/playwright.config.ts | 34 - browserbase/src/config.ts | 161 - browserbase/src/context.ts | 601 ---- browserbase/src/index.ts | 109 - browserbase/src/pageSnapshot.ts | 112 - browserbase/src/program.ts | 69 - browserbase/src/server.ts | 27 - browserbase/src/sessionManager.ts | 409 --- browserbase/src/tools/common.ts | 111 - browserbase/src/tools/context.ts | 198 -- browserbase/src/tools/getText.ts | 54 - browserbase/src/tools/hover.ts | 8 - browserbase/src/tools/keyboard.ts | 41 - browserbase/src/tools/navigate.ts | 106 - browserbase/src/tools/selectOption.ts | 8 - browserbase/src/tools/session.ts | 239 -- browserbase/src/tools/snapshot.ts | 499 --- browserbase/src/tools/tool.ts | 67 - browserbase/src/tools/toolUtils.ts | 31 - browserbase/src/tools/utils.ts | 59 - browserbase/src/transport.ts | 118 - browserbase/tests/.gitkeep | 1 - browserbase/tsconfig.json | 16 - browserbase/utils/.gitkeep | 1 - browserbase/cli.js => cli.js | 0 stagehand/config.d.ts => config.d.ts | 0 browserbase/index.d.ts => index.d.ts | 0 browserbase/index.js => index.js | 0 .../package-lock.json => package-lock.json | 2 +- stagehand/package.json => package.json | 2 +- .../smithery.config.js => smithery.config.js | 0 browserbase/smithery.yaml => smithery.yaml | 0 {stagehand/src => src}/config.ts | 2 +- {stagehand/src => src}/context.ts | 0 {stagehand/src => src}/index.ts | 0 {stagehand/src => src}/program.ts | 0 {stagehand/src => src}/prompts.ts | 3 +- {stagehand/src => src}/resources.ts | 0 {stagehand/src => src}/server.ts | 0 {stagehand/src => src}/sessionManager.ts | 0 {stagehand/src => src}/tools/act.ts | 0 {stagehand/src => src}/tools/extract.ts | 0 {stagehand/src => src}/tools/index.ts | 0 {stagehand/src => src}/tools/navigate.ts | 0 {stagehand/src => src}/tools/observe.ts | 0 {stagehand/src => src}/tools/screenshot.ts | 0 {stagehand/src => src}/tools/session.ts | 0 {stagehand/src => src}/tools/tool.ts | 0 {stagehand/src => src}/transport.ts | 0 {stagehand/src => src}/utils.ts | 4 + stagehand/README.md | 510 --- stagehand/cli.js | 2 - stagehand/index.d.ts | 6 - stagehand/index.js | 2 - stagehand/smithery.config.js | 10 - stagehand/smithery.yaml | 1 - stagehand/src/tools/utils.ts | 3 - tests/.gitkeep | 0 stagehand/tsconfig.json => tsconfig.json | 0 66 files changed, 435 insertions(+), 7029 deletions(-) delete mode 100644 assets/stagehand-mcp.png delete mode 100644 browserbase/.npmignore delete mode 100644 browserbase/README.md delete mode 100644 browserbase/config.d.ts delete mode 100644 browserbase/package-lock.json delete mode 100644 browserbase/package.json delete mode 100644 browserbase/playwright.config.ts delete mode 100644 browserbase/src/config.ts delete mode 100644 browserbase/src/context.ts delete mode 100644 browserbase/src/index.ts delete mode 100644 browserbase/src/pageSnapshot.ts delete mode 100644 browserbase/src/program.ts delete mode 100644 browserbase/src/server.ts delete mode 100644 browserbase/src/sessionManager.ts delete mode 100644 browserbase/src/tools/common.ts delete mode 100644 browserbase/src/tools/context.ts delete mode 100644 browserbase/src/tools/getText.ts delete mode 100644 browserbase/src/tools/hover.ts delete mode 100644 browserbase/src/tools/keyboard.ts delete mode 100644 browserbase/src/tools/navigate.ts delete mode 100644 browserbase/src/tools/selectOption.ts delete mode 100644 browserbase/src/tools/session.ts delete mode 100644 browserbase/src/tools/snapshot.ts delete mode 100644 browserbase/src/tools/tool.ts delete mode 100644 browserbase/src/tools/toolUtils.ts delete mode 100644 browserbase/src/tools/utils.ts delete mode 100644 browserbase/src/transport.ts delete mode 100644 browserbase/tests/.gitkeep delete mode 100644 browserbase/tsconfig.json delete mode 100644 browserbase/utils/.gitkeep rename browserbase/cli.js => cli.js (100%) rename stagehand/config.d.ts => config.d.ts (100%) rename browserbase/index.d.ts => index.d.ts (100%) rename browserbase/index.js => index.js (100%) rename stagehand/package-lock.json => package-lock.json (99%) rename stagehand/package.json => package.json (97%) rename browserbase/smithery.config.js => smithery.config.js (100%) rename browserbase/smithery.yaml => smithery.yaml (100%) rename {stagehand/src => src}/config.ts (98%) rename {stagehand/src => src}/context.ts (100%) rename {stagehand/src => src}/index.ts (100%) rename {stagehand/src => src}/program.ts (100%) rename {stagehand/src => src}/prompts.ts (88%) rename {stagehand/src => src}/resources.ts (100%) rename {stagehand/src => src}/server.ts (100%) rename {stagehand/src => src}/sessionManager.ts (100%) rename {stagehand/src => src}/tools/act.ts (100%) rename {stagehand/src => src}/tools/extract.ts (100%) rename {stagehand/src => src}/tools/index.ts (100%) rename {stagehand/src => src}/tools/navigate.ts (100%) rename {stagehand/src => src}/tools/observe.ts (100%) rename {stagehand/src => src}/tools/screenshot.ts (100%) rename {stagehand/src => src}/tools/session.ts (100%) rename {stagehand/src => src}/tools/tool.ts (100%) rename {stagehand/src => src}/transport.ts (100%) rename {stagehand/src => src}/utils.ts (82%) delete mode 100644 stagehand/README.md delete mode 100755 stagehand/cli.js delete mode 100644 stagehand/index.d.ts delete mode 100644 stagehand/index.js delete mode 100644 stagehand/smithery.config.js delete mode 100644 stagehand/smithery.yaml delete mode 100644 stagehand/src/tools/utils.ts create mode 100644 tests/.gitkeep rename stagehand/tsconfig.json => tsconfig.json (100%) diff --git a/README.md b/README.md index de0de0b..844fedd 100644 --- a/README.md +++ b/README.md @@ -4,38 +4,440 @@ ![cover](assets/cover-mcp.png) -[The Model Context Protocol (MCP)](https://modelcontextprotocol.io/introduction) is an open protocol that enables seamless integration between LLM applications and external data sources and tools. Whether you’re building an AI-powered IDE, enhancing a chat interface, or creating custom AI workflows, MCP provides a standardized way to connect LLMs with the context they need. +[The Model Context Protocol (MCP)](https://modelcontextprotocol.io/introduction) is an open protocol that enables seamless integration between LLM applications and external data sources and tools. Whether you're building an AI-powered IDE, enhancing a chat interface, or creating custom AI workflows, MCP provides a standardized way to connect LLMs with the context they need. -This server provides cloud browser automation capabilities using [Browserbase](https://www.browserbase.com/) and [Stagehand](https://github.com/browserbase/stagehand). This server enables LLMs to interact with web pages, take screenshots, and execute JavaScript in a cloud browser environment. +This server provides cloud browser automation capabilities using [Browserbase](https://www.browserbase.com/) and [Stagehand](https://github.com/browserbase/stagehand). It enables LLMs to interact with web pages, take screenshots, extract information, and perform automated actions with atomic precision. -To learn to get started with Browserbase, check out [Browserbase MCP](./browserbase/README.md) or [Stagehand MCP](./stagehand/README.md). +## Features -## Getting Started with available MCPs +| Feature | Description | +| ------------------- | -------------------------------------------------------------- | +| Browser Automation | Control and orchestrate cloud browsers via Browserbase | +| Data Extraction | Extract structured data from any webpage | +| Web Interaction | Navigate, click, and fill forms with ease | +| Screenshots | Capture full-page and element screenshots | +| Model Flexibility | Supports multiple models (OpenAI, Claude, Gemini, and more) | +| Vision Support | Use annotated screenshots for complex DOMs | +| Session Management | Create, manage, and close browser sessions | -🌐 **Browserbase MCP** - Located in [`browserbase/`](./browserbase/) +### Alternative Installation Methods -| Feature | Description | -| ------------------ | ----------------------------------------- | -| Browser Automation | Control and orchestrate cloud browsers | -| Data Extraction | Extract structured data from any webpage | -| Console Monitoring | Track and analyze browser console logs | -| Screenshots | Capture full-page and element screenshots | -| Web Interaction | Navigate, click, and fill forms with ease | +[Smithery](https://smithery.ai/server/@browserbasehq/mcp-browserbase) -🤘 **Stagehand MCP** - Located in [`stagehand/`](./stagehand/) +## How to Setup -| Feature | Description | -| ------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| Atomic Instructions | Execute precise actions like `act("click the login button")` or `extract("find the red shoes")` | -| Model Flexibility | Supports multiple models, including OpenAI's GPT-4 and Anthropic's Claude-3.7 Sonnet | -| Modular Design | Easily integrate new models with minimal changes | -| Vision Support | Use annotated screenshots for complex DOMs | -| Open Source | Contribute to the project and join the [Slack community](https://join.slack.com/t/stagehand-dev/shared_invite/zt-2uvuobu50-~wVSx2Si75CPa3332hwVEw) for support | +### Quickstarts: -### Alternative Installation Methods +[![Install MCP Server](https://cursor.com/deeplink/mcp-install-dark.png)](cursor://anysphere.cursor-deeplink/mcp/install?name=browserbase&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyJAYnJvd3NlcmJhc2VocS9tY3AiXSwiZW52Ijp7IkJST1dTRVJCQVNFX0FQSV9LRVkiOiIiLCJCUk9XU0VSQkFTRV9QUk9KRUNUX0lEIjoiIn19) -[Smithery](https://smithery.ai/server/@browserbasehq/mcp-browserbase) +You can either use our Server hosted on NPM or run it completely locally by cloning this repo. + +### To run on NPM (Recommended) + +Go into your MCP Config JSON and add the Browserbase Server: + +```json +{ + "mcpServers": { + "browserbase": { + "command": "npx", + "args" : ["@browserbasehq/mcp"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +That's it! Reload your MCP client and Claude will be able to use Browserbase. + +### To run 100% local: + +```bash +# Clone the Repo +git clone https://github.com/browserbase/mcp-server-browserbase.git +cd mcp-server-browserbase + +# Install the dependencies and build the project +npm install && npm run build +``` + +Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. + +### STDIO: + +To your MCP Config JSON file add the following: + +```json +{ +"mcpServers": { + "browserbase": { + "command" : "node", + "args" : ["/path/to/mcp-server-browserbase/cli.js"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### SSE: + +Run the following command in your terminal. You can add any flags (see options below) that you see fit to customize your configuration. + +```bash + node cli.js --port 8931 +``` + +Then in your MCP Config JSON file put the following: + +```json + { + "mcpServers": { + "browserbase": { + "url": "http://localhost:8931/sse", + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } + } +``` + +Then reload your MCP client and you should be good to go! + +## Configuration + +The Browserbase MCP server accepts the following command-line flags: + +| Flag | Description | +|------|-------------| +| `--browserbaseApiKey ` | Your Browserbase API key for authentication | +| `--browserbaseProjectId ` | Your Browserbase project ID | +| `--proxies` | Enable Browserbase proxies for the session | +| `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | +| `--contextId ` | Specify a Browserbase Context ID to use | +| `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | +| `--port ` | Port to listen on for HTTP/SSE transport | +| `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | +| `--cookies [json]` | JSON array of cookies to inject into the browser | +| `--browserWidth ` | Browser viewport width (default: 1024) | +| `--browserHeight ` | Browser viewport height (default: 768) | +| `--modelName ` | The model to use for Stagehand (default: google/gemini-2.0-flash) | + +These flags can be passed directly to the CLI or configured in your MCP configuration file. + +### NOTE: + +Currently, these flags can only be used with the local server (npx @browserbasehq/mcp). + +## Configuration Examples + +### Proxies + +Here are our docs on [Proxies](https://docs.browserbase.com/features/proxies). + +To use proxies, set the --proxies flag in your MCP Config: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : ["@browserbasehq/mcp", "--proxies"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Advanced Stealth + +Here are our docs on [Advanced Stealth](https://docs.browserbase.com/features/stealth-mode#advanced-stealth-mode). + +To use advanced stealth, set the --advancedStealth flag in your MCP Config: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : ["@browserbasehq/mcp", "--advancedStealth"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Contexts + +Here are our docs on [Contexts](https://docs.browserbase.com/features/contexts) + +To use contexts, set the --contextId flag in your MCP Config: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : ["@browserbasehq/mcp", "--contextId", ""], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Cookie Injection + +Why would you need to inject cookies? Our context API currently works on persistent cookies, but not session cookies. So sometimes our persistent auth might not work (we're working hard to add this functionality). + +You can inject cookies into the MCP by adding them to your MCP Config. Your cookies JSON must be in the format of [Playwright Cookies](https://playwright.dev/docs/api/class-browsercontext#browser-context-cookies) + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : [ + "@browserbasehq/mcp", "--cookies", + '[{"name": "session", "value": "abc123", "domain": ".example.com"}]' + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Browser Viewport Sizing + +The default viewport sizing for a browser session is 1024 x 768. You can adjust the Browser viewport sizing with browserWidth and browserHeight flags. + +Here's how to use it for custom browser sizing. We recommend to stick with 16:9 aspect ratios (ie: 1920 x 1080, 1280 x 720, 1024 x 768) + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : [ + "@browserbasehq/mcp", + "--browserHeight 1080", + "--browserWidth 1920", + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +### Model Configuration + +Stagehand defaults to using Google's Gemini 2.0 Flash model, but you can configure it to use other models like GPT-4o, Claude, or other providers. + +Here's how to configure different models: + +```json +{ + "mcpServers": { + "browserbase": { + "command" : "npx", + "args" : [ + "@browserbasehq/mcp", + "--modelName", "gpt-4o" + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +Available models include: +- **Gemini**: `google/gemini-2.0-flash` (default), `google/gemini-1.5-pro`, `google/gemini-1.5-flash` +- **OpenAI**: `gpt-4o`, `gpt-4o-mini`, `o1-mini`, `o1-preview`, `o3-mini` +- **Claude**: `claude-3-5-sonnet-latest`, `claude-3-7-sonnet-latest` +- **Other providers**: Cerebras, Groq, and more + +*Note: The model must be supported in Stagehand. Check out the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms).* + +## Tools + +The Browserbase MCP server provides the following tools for browser automation: + +### Browser Automation Tools + +- **stagehand_navigate** + - Navigate to any URL in the browser + - Input: + - `url` (string): The URL to navigate to + +- **stagehand_act** + - Perform an action on the web page using natural language + - Inputs: + - `action` (string): The action to perform (e.g., "click the login button") + - `variables` (object, optional): Variables used in the action template for sensitive data + +- **stagehand_extract** + - Extract all text content from the current page (filters out CSS and JavaScript) + - No inputs required + +- **stagehand_observe** + - Observe and find actionable elements on the web page + - Input: + - `instruction` (string): Specific instruction for observation (e.g., "find the login button") + +- **screenshot** + - Capture a PNG screenshot of the current page + - No inputs required + - Output: + - `text`: Friendly confirmation message with the screenshot name + - `image`: Base-64 encoded PNG data + +### Session Management Tools + +- **browserbase_session_create** + - Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand + - Applies all configuration flags (proxies, stealth, viewport, cookies, etc.) + - Initializes Stagehand instance connected to the browser session + - Input: + - `sessionId` (string, optional): Optional session ID to use/reuse. If not provided, creates new session + - Output: + - Live debugger URL for the Browserbase session + +- **browserbase_session_close** + - Close the current Browserbase session, disconnect the browser, and cleanup Stagehand instance + - Input: + - `random_string` (string, optional): Dummy parameter for consistent tool call format + - Output: + - Confirmation message and session replay URL + +### Resources + +The server provides access to screenshot resources: + +1. **Screenshots** (`screenshot://`) + - PNG images of captured screenshots + +## Project Structure + +``` +mcp-server-browserbase/ +├── src/ # TypeScript source code +│ ├── index.ts # Main entry point and Smithery default export +│ ├── config.ts # Configuration management and CLI parsing +│ ├── context.ts # Context class managing Stagehand instances +│ ├── sessionManager.ts # Browserbase session lifecycle management +│ ├── program.ts # CLI program setup using Commander.js +│ ├── transport.ts # HTTP/SSE and STDIO transport handlers +│ ├── server.ts # Server list management +│ ├── resources.ts # Screenshot resource management +│ ├── prompts.ts # Prompt templates for MCP clients +│ ├── utils.ts # Utility functions +│ └── tools/ # Tool definitions and implementations +│ ├── act.ts # Stagehand action execution tool +│ ├── extract.ts # Page content extraction tool +│ ├── navigate.ts # URL navigation tool +│ ├── observe.ts # Element observation tool +│ ├── screenshot.ts # Screenshot capture tool +│ ├── session.ts # Session management tools +│ ├── tool.ts # Tool type definitions +│ └── utils.ts # Tool utility functions +├── dist/ # Compiled JavaScript output +├── assets/ # Images and documentation assets +├── cli.js # Executable entry point for CLI usage +├── config.d.ts # TypeScript type definitions +├── index.d.ts & index.js # Module exports for programmatic usage +├── package.json # Package metadata and dependencies +├── smithery.config.js # Smithery configuration +├── tsconfig.json # TypeScript compiler configuration +└── README.md # This file +``` + +## Module Descriptions + +### Core Modules + +**index.ts** - The main Smithery export function that creates and configures the MCP server with Zod schema validation, tool registration, and proper metadata. + +**config.ts** - Configuration management handling CLI options, environment variables, defaults, and Browserbase API validation. + +**context.ts** - The Context class that manages Stagehand instances per session, executes tool actions with error handling, and coordinates between tools and sessions. + +**sessionManager.ts** - Creates and manages Browserbase sessions via CDP, handles session lifecycle, cookie injection, and tracks active sessions. + +### Infrastructure + +**program.ts** - CLI program setup using Commander.js with all command-line options, argument parsing, and transport initialization. + +**transport.ts** - Transport layer implementations for STDIO and HTTP/SSE communication with session management across different connection types. + +**server.ts** - Server list management providing factory patterns for server creation and handling multiple concurrent connections. + +### Tools & Resources + +**tools/** - Individual tool implementations with type-safe schemas including browser automation (navigate, act, extract, observe, screenshot) and session management tools. + +**resources.ts** - Screenshot resource management with in-memory storage, URI resolution, and base64-encoded PNG data serving. + +**prompts.ts** - Prompt template definitions and retrieval system for MCP clients. + +**utils.ts** - Message sanitization utilities ensuring proper JSON formatting for MCP messages. + +## Environment Variables + +- `BROWSERBASE_API_KEY`: API key for Browserbase authentication (required) +- `BROWSERBASE_PROJECT_ID`: Project ID for Browserbase (required) +- `DEBUG`: Enable debug logging (optional) + +## MCP Capabilities + +This server implements the following MCP capabilities: + +- **Tools**: 7 tools for comprehensive browser automation + - 5 Stagehand tools: navigate, act, extract, observe, screenshot + - 2 Session management tools: create and close Browserbase sessions +- **Prompts**: Prompt templates for common automation tasks +- **Resources**: Screenshot resource management with URI-based access + +## Key Features + +- **AI-Powered Automation**: Natural language commands for web interactions +- **Multi-Model Support**: Works with OpenAI, Claude, Gemini, and more +- **Session Management**: Create, manage, and persist browser sessions +- **Screenshot Capture**: Full-page and element-specific screenshots +- **Data Extraction**: Intelligent content extraction from web pages +- **Proxy Support**: Enterprise-grade proxy capabilities +- **Stealth Mode**: Advanced anti-detection features +- **Context Persistence**: Maintain authentication and state across sessions + +For more information about the Model Context Protocol, visit: +- [MCP Documentation](https://modelcontextprotocol.io/docs) +- [MCP Specification](https://spec.modelcontextprotocol.io/) + +## License -### Credits +Licensed under the MIT License. -Huge thanks and shoutout to the Playwright team for their contributions to the framework, and their work on the [Playwright MCP Server](https://github.com/microsoft/playwright-mcp) \ No newline at end of file +Copyright 2025 Browserbase, Inc. \ No newline at end of file diff --git a/assets/stagehand-mcp.png b/assets/stagehand-mcp.png deleted file mode 100644 index 1e280f8c4592ee291382a4caba2cd885b0f1fa68..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 575806 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

- -## How to Setup - -### Quickstarts: - -[![Install MCP Server](https://cursor.com/deeplink/mcp-install-dark.png)](cursor://anysphere.cursor-deeplink/mcp/install?name=browserbase&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyJAYnJvd3NlcmJhc2VocS9tY3AiXSwiZW52Ijp7IkJST1dTRVJCQVNFX0FQSV9LRVkiOiIiLCJCUk9XU0VSQkFTRV9QUk9KRUNUX0lEIjoiIn19) - -You can either use our Server hosted on NPM or run it completely locally by cloning this repo. - -### To run on NPM (Recommended) - -Go into your MCP Config JSON and add the Browserbase Server: - -```json -{ - "mcpServers": { - "browserbase": { - "command": "npx", - "args" : ["@browserbasehq/mcp"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -Thats it! Reload your MCP client and Claude will be able to use Browserbase. - -### To run 100% local: - -```bash -# Clone the Repo -git clone https://github.com/browserbase/mcp-server-browserbase.git - -# Install the dependencies in the proper directory and build the project -cd browserbase -npm install && npm run build - -``` - -Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. - -### STDIO: - -To your MCP Config JSON file add the following: - -```json -{ -"mcpServers": { - "browserbase": { - "command" : "node", - "args" : ["/path/to/mcp-server-browserbase/browserbase/cli.js"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### SSE: - -Run the following command in your terminal. You can add any flags (see options below) that you see fit to customize your configuration. - -```bash - node cli.js --port 8931 -``` - -Then in your MCP Config JSON file put the following: - -```json - { - "mcpServers": { - "browserbase": { - "url": "http://localhost:8931/sse", - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } - } -``` - -Then reload your MCP client and you should be good to go! - -## Flags Explained: - -The Browserbase MCP server accepts the following command-line flags: - -| Flag | Description | -|------|-------------| -| `--browserbaseApiKey ` | Your Browserbase API key for authentication | -| `--browserbaseProjectId ` | Your Browserbase project ID | -| `--proxies` | Enable Browserbase proxies for the session | -| `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | -| `--contextId ` | Specify a Browserbase Context ID to use | -| `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | -| `--port ` | Port to listen on for HTTP/SSE transport | -| `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | -| `--cookies [json]` | JSON array of cookies to inject into the browser | -| `--browserWidth ` | Browser viewport width (default: 1024) | -| `--browserHeight ` | Browser viewport height (default: 768) | - -These flags can be passed directly to the CLI or configured in your MCP configuration file. - -### NOTE: - -Currently, these flags can only be used with the local server (npx @browserbasehq/mcp). - -____ - -## Flags & Example Configs - -### Proxies - -Here are our docs on [Proxies](https://docs.browserbase.com/features/proxies). - -To use proxies in STDIO, set the --proxies flag in your MCP Config: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--proxies"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` -### Advanced Stealth - -Here are our docs on [Advanced Stealth](https://docs.browserbase.com/features/stealth-mode#advanced-stealth-mode). - -To use proxies in STDIO, set the --advancedStealth flag in your MCP Config: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--advancedStealth"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Contexts - -Here are our docs on [Contexts](https://docs.browserbase.com/features/contexts) - -To use contexts in STDIO, set the --contextId flag in your MCP Config: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--contextId", ""], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Cookie Injection - -Why would you need to inject cookies? Our context API currently works on persistent cookies, but not session cookies. So sometimes our persistent auth might not work (we're working hard to add this functionality). - -You can flag cookies into the MCP by adding the cookies.json to your MCP Config. - -To use proxies in STDIO, set the --proxies flag in your MCP Config. Your cookies JSON must be in the type of [Playwright Cookies](https://playwright.dev/docs/api/class-browsercontext#browser-context-cookies) - -```json -{ - "mcpServers": { - "browserbase" { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", "--cookies", - '{ - "cookies": json, - }' - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Browser Viewport Sizing - -The default viewport sizing for a browser session is 1024 x 768. You can adjust the Browser viewport sizing with browserWidth and browserHeight flags. - -Here's how to use it for custom browser sizing. We recommend to stick with 16:9 aspect ratios (ie: 1920 x 1080, 1280, 720, 1024 x 768) - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", - "--browserHeight 1080", - "--browserWidth 1920", - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -## Structure - -* `src/`: TypeScript source code - * `index.ts`: Main entry point, env checks, shutdown - * `server.ts`: MCP Server setup and request routing - * `sessionManager.ts`: Handles Browserbase session creation/management - * `tools/`: Tool definitions and implementations - * `resources/`: Resource (screenshot) handling - * `types.ts`: Shared TypeScript types -* `dist/`: Compiled JavaScript output -* `tests/`: Placeholder for tests -* `utils/`: Placeholder for utility scripts -* `Dockerfile`: For building a Docker image -* Configuration files (`.json`, `.ts`, `.mjs`, `.npmignore`) - -## Contexts for Persistence - -This server supports Browserbase's Contexts feature, which allows persisting cookies, authentication, and cached data across browser sessions: - -1. **Creating a Context**: - ``` - browserbase_context_create: Creates a new context, optionally with a friendly name - ``` - -2. **Using a Context with a Session**: - ``` - browserbase_session_create: Now accepts a 'context' parameter with: - - id: The context ID to use - - name: Alternative to ID, the friendly name of the context - - persist: Whether to save changes (cookies, cache) back to the context (default: true) - ``` - -3. **Deleting a Context**: - ``` - browserbase_context_delete: Deletes a context when you no longer need it - ``` - -Contexts make it much easier to: -- Maintain login state across sessions -- Reduce page load times by preserving cache -- Avoid CAPTCHAs and detection by reusing browser fingerprints - -## Cookie Management - -This server also provides direct cookie management capabilities: - -1. **Adding Cookies**: - ``` - browserbase_cookies_add: Add cookies to the current browser session with full control over properties - ``` - -2. **Getting Cookies**: - ``` - browserbase_cookies_get: View all cookies in the current session (optionally filtered by URLs) - ``` - -3. **Deleting Cookies**: - ``` - browserbase_cookies_delete: Delete specific cookies or clear all cookies from the session - ``` - -These tools are useful for: -- Setting authentication cookies without navigating to login pages -- Backing up and restoring cookie state -- Debugging cookie-related issues -- Manipulating cookie attributes (expiration, security flags, etc.) - -## TODO/Roadmap - -* Implement true `ref`-based interaction logic for click, type, drag, hover, select_option. -* Implement element-specific screenshots using `ref`. -* Add more standard MCP tools (tabs, navigation, etc.). -* Add tests. diff --git a/browserbase/config.d.ts b/browserbase/config.d.ts deleted file mode 100644 index 4950123..0000000 --- a/browserbase/config.d.ts +++ /dev/null @@ -1,85 +0,0 @@ -import type { Cookie } from "playwright-core"; - -export type Config = { - /** - * The Browserbase API Key to use - */ - browserbaseApiKey?: string; - /** - * The Browserbase Project ID to use - */ - browserbaseProjectId?: string; - /** - * Whether or not to use Browserbase proxies - * https://docs.browserbase.com/features/proxies - * - * @default false - */ - proxies?: boolean; - /** - * Use advanced stealth mode. Only available to Browserbase Scale Plan users. - * - * @default false - */ - advancedStealth?: boolean; - /** - * Potential Browserbase Context to use - * Would be a context ID - */ - context?: { - /** - * The ID of the context to use - */ - contextId?: string; - /** - * Whether or not to persist the context - * - * @default true - */ - persist?: boolean; - }; - /** - * - */ - viewPort?: { - /** - * The width of the browser - */ - browserWidth?: number; - /** - * The height of the browser - */ - browserHeight?: number; - }; - /** - * Cookies to inject into the Browserbase context - * Format: Array of cookie objects with name, value, domain, and optional path, expires, httpOnly, secure, sameSite - */ - cookies?: Cookie[]; - /** - * Whether or not to port to a server - * - */ - server?: { - /** - * The port to listen on for SSE or MCP transport. - */ - port?: number; - /** - * The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces. - */ - host?: string; - }; - tools?: { - /** - * Configuration for the browser_take_screenshot tool. - */ - browserbase_take_screenshot?: { - /** - * Whether to disable base64-encoded image responses to the clients that - * don't support binary data or prefer to save on tokens. - */ - omitBase64?: boolean; - } - } -}; \ No newline at end of file diff --git a/browserbase/package-lock.json b/browserbase/package-lock.json deleted file mode 100644 index 3496fc9..0000000 --- a/browserbase/package-lock.json +++ /dev/null @@ -1,2911 +0,0 @@ -{ - "name": "@browserbasehq/mcp", - "version": "1.0.6", - "lockfileVersion": 3, - "requires": true, - "packages": { - "": { - "name": "@browserbasehq/mcp", - "version": "1.0.6", - "dependencies": { - "@browserbasehq/sdk": "^2.5.0", - "@modelcontextprotocol/sdk": "^1.10.2", - "@types/yaml": "^1.9.6", - "chromium-bidi": "^5.3.1", - "commander": "^13.1.0", - "dotenv": "^16.5.0", - "playwright": "^1.52.0", - "yaml": "^2.7.1", - "zod": "^3.24.3", - "zod-to-json-schema": "^3.24.5" - }, - "bin": { - "mcp-server-browserbase": "cli.js" - }, - "devDependencies": { - "@smithery/cli": "^1.2.4", - "shx": "^0.3.4", - "tsx": "^4.19.4", - "typescript": "^5.6.2" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@ai-sdk/provider": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/@ai-sdk/provider/-/provider-1.1.3.tgz", - "integrity": "sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "json-schema": "^0.4.0" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@ai-sdk/provider-utils": { - "version": "2.2.8", - "resolved": "https://registry.npmjs.org/@ai-sdk/provider-utils/-/provider-utils-2.2.8.tgz", - "integrity": "sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "nanoid": "^3.3.8", - "secure-json-parse": "^2.7.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.23.8" - } - }, - "node_modules/@ai-sdk/react": { - "version": "1.2.12", - "resolved": "https://registry.npmjs.org/@ai-sdk/react/-/react-1.2.12.tgz", - "integrity": "sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider-utils": "2.2.8", - "@ai-sdk/ui-utils": "1.2.11", - "swr": "^2.2.5", - "throttleit": "2.1.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "react": "^18 || ^19 || ^19.0.0-rc", - "zod": "^3.23.8" - }, - "peerDependenciesMeta": { - "zod": { - "optional": true - } - } - }, - "node_modules/@ai-sdk/ui-utils": { - "version": "1.2.11", - "resolved": "https://registry.npmjs.org/@ai-sdk/ui-utils/-/ui-utils-1.2.11.tgz", - "integrity": "sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8", - "zod-to-json-schema": "^3.24.1" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.23.8" - } - }, - "node_modules/@anthropic-ai/sdk": { - "version": "0.32.1", - "resolved": "https://registry.npmjs.org/@anthropic-ai/sdk/-/sdk-0.32.1.tgz", - "integrity": "sha512-U9JwTrDvdQ9iWuABVsMLj8nJVwAyQz6QXvgLsVhryhCEPkLsbcP/MXxm+jYcAwLoV8ESbaTTjnD4kuAFa+Hyjg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - } - }, - "node_modules/@browserbasehq/sdk": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@browserbasehq/sdk/-/sdk-2.5.0.tgz", - "integrity": "sha512-bcnbYZvm5Ht1nrHUfWDK4crspiTy1ESJYMApsMiOTUnlKOan0ocRD6m7hZH34iSC2c2XWsoryR80cwsYgCBWzQ==", - "license": "Apache-2.0", - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - } - }, - "node_modules/@esbuild/darwin-arm64": { - "version": "0.25.5", - "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.25.5.tgz", - "integrity": "sha512-GtaBgammVvdF7aPIgH2jxMDdivezgFu6iKpmT+48+F8Hhg5J/sfnDieg0aeG/jfSvkYQU2/pceFPDKlqZzwnfQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">=18" - } - }, - "node_modules/@modelcontextprotocol/sdk": { - "version": "1.10.2", - "license": "MIT", - "dependencies": { - "content-type": "^1.0.5", - "cors": "^2.8.5", - "cross-spawn": "^7.0.3", - "eventsource": "^3.0.2", - "express": "^5.0.1", - "express-rate-limit": "^7.5.0", - "pkce-challenge": "^5.0.0", - "raw-body": "^3.0.0", - "zod": "^3.23.8", - "zod-to-json-schema": "^3.24.1" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@ngrok/ngrok": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/@ngrok/ngrok/-/ngrok-1.5.1.tgz", - "integrity": "sha512-sfcgdpiAJHqmuO3e6QjQGbavIrR3E72do/NAsnGhm+7SGstLj1aM3Sd8mkfTORb2Hj7ATMuoBYuED5ylKuRQCg==", - "dev": true, - "license": "(MIT OR Apache-2.0)", - "engines": { - "node": ">= 10" - }, - "optionalDependencies": { - "@ngrok/ngrok-android-arm64": "1.5.1", - "@ngrok/ngrok-darwin-arm64": "1.5.1", - "@ngrok/ngrok-darwin-universal": "1.5.1", - "@ngrok/ngrok-darwin-x64": "1.5.1", - "@ngrok/ngrok-freebsd-x64": "1.5.1", - "@ngrok/ngrok-linux-arm-gnueabihf": "1.5.1", - "@ngrok/ngrok-linux-arm64-gnu": "1.5.1", - "@ngrok/ngrok-linux-arm64-musl": "1.5.1", - "@ngrok/ngrok-linux-x64-gnu": "1.5.1", - "@ngrok/ngrok-linux-x64-musl": "1.5.1", - "@ngrok/ngrok-win32-arm64-msvc": "1.5.1", - "@ngrok/ngrok-win32-ia32-msvc": "1.5.1", - "@ngrok/ngrok-win32-x64-msvc": "1.5.1" - } - }, - "node_modules/@ngrok/ngrok-darwin-arm64": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/@ngrok/ngrok-darwin-arm64/-/ngrok-darwin-arm64-1.5.1.tgz", - "integrity": "sha512-HNOhrPDP+nJJY7Bh45DOeh6jmcGASWINGbUuseZM0C8psQMp7crPywjRh0inkRegUrb4K8y06sfmgt2fmsF6jQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@ngrok/ngrok-darwin-universal": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/@ngrok/ngrok-darwin-universal/-/ngrok-darwin-universal-1.5.1.tgz", - "integrity": "sha512-EsMxYC/tY+ZqhjbeZtVq5MFIuD8SEPgAlHINEszsHd8ZRICc2U9Xl15CbDrew3pcfEg/ZVFrOH9CyC4aZ/V/cA==", - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@opentelemetry/api": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.0.tgz", - "integrity": "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/@smithery/cli": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/@smithery/cli/-/cli-1.2.4.tgz", - "integrity": "sha512-cXQoV6sTdOaBKQLx0UTTkHjRRD19p+tU93CqK0uOU2yfgTiG7iYYZ0/50lLbvrMWByB/80Xnk1b+atbC8F1rKQ==", - "dev": true, - "dependencies": { - "@modelcontextprotocol/sdk": "^1.10.1", - "@ngrok/ngrok": "^1.5.1", - "@smithery/registry": "^0.3.7", - "@smithery/sdk": "^1.4.3", - "@types/uuid": "^10.0.0", - "chalk": "^4.1.2", - "commander": "^14.0.0", - "cors": "^2.8.5", - "cross-fetch": "^4.1.0", - "esbuild": "^0.25.5", - "express": "^5.1.0", - "inquirer": "^8.2.4", - "inquirer-autocomplete-prompt": "^2.0.0", - "lodash": "^4.17.21", - "ora": "^8.2.0", - "uuid": "^11.1.0", - "uuidv7": "^1.0.2" - }, - "bin": { - "cli": "dist/index.js" - }, - "engines": { - "node": ">=18.0.0" - }, - "optionalDependencies": { - "bufferutil": "^4.0.9" - } - }, - "node_modules/@smithery/cli/node_modules/commander": { - "version": "14.0.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-14.0.0.tgz", - "integrity": "sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=20" - } - }, - "node_modules/@smithery/registry": { - "version": "0.3.7", - "resolved": "https://registry.npmjs.org/@smithery/registry/-/registry-0.3.7.tgz", - "integrity": "sha512-lfVsxsxF/RdQmaLTleAL2/K+blCGiEeJseFoHYWfqk8K/vZc8ypN4inVA4ABMW/cAS31VZS8inFMYeVTYgLZdQ==", - "dev": true, - "peerDependencies": { - "zod": ">= 3" - } - }, - "node_modules/@smithery/sdk": { - "version": "1.4.3", - "resolved": "https://registry.npmjs.org/@smithery/sdk/-/sdk-1.4.3.tgz", - "integrity": "sha512-Lq4F/d6aoZABR5DJdcewXzS/6FC9ov/nScykHJnALwGBX5R79AfTHXIs/egMccL9rTxlCvlYI2XhuJPBiEATMA==", - "dev": true, - "license": "MIT", - "dependencies": { - "@anthropic-ai/sdk": "^0.32.1", - "@modelcontextprotocol/sdk": "^1.10.2", - "ai": "^4.3.15", - "express": "^5.1.0", - "json-schema": "^0.4.0", - "lodash": "^4.17.21", - "okay-error": "^1.0.2", - "openai": "^4.0.0", - "uuid": "^11.0.3", - "zod": "^3.23.8", - "zod-to-json-schema": "^3.24.1" - } - }, - "node_modules/@types/diff-match-patch": { - "version": "1.0.36", - "resolved": "https://registry.npmjs.org/@types/diff-match-patch/-/diff-match-patch-1.0.36.tgz", - "integrity": "sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==", - "dev": true, - "license": "MIT" - }, - "node_modules/@types/node": { - "version": "18.19.67", - "license": "MIT", - "dependencies": { - "undici-types": "~5.26.4" - } - }, - "node_modules/@types/node-fetch": { - "version": "2.6.12", - "license": "MIT", - "dependencies": { - "@types/node": "*", - "form-data": "^4.0.0" - } - }, - "node_modules/@types/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-7gqG38EyHgyP1S+7+xomFtL+ZNHcKv6DwNaCZmJmo1vgMugyF3TCnXVg4t1uk89mLNwnLtnY3TpOpCOyp1/xHQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/@types/yaml": { - "version": "1.9.6", - "resolved": "https://registry.npmjs.org/@types/yaml/-/yaml-1.9.6.tgz", - "integrity": "sha512-VKOCuDN57wngmyQnRqcn4vuGWCXViISHv+UCCjrKcf1yt4zyfMmOGlZDI2ucTHK72V8ki+sd7h21OZL6O5S52A==", - "license": "MIT", - "dependencies": { - "yaml": "*" - } - }, - "node_modules/abort-controller": { - "version": "3.0.0", - "license": "MIT", - "dependencies": { - "event-target-shim": "^5.0.0" - }, - "engines": { - "node": ">=6.5" - } - }, - "node_modules/accepts": { - "version": "2.0.0", - "license": "MIT", - "dependencies": { - "mime-types": "^3.0.0", - "negotiator": "^1.0.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/accepts/node_modules/mime-db": { - "version": "1.54.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/accepts/node_modules/mime-types": { - "version": "3.0.1", - "license": "MIT", - "dependencies": { - "mime-db": "^1.54.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/agentkeepalive": { - "version": "4.5.0", - "license": "MIT", - "dependencies": { - "humanize-ms": "^1.2.1" - }, - "engines": { - "node": ">= 8.0.0" - } - }, - "node_modules/ai": { - "version": "4.3.16", - "resolved": "https://registry.npmjs.org/ai/-/ai-4.3.16.tgz", - "integrity": "sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8", - "@ai-sdk/react": "1.2.12", - "@ai-sdk/ui-utils": "1.2.11", - "@opentelemetry/api": "1.9.0", - "jsondiffpatch": "0.6.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "react": "^18 || ^19 || ^19.0.0-rc", - "zod": "^3.23.8" - }, - "peerDependenciesMeta": { - "react": { - "optional": true - } - } - }, - "node_modules/ansi-escapes": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.2.tgz", - "integrity": "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "type-fest": "^0.21.3" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ansi-regex": { - "version": "5.0.1", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/ansi-styles": { - "version": "4.3.0", - "dev": true, - "license": "MIT", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/asynckit": { - "version": "0.4.0", - "license": "MIT" - }, - "node_modules/balanced-match": { - "version": "1.0.2", - "dev": true, - "license": "MIT" - }, - "node_modules/base64-js": { - "version": "1.5.1", - "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/bl": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", - "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", - "dev": true, - "license": "MIT", - "dependencies": { - "buffer": "^5.5.0", - "inherits": "^2.0.4", - "readable-stream": "^3.4.0" - } - }, - "node_modules/body-parser": { - "version": "2.2.0", - "license": "MIT", - "dependencies": { - "bytes": "^3.1.2", - "content-type": "^1.0.5", - "debug": "^4.4.0", - "http-errors": "^2.0.0", - "iconv-lite": "^0.6.3", - "on-finished": "^2.4.1", - "qs": "^6.14.0", - "raw-body": "^3.0.0", - "type-is": "^2.0.0" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/brace-expansion": { - "version": "1.1.11", - "dev": true, - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "node_modules/buffer": { - "version": "5.7.1", - "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT", - "dependencies": { - "base64-js": "^1.3.1", - "ieee754": "^1.1.13" - } - }, - "node_modules/bufferutil": { - "version": "4.0.9", - "resolved": "https://registry.npmjs.org/bufferutil/-/bufferutil-4.0.9.tgz", - "integrity": "sha512-WDtdLmJvAuNNPzByAYpRo2rF1Mmradw6gvWsQKf63476DDXmomT9zUiGypLcG4ibIM67vhAj8jJRdbmEws2Aqw==", - "dev": true, - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "dependencies": { - "node-gyp-build": "^4.3.0" - }, - "engines": { - "node": ">=6.14.2" - } - }, - "node_modules/bytes": { - "version": "3.1.2", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/call-bind-apply-helpers": { - "version": "1.0.2", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/call-bound": { - "version": "1.0.4", - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.2", - "get-intrinsic": "^1.3.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/chardet": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", - "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==", - "dev": true, - "license": "MIT" - }, - "node_modules/chromium-bidi": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/chromium-bidi/-/chromium-bidi-5.3.1.tgz", - "integrity": "sha512-fbkgn0/m6RIRknVEez+QOYuvukUomBC0XnS8fgdbl9FeunjR3vUvPN6iYrbzXIuaJXYOwGU8FZgOTDzBImGvLw==", - "license": "Apache-2.0", - "dependencies": { - "mitt": "^3.0.1", - "zod": "^3.24.1" - }, - "peerDependencies": { - "devtools-protocol": "*" - } - }, - "node_modules/cli-cursor": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-3.1.0.tgz", - "integrity": "sha512-I/zHAwsKf9FqGoXM4WWRACob9+SNukZTd94DWF57E4toouRulbCxcUh6RKUEOQlYTHJnzkPMySvPNaaSLNfLZw==", - "dev": true, - "license": "MIT", - "dependencies": { - "restore-cursor": "^3.1.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/cli-spinners": { - "version": "2.9.2", - "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.9.2.tgz", - "integrity": "sha512-ywqV+5MmyL4E7ybXgKys4DugZbX0FC6LnwrhjuykIjnK9k8OQacQ7axGKnjDXWNhns0xot3bZI5h55H8yo9cJg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/cli-width": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-3.0.0.tgz", - "integrity": "sha512-FxqpkPPwu1HjuN93Omfm4h8uIanXofW0RxVEW3k5RKx+mJJYSthzNhp32Kzxxy3YAEZ/Dc/EWN1vZRY0+kOhbw==", - "dev": true, - "license": "ISC", - "engines": { - "node": ">= 10" - } - }, - "node_modules/clone": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", - "integrity": "sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.8" - } - }, - "node_modules/color-convert": { - "version": "2.0.1", - "dev": true, - "license": "MIT", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/color-name": { - "version": "1.1.4", - "dev": true, - "license": "MIT" - }, - "node_modules/combined-stream": { - "version": "1.0.8", - "license": "MIT", - "dependencies": { - "delayed-stream": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/commander": { - "version": "13.1.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-13.1.0.tgz", - "integrity": "sha512-/rFeCpNJQbhSZjGVwO9RFV3xPqbnERS8MmIQzCtD/zl6gpJuV/bMLuN92oG3F7d8oDEHHRrujSXNUr8fpjntKw==", - "license": "MIT", - "engines": { - "node": ">=18" - } - }, - "node_modules/concat-map": { - "version": "0.0.1", - "dev": true, - "license": "MIT" - }, - "node_modules/content-disposition": { - "version": "1.0.0", - "license": "MIT", - "dependencies": { - "safe-buffer": "5.2.1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/content-type": { - "version": "1.0.5", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie": { - "version": "0.7.2", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie-signature": { - "version": "1.2.2", - "license": "MIT", - "engines": { - "node": ">=6.6.0" - } - }, - "node_modules/cors": { - "version": "2.8.5", - "license": "MIT", - "dependencies": { - "object-assign": "^4", - "vary": "^1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/cross-fetch": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/cross-fetch/-/cross-fetch-4.1.0.tgz", - "integrity": "sha512-uKm5PU+MHTootlWEY+mZ4vvXoCn4fLQxT9dSc1sXVMSFkINTJVN8cAQROpwcKm8bJ/c7rgZVIBWzH5T78sNZZw==", - "dev": true, - "license": "MIT", - "dependencies": { - "node-fetch": "^2.7.0" - } - }, - "node_modules/cross-spawn": { - "version": "7.0.6", - "license": "MIT", - "dependencies": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/debug": { - "version": "4.4.0", - "license": "MIT", - "dependencies": { - "ms": "^2.1.3" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/defaults": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.4.tgz", - "integrity": "sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A==", - "dev": true, - "license": "MIT", - "dependencies": { - "clone": "^1.0.2" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/delayed-stream": { - "version": "1.0.0", - "license": "MIT", - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/depd": { - "version": "2.0.0", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/dequal": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", - "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/devtools-protocol": { - "version": "0.0.1467305", - "resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1467305.tgz", - "integrity": "sha512-LxwMLqBoPPGpMdRL4NkLFRNy3QLp6Uqa7GNp1v6JaBheop2QrB9Q7q0A/q/CYYP9sBfZdHOyszVx4gc9zyk7ow==", - "license": "BSD-3-Clause", - "peer": true - }, - "node_modules/diff-match-patch": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/diff-match-patch/-/diff-match-patch-1.0.5.tgz", - "integrity": "sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==", - "dev": true, - "license": "Apache-2.0" - }, - "node_modules/dotenv": { - "version": "16.5.0", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.5.0.tgz", - "integrity": "sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://dotenvx.com" - } - }, - "node_modules/dunder-proto": { - "version": "1.0.1", - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.1", - "es-errors": "^1.3.0", - "gopd": "^1.2.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/ee-first": { - "version": "1.1.1", - "license": "MIT" - }, - "node_modules/emoji-regex": { - "version": "8.0.0", - "dev": true, - "license": "MIT" - }, - "node_modules/encodeurl": { - "version": "2.0.0", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/es-define-property": { - "version": "1.0.1", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-errors": { - "version": "1.3.0", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-object-atoms": { - "version": "1.1.1", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/esbuild": { - "version": "0.25.5", - "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.5.tgz", - "integrity": "sha512-P8OtKZRv/5J5hhz0cUAdu/cLuPIKXpQl1R9pZtvmHWQvrAUVd0UNIPT4IB4W3rNOqVO0rlqHmCIbSwxh/c9yUQ==", - "dev": true, - "hasInstallScript": true, - "license": "MIT", - "bin": { - "esbuild": "bin/esbuild" - }, - "engines": { - "node": ">=18" - }, - "optionalDependencies": { - "@esbuild/aix-ppc64": "0.25.5", - "@esbuild/android-arm": "0.25.5", - "@esbuild/android-arm64": "0.25.5", - "@esbuild/android-x64": "0.25.5", - "@esbuild/darwin-arm64": "0.25.5", - "@esbuild/darwin-x64": "0.25.5", - "@esbuild/freebsd-arm64": "0.25.5", - "@esbuild/freebsd-x64": "0.25.5", - "@esbuild/linux-arm": "0.25.5", - "@esbuild/linux-arm64": "0.25.5", - "@esbuild/linux-ia32": "0.25.5", - "@esbuild/linux-loong64": "0.25.5", - "@esbuild/linux-mips64el": "0.25.5", - "@esbuild/linux-ppc64": "0.25.5", - "@esbuild/linux-riscv64": "0.25.5", - "@esbuild/linux-s390x": "0.25.5", - "@esbuild/linux-x64": "0.25.5", - "@esbuild/netbsd-arm64": "0.25.5", - "@esbuild/netbsd-x64": "0.25.5", - "@esbuild/openbsd-arm64": "0.25.5", - "@esbuild/openbsd-x64": "0.25.5", - "@esbuild/sunos-x64": "0.25.5", - "@esbuild/win32-arm64": "0.25.5", - "@esbuild/win32-ia32": "0.25.5", - "@esbuild/win32-x64": "0.25.5" - } - }, - "node_modules/escape-html": { - "version": "1.0.3", - "license": "MIT" - }, - "node_modules/escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/etag": { - "version": "1.8.1", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/event-target-shim": { - "version": "5.0.1", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/eventsource": { - "version": "3.0.6", - "license": "MIT", - "dependencies": { - "eventsource-parser": "^3.0.1" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/eventsource-parser": { - "version": "3.0.1", - "license": "MIT", - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/express": { - "version": "5.1.0", - "license": "MIT", - "dependencies": { - "accepts": "^2.0.0", - "body-parser": "^2.2.0", - "content-disposition": "^1.0.0", - "content-type": "^1.0.5", - "cookie": "^0.7.1", - "cookie-signature": "^1.2.1", - "debug": "^4.4.0", - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "etag": "^1.8.1", - "finalhandler": "^2.1.0", - "fresh": "^2.0.0", - "http-errors": "^2.0.0", - "merge-descriptors": "^2.0.0", - "mime-types": "^3.0.0", - "on-finished": "^2.4.1", - "once": "^1.4.0", - "parseurl": "^1.3.3", - "proxy-addr": "^2.0.7", - "qs": "^6.14.0", - "range-parser": "^1.2.1", - "router": "^2.2.0", - "send": "^1.1.0", - "serve-static": "^2.2.0", - "statuses": "^2.0.1", - "type-is": "^2.0.1", - "vary": "^1.1.2" - }, - "engines": { - "node": ">= 18" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/express" - } - }, - "node_modules/express-rate-limit": { - "version": "7.5.0", - "license": "MIT", - "engines": { - "node": ">= 16" - }, - "funding": { - "url": "https://github.com/sponsors/express-rate-limit" - }, - "peerDependencies": { - "express": "^4.11 || 5 || ^5.0.0-beta.1" - } - }, - "node_modules/express/node_modules/mime-db": { - "version": "1.54.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/express/node_modules/mime-types": { - "version": "3.0.1", - "license": "MIT", - "dependencies": { - "mime-db": "^1.54.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/external-editor": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.1.0.tgz", - "integrity": "sha512-hMQ4CX1p1izmuLYyZqLMO/qGNw10wSv9QDCPfzXfyFrOaCSSoRfqE1Kf1s5an66J5JZC62NewG+mK49jOCtQew==", - "dev": true, - "license": "MIT", - "dependencies": { - "chardet": "^0.7.0", - "iconv-lite": "^0.4.24", - "tmp": "^0.0.33" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/external-editor/node_modules/iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "dev": true, - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/figures": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", - "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", - "dev": true, - "license": "MIT", - "dependencies": { - "escape-string-regexp": "^1.0.5" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/finalhandler": { - "version": "2.1.0", - "license": "MIT", - "dependencies": { - "debug": "^4.4.0", - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "on-finished": "^2.4.1", - "parseurl": "^1.3.3", - "statuses": "^2.0.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/form-data": { - "version": "4.0.1", - "license": "MIT", - "dependencies": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "mime-types": "^2.1.12" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/form-data-encoder": { - "version": "1.7.2", - "license": "MIT" - }, - "node_modules/formdata-node": { - "version": "4.4.1", - "license": "MIT", - "dependencies": { - "node-domexception": "1.0.0", - "web-streams-polyfill": "4.0.0-beta.3" - }, - "engines": { - "node": ">= 12.20" - } - }, - "node_modules/forwarded": { - "version": "0.2.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fresh": { - "version": "2.0.0", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/fs.realpath": { - "version": "1.0.0", - "dev": true, - "license": "ISC" - }, - "node_modules/fsevents": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", - "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" - } - }, - "node_modules/function-bind": { - "version": "1.1.2", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/get-east-asian-width": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/get-east-asian-width/-/get-east-asian-width-1.3.0.tgz", - "integrity": "sha512-vpeMIQKxczTD/0s2CdEWHcb0eeJe6TFjxb+J5xgX7hScxqrGuyjmv4c1D4A/gelKfyox0gJJwIHF+fLjeaM8kQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/get-intrinsic": { - "version": "1.3.0", - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.2", - "es-define-property": "^1.0.1", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.1.1", - "function-bind": "^1.1.2", - "get-proto": "^1.0.1", - "gopd": "^1.2.0", - "has-symbols": "^1.1.0", - "hasown": "^2.0.2", - "math-intrinsics": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/get-proto": { - "version": "1.0.1", - "license": "MIT", - "dependencies": { - "dunder-proto": "^1.0.1", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/get-tsconfig": { - "version": "4.10.1", - "resolved": "https://registry.npmjs.org/get-tsconfig/-/get-tsconfig-4.10.1.tgz", - "integrity": "sha512-auHyJ4AgMz7vgS8Hp3N6HXSmlMdUyhSUrfBF16w153rxtLIEOE+HGqaBppczZvnHLqQJfiHotCYpNhl0lUROFQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "resolve-pkg-maps": "^1.0.0" - }, - "funding": { - "url": "https://github.com/privatenumber/get-tsconfig?sponsor=1" - } - }, - "node_modules/glob": { - "version": "7.2.3", - "dev": true, - "license": "ISC", - "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.1.1", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - }, - "engines": { - "node": "*" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/gopd": { - "version": "1.2.0", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/has-symbols": { - "version": "1.1.0", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/hasown": { - "version": "2.0.2", - "license": "MIT", - "dependencies": { - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/http-errors": { - "version": "2.0.0", - "license": "MIT", - "dependencies": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/humanize-ms": { - "version": "1.2.1", - "license": "MIT", - "dependencies": { - "ms": "^2.0.0" - } - }, - "node_modules/iconv-lite": { - "version": "0.6.3", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/ieee754": { - "version": "1.2.1", - "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "BSD-3-Clause" - }, - "node_modules/inflight": { - "version": "1.0.6", - "dev": true, - "license": "ISC", - "dependencies": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "node_modules/inherits": { - "version": "2.0.4", - "license": "ISC" - }, - "node_modules/inquirer": { - "version": "8.2.6", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-8.2.6.tgz", - "integrity": "sha512-M1WuAmb7pn9zdFRtQYk26ZBoY043Sse0wVDdk4Bppr+JOXyQYybdtvK+l9wUibhtjdjvtoiNy8tk+EgsYIUqKg==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-escapes": "^4.2.1", - "chalk": "^4.1.1", - "cli-cursor": "^3.1.0", - "cli-width": "^3.0.0", - "external-editor": "^3.0.3", - "figures": "^3.0.0", - "lodash": "^4.17.21", - "mute-stream": "0.0.8", - "ora": "^5.4.1", - "run-async": "^2.4.0", - "rxjs": "^7.5.5", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0", - "through": "^2.3.6", - "wrap-ansi": "^6.0.1" - }, - "engines": { - "node": ">=12.0.0" - } - }, - "node_modules/inquirer-autocomplete-prompt": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/inquirer-autocomplete-prompt/-/inquirer-autocomplete-prompt-2.0.1.tgz", - "integrity": "sha512-jUHrH0btO7j5r8DTQgANf2CBkTZChoVySD8zF/wp5fZCOLIuUbleXhf4ZY5jNBOc1owA3gdfWtfZuppfYBhcUg==", - "dev": true, - "license": "ISC", - "dependencies": { - "ansi-escapes": "^4.3.2", - "figures": "^3.2.0", - "picocolors": "^1.0.0", - "run-async": "^2.4.1", - "rxjs": "^7.5.4" - }, - "engines": { - "node": ">=12" - }, - "peerDependencies": { - "inquirer": "^8.0.0" - } - }, - "node_modules/inquirer/node_modules/is-interactive": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-interactive/-/is-interactive-1.0.0.tgz", - "integrity": "sha512-2HvIEKRoqS62guEC+qBjpvRubdX910WCMuJTZ+I9yvqKU2/12eSL549HMwtabb4oupdj2sMP50k+XJfB/8JE6w==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/inquirer/node_modules/is-unicode-supported": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz", - "integrity": "sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/inquirer/node_modules/log-symbols": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-4.1.0.tgz", - "integrity": "sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg==", - "dev": true, - "license": "MIT", - "dependencies": { - "chalk": "^4.1.0", - "is-unicode-supported": "^0.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/inquirer/node_modules/ora": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/ora/-/ora-5.4.1.tgz", - "integrity": "sha512-5b6Y85tPxZZ7QytO+BQzysW31HJku27cRIlkbAXaNx+BdcVi+LlRFmVXzeF6a7JCwJpyw5c4b+YSVImQIrBpuQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "bl": "^4.1.0", - "chalk": "^4.1.0", - "cli-cursor": "^3.1.0", - "cli-spinners": "^2.5.0", - "is-interactive": "^1.0.0", - "is-unicode-supported": "^0.1.0", - "log-symbols": "^4.1.0", - "strip-ansi": "^6.0.0", - "wcwidth": "^1.0.1" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/inquirer/node_modules/wrap-ansi": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-6.2.0.tgz", - "integrity": "sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/interpret": { - "version": "1.4.0", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/ipaddr.js": { - "version": "1.9.1", - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/is-core-module": { - "version": "2.15.1", - "dev": true, - "license": "MIT", - "dependencies": { - "hasown": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-fullwidth-code-point": { - "version": "3.0.0", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/is-interactive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-interactive/-/is-interactive-2.0.0.tgz", - "integrity": "sha512-qP1vozQRI+BMOPcjFzrjXuQvdak2pHNUMZoeG2eRbiSqyvbEf/wQtEOTOX1guk6E3t36RkaqiSt8A/6YElNxLQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-promise": { - "version": "4.0.0", - "license": "MIT" - }, - "node_modules/is-unicode-supported": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-2.1.0.tgz", - "integrity": "sha512-mE00Gnza5EEB3Ds0HfMyllZzbBrmLOX3vfWoj9A9PEnTfratQ/BcaJOuMhnkhjXvb2+FkY3VuHqtAGpTPmglFQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/isexe": { - "version": "2.0.0", - "license": "ISC" - }, - "node_modules/json-schema": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", - "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==", - "dev": true, - "license": "(AFL-2.1 OR BSD-3-Clause)" - }, - "node_modules/jsondiffpatch": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/jsondiffpatch/-/jsondiffpatch-0.6.0.tgz", - "integrity": "sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "@types/diff-match-patch": "^1.0.36", - "chalk": "^5.3.0", - "diff-match-patch": "^1.0.5" - }, - "bin": { - "jsondiffpatch": "bin/jsondiffpatch.js" - }, - "engines": { - "node": "^18.0.0 || >=20.0.0" - } - }, - "node_modules/jsondiffpatch/node_modules/chalk": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", - "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^12.17.0 || ^14.13 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/lodash": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", - "dev": true, - "license": "MIT" - }, - "node_modules/log-symbols": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-6.0.0.tgz", - "integrity": "sha512-i24m8rpwhmPIS4zscNzK6MSEhk0DUWa/8iYQWxhffV8jkI4Phvs3F+quL5xvS0gdQR0FyTCMMH33Y78dDTzzIw==", - "dev": true, - "license": "MIT", - "dependencies": { - "chalk": "^5.3.0", - "is-unicode-supported": "^1.3.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/log-symbols/node_modules/chalk": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", - "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^12.17.0 || ^14.13 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/log-symbols/node_modules/is-unicode-supported": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-1.3.0.tgz", - "integrity": "sha512-43r2mRvz+8JRIKnWJ+3j8JtjRKZ6GmjzfaE/qiBJnikNnYv/6bagRJ1kUhNk8R5EX/GkobD+r+sfxCPJsiKBLQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/math-intrinsics": { - "version": "1.1.0", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/media-typer": { - "version": "1.1.0", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/merge-descriptors": { - "version": "2.0.0", - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mime-db": { - "version": "1.52.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/mime-types": { - "version": "2.1.35", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/mimic-fn": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", - "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/mimic-function": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/mimic-function/-/mimic-function-5.0.1.tgz", - "integrity": "sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/minimatch": { - "version": "3.1.2", - "dev": true, - "license": "ISC", - "dependencies": { - "brace-expansion": "^1.1.7" - }, - "engines": { - "node": "*" - } - }, - "node_modules/minimist": { - "version": "1.2.8", - "dev": true, - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/mitt": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/mitt/-/mitt-3.0.1.tgz", - "integrity": "sha512-vKivATfr97l2/QBCYAkXYDbrIWPM2IIKEl7YPhjCvKlG3kE2gm+uBo6nEXK3M5/Ffh/FLpKExzOQ3JJoJGFKBw==", - "license": "MIT" - }, - "node_modules/ms": { - "version": "2.1.3", - "license": "MIT" - }, - "node_modules/mute-stream": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", - "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", - "dev": true, - "license": "ISC" - }, - "node_modules/nanoid": { - "version": "3.3.11", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.11.tgz", - "integrity": "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==", - "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "bin": { - "nanoid": "bin/nanoid.cjs" - }, - "engines": { - "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" - } - }, - "node_modules/negotiator": { - "version": "1.0.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/node-domexception": { - "version": "1.0.0", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/jimmywarting" - }, - { - "type": "github", - "url": "https://paypal.me/jimmywarting" - } - ], - "license": "MIT", - "engines": { - "node": ">=10.5.0" - } - }, - "node_modules/node-fetch": { - "version": "2.7.0", - "license": "MIT", - "dependencies": { - "whatwg-url": "^5.0.0" - }, - "engines": { - "node": "4.x || >=6.0.0" - }, - "peerDependencies": { - "encoding": "^0.1.0" - }, - "peerDependenciesMeta": { - "encoding": { - "optional": true - } - } - }, - "node_modules/node-gyp-build": { - "version": "4.8.4", - "resolved": "https://registry.npmjs.org/node-gyp-build/-/node-gyp-build-4.8.4.tgz", - "integrity": "sha512-LA4ZjwlnUblHVgq0oBF3Jl/6h/Nvs5fzBLwdEF4nuxnFdsfajde4WfxtJr3CaiH+F6ewcIB/q4jQ4UzPyid+CQ==", - "dev": true, - "license": "MIT", - "optional": true, - "bin": { - "node-gyp-build": "bin.js", - "node-gyp-build-optional": "optional.js", - "node-gyp-build-test": "build-test.js" - } - }, - "node_modules/object-assign": { - "version": "4.1.1", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/object-inspect": { - "version": "1.13.4", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/okay-error": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/okay-error/-/okay-error-1.0.2.tgz", - "integrity": "sha512-jbaUyzfqiOlVmrqNzxJhjNwdB2zDCtXFfIfYz49CHemPbOldo6mA7iDELiSZJkbxYj4KCmS8GdmGE6hhcjZ+Qg==", - "dev": true, - "license": "MIT" - }, - "node_modules/on-finished": { - "version": "2.4.1", - "license": "MIT", - "dependencies": { - "ee-first": "1.1.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/once": { - "version": "1.4.0", - "license": "ISC", - "dependencies": { - "wrappy": "1" - } - }, - "node_modules/onetime": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", - "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", - "dev": true, - "license": "MIT", - "dependencies": { - "mimic-fn": "^2.1.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/openai": { - "version": "4.104.0", - "resolved": "https://registry.npmjs.org/openai/-/openai-4.104.0.tgz", - "integrity": "sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - }, - "bin": { - "openai": "bin/cli" - }, - "peerDependencies": { - "ws": "^8.18.0", - "zod": "^3.23.8" - }, - "peerDependenciesMeta": { - "ws": { - "optional": true - }, - "zod": { - "optional": true - } - } - }, - "node_modules/ora": { - "version": "8.2.0", - "resolved": "https://registry.npmjs.org/ora/-/ora-8.2.0.tgz", - "integrity": "sha512-weP+BZ8MVNnlCm8c0Qdc1WSWq4Qn7I+9CJGm7Qali6g44e/PUzbjNqJX5NJ9ljlNMosfJvg1fKEGILklK9cwnw==", - "dev": true, - "license": "MIT", - "dependencies": { - "chalk": "^5.3.0", - "cli-cursor": "^5.0.0", - "cli-spinners": "^2.9.2", - "is-interactive": "^2.0.0", - "is-unicode-supported": "^2.0.0", - "log-symbols": "^6.0.0", - "stdin-discarder": "^0.2.2", - "string-width": "^7.2.0", - "strip-ansi": "^7.1.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ora/node_modules/ansi-regex": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", - "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-regex?sponsor=1" - } - }, - "node_modules/ora/node_modules/chalk": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", - "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^12.17.0 || ^14.13 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/ora/node_modules/cli-cursor": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-5.0.0.tgz", - "integrity": "sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==", - "dev": true, - "license": "MIT", - "dependencies": { - "restore-cursor": "^5.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ora/node_modules/emoji-regex": { - "version": "10.4.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.4.0.tgz", - "integrity": "sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw==", - "dev": true, - "license": "MIT" - }, - "node_modules/ora/node_modules/onetime": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-7.0.0.tgz", - "integrity": "sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "mimic-function": "^5.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ora/node_modules/restore-cursor": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz", - "integrity": "sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==", - "dev": true, - "license": "MIT", - "dependencies": { - "onetime": "^7.0.0", - "signal-exit": "^4.1.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ora/node_modules/signal-exit": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", - "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", - "dev": true, - "license": "ISC", - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/ora/node_modules/string-width": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-7.2.0.tgz", - "integrity": "sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "emoji-regex": "^10.3.0", - "get-east-asian-width": "^1.0.0", - "strip-ansi": "^7.1.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ora/node_modules/strip-ansi": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-regex": "^6.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/strip-ansi?sponsor=1" - } - }, - "node_modules/os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/parseurl": { - "version": "1.3.3", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/path-is-absolute": { - "version": "1.0.1", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/path-key": { - "version": "3.1.1", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/path-parse": { - "version": "1.0.7", - "dev": true, - "license": "MIT" - }, - "node_modules/path-to-regexp": { - "version": "8.2.0", - "license": "MIT", - "engines": { - "node": ">=16" - } - }, - "node_modules/picocolors": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", - "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", - "dev": true, - "license": "ISC" - }, - "node_modules/pkce-challenge": { - "version": "5.0.0", - "license": "MIT", - "engines": { - "node": ">=16.20.0" - } - }, - "node_modules/playwright": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.52.0.tgz", - "integrity": "sha512-JAwMNMBlxJ2oD1kce4KPtMkDeKGHQstdpFPcPH3maElAXon/QZeTvtsfXmTMRyO9TslfoYOXkSsvao2nE1ilTw==", - "license": "Apache-2.0", - "dependencies": { - "playwright-core": "1.52.0" - }, - "bin": { - "playwright": "cli.js" - }, - "engines": { - "node": ">=18" - }, - "optionalDependencies": { - "fsevents": "2.3.2" - } - }, - "node_modules/playwright-core": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.52.0.tgz", - "integrity": "sha512-l2osTgLXSMeuLZOML9qYODUQoPPnUsKsb5/P6LJ2e6uPKXUdPK5WYhN4z03G+YNbWmGDY4YENauNu4ZKczreHg==", - "license": "Apache-2.0", - "bin": { - "playwright-core": "cli.js" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/proxy-addr": { - "version": "2.0.7", - "license": "MIT", - "dependencies": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/qs": { - "version": "6.14.0", - "license": "BSD-3-Clause", - "dependencies": { - "side-channel": "^1.1.0" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/range-parser": { - "version": "1.2.1", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/raw-body": { - "version": "3.0.0", - "license": "MIT", - "dependencies": { - "bytes": "3.1.2", - "http-errors": "2.0.0", - "iconv-lite": "0.6.3", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/react": { - "version": "19.1.0", - "resolved": "https://registry.npmjs.org/react/-/react-19.1.0.tgz", - "integrity": "sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==", - "dev": true, - "license": "MIT", - "peer": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/readable-stream": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", - "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", - "dev": true, - "license": "MIT", - "dependencies": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/rechoir": { - "version": "0.6.2", - "dev": true, - "dependencies": { - "resolve": "^1.1.6" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/resolve": { - "version": "1.22.8", - "dev": true, - "license": "MIT", - "dependencies": { - "is-core-module": "^2.13.0", - "path-parse": "^1.0.7", - "supports-preserve-symlinks-flag": "^1.0.0" - }, - "bin": { - "resolve": "bin/resolve" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/resolve-pkg-maps": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/resolve-pkg-maps/-/resolve-pkg-maps-1.0.0.tgz", - "integrity": "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==", - "dev": true, - "license": "MIT", - "funding": { - "url": "https://github.com/privatenumber/resolve-pkg-maps?sponsor=1" - } - }, - "node_modules/restore-cursor": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-3.1.0.tgz", - "integrity": "sha512-l+sSefzHpj5qimhFSE5a8nufZYAM3sBSVMAPtYkmC+4EH2anSGaEMXSD0izRQbu9nfyQ9y5JrVmp7E8oZrUjvA==", - "dev": true, - "license": "MIT", - "dependencies": { - "onetime": "^5.1.0", - "signal-exit": "^3.0.2" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/router": { - "version": "2.2.0", - "license": "MIT", - "dependencies": { - "debug": "^4.4.0", - "depd": "^2.0.0", - "is-promise": "^4.0.0", - "parseurl": "^1.3.3", - "path-to-regexp": "^8.0.0" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/run-async": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.4.1.tgz", - "integrity": "sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.12.0" - } - }, - "node_modules/rxjs": { - "version": "7.8.2", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.2.tgz", - "integrity": "sha512-dhKf903U/PQZY6boNNtAGdWbG85WAbjT/1xYoZIC7FAY0yWapOBQVsVrDl58W86//e1VpMNBtRV4MaXfdMySFA==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "tslib": "^2.1.0" - } - }, - "node_modules/safe-buffer": { - "version": "5.2.1", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/safer-buffer": { - "version": "2.1.2", - "license": "MIT" - }, - "node_modules/secure-json-parse": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/secure-json-parse/-/secure-json-parse-2.7.0.tgz", - "integrity": "sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==", - "dev": true, - "license": "BSD-3-Clause" - }, - "node_modules/send": { - "version": "1.2.0", - "license": "MIT", - "dependencies": { - "debug": "^4.3.5", - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "etag": "^1.8.1", - "fresh": "^2.0.0", - "http-errors": "^2.0.0", - "mime-types": "^3.0.1", - "ms": "^2.1.3", - "on-finished": "^2.4.1", - "range-parser": "^1.2.1", - "statuses": "^2.0.1" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/send/node_modules/mime-db": { - "version": "1.54.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/send/node_modules/mime-types": { - "version": "3.0.1", - "license": "MIT", - "dependencies": { - "mime-db": "^1.54.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/serve-static": { - "version": "2.2.0", - "license": "MIT", - "dependencies": { - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "parseurl": "^1.3.3", - "send": "^1.2.0" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/setprototypeof": { - "version": "1.2.0", - "license": "ISC" - }, - "node_modules/shebang-command": { - "version": "2.0.0", - "license": "MIT", - "dependencies": { - "shebang-regex": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/shebang-regex": { - "version": "3.0.0", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/shelljs": { - "version": "0.8.5", - "dev": true, - "license": "BSD-3-Clause", - "dependencies": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - }, - "bin": { - "shjs": "bin/shjs" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/shx": { - "version": "0.3.4", - "dev": true, - "license": "MIT", - "dependencies": { - "minimist": "^1.2.3", - "shelljs": "^0.8.5" - }, - "bin": { - "shx": "lib/cli.js" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/side-channel": { - "version": "1.1.0", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "object-inspect": "^1.13.3", - "side-channel-list": "^1.0.0", - "side-channel-map": "^1.0.1", - "side-channel-weakmap": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/side-channel-list": { - "version": "1.0.0", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "object-inspect": "^1.13.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/side-channel-map": { - "version": "1.0.1", - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.5", - "object-inspect": "^1.13.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/side-channel-weakmap": { - "version": "1.0.2", - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.5", - "object-inspect": "^1.13.3", - "side-channel-map": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/signal-exit": { - "version": "3.0.7", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", - "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", - "dev": true, - "license": "ISC" - }, - "node_modules/statuses": { - "version": "2.0.1", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/stdin-discarder": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/stdin-discarder/-/stdin-discarder-0.2.2.tgz", - "integrity": "sha512-UhDfHmA92YAlNnCfhmq0VeNL5bDbiZGg7sZ2IvPsXubGkiNa9EC+tUTsjBRsYUAz87btI6/1wf4XoVvQ3uRnmQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/string_decoder": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", - "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", - "dev": true, - "license": "MIT", - "dependencies": { - "safe-buffer": "~5.2.0" - } - }, - "node_modules/string-width": { - "version": "4.2.3", - "dev": true, - "license": "MIT", - "dependencies": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/strip-ansi": { - "version": "6.0.1", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-regex": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, - "license": "MIT", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/supports-preserve-symlinks-flag": { - "version": "1.0.0", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/swr": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/swr/-/swr-2.3.3.tgz", - "integrity": "sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==", - "dev": true, - "license": "MIT", - "dependencies": { - "dequal": "^2.0.3", - "use-sync-external-store": "^1.4.0" - }, - "peerDependencies": { - "react": "^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" - } - }, - "node_modules/throttleit": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/throttleit/-/throttleit-2.1.0.tgz", - "integrity": "sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/through": { - "version": "2.3.8", - "dev": true, - "license": "MIT" - }, - "node_modules/tmp": { - "version": "0.0.33", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", - "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", - "dev": true, - "license": "MIT", - "dependencies": { - "os-tmpdir": "~1.0.2" - }, - "engines": { - "node": ">=0.6.0" - } - }, - "node_modules/toidentifier": { - "version": "1.0.1", - "license": "MIT", - "engines": { - "node": ">=0.6" - } - }, - "node_modules/tr46": { - "version": "0.0.3", - "license": "MIT" - }, - "node_modules/tslib": { - "version": "2.8.1", - "dev": true, - "license": "0BSD" - }, - "node_modules/tsx": { - "version": "4.19.4", - "resolved": "https://registry.npmjs.org/tsx/-/tsx-4.19.4.tgz", - "integrity": "sha512-gK5GVzDkJK1SI1zwHf32Mqxf2tSJkNx+eYcNly5+nHvWqXUJYUkWBQtKauoESz3ymezAI++ZwT855x5p5eop+Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "esbuild": "~0.25.0", - "get-tsconfig": "^4.7.5" - }, - "bin": { - "tsx": "dist/cli.mjs" - }, - "engines": { - "node": ">=18.0.0" - }, - "optionalDependencies": { - "fsevents": "~2.3.3" - } - }, - "node_modules/tsx/node_modules/fsevents": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", - "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", - "dev": true, - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" - } - }, - "node_modules/type-fest": { - "version": "0.21.3", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.21.3.tgz", - "integrity": "sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==", - "dev": true, - "license": "(MIT OR CC0-1.0)", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/type-is": { - "version": "2.0.1", - "license": "MIT", - "dependencies": { - "content-type": "^1.0.5", - "media-typer": "^1.1.0", - "mime-types": "^3.0.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/type-is/node_modules/mime-db": { - "version": "1.54.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/type-is/node_modules/mime-types": { - "version": "3.0.1", - "license": "MIT", - "dependencies": { - "mime-db": "^1.54.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/typescript": { - "version": "5.7.2", - "dev": true, - "license": "Apache-2.0", - "bin": { - "tsc": "bin/tsc", - "tsserver": "bin/tsserver" - }, - "engines": { - "node": ">=14.17" - } - }, - "node_modules/undici-types": { - "version": "5.26.5", - "license": "MIT" - }, - "node_modules/unpipe": { - "version": "1.0.0", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/use-sync-external-store": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.5.0.tgz", - "integrity": "sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==", - "dev": true, - "license": "MIT", - "peerDependencies": { - "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" - } - }, - "node_modules/util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", - "dev": true, - "license": "MIT" - }, - "node_modules/uuid": { - "version": "11.1.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-11.1.0.tgz", - "integrity": "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A==", - "dev": true, - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/esm/bin/uuid" - } - }, - "node_modules/uuidv7": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uuidv7/-/uuidv7-1.0.2.tgz", - "integrity": "sha512-8JQkH4ooXnm1JCIhqTMbtmdnYEn6oKukBxHn1Ic9878jMkL7daTI7anTExfY18VRCX7tcdn5quzvCb6EWrR8PA==", - "dev": true, - "license": "Apache-2.0", - "bin": { - "uuidv7": "cli.js" - } - }, - "node_modules/vary": { - "version": "1.1.2", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/wcwidth": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/wcwidth/-/wcwidth-1.0.1.tgz", - "integrity": "sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==", - "dev": true, - "license": "MIT", - "dependencies": { - "defaults": "^1.0.3" - } - }, - "node_modules/web-streams-polyfill": { - "version": "4.0.0-beta.3", - "license": "MIT", - "engines": { - "node": ">= 14" - } - }, - "node_modules/webidl-conversions": { - "version": "3.0.1", - "license": "BSD-2-Clause" - }, - "node_modules/whatwg-url": { - "version": "5.0.0", - "license": "MIT", - "dependencies": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" - } - }, - "node_modules/which": { - "version": "2.0.2", - "license": "ISC", - "dependencies": { - "isexe": "^2.0.0" - }, - "bin": { - "node-which": "bin/node-which" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/wrappy": { - "version": "1.0.2", - "license": "ISC" - }, - "node_modules/ws": { - "version": "8.18.0", - "dev": true, - "license": "MIT", - "optional": true, - "peer": true, - "engines": { - "node": ">=10.0.0" - }, - "peerDependencies": { - "bufferutil": "^4.0.1", - "utf-8-validate": ">=5.0.2" - }, - "peerDependenciesMeta": { - "bufferutil": { - "optional": true - }, - "utf-8-validate": { - "optional": true - } - } - }, - "node_modules/yaml": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.7.1.tgz", - "integrity": "sha512-10ULxpnOCQXxJvBgxsn9ptjq6uviG/htZKk9veJGhlqn3w/DxQ631zFF+nlQXLwmImeS5amR2dl2U8sg6U9jsQ==", - "license": "ISC", - "bin": { - "yaml": "bin.mjs" - }, - "engines": { - "node": ">= 14" - } - }, - "node_modules/zod": { - "version": "3.24.3", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/colinhacks" - } - }, - "node_modules/zod-to-json-schema": { - "version": "3.24.5", - "resolved": "https://registry.npmjs.org/zod-to-json-schema/-/zod-to-json-schema-3.24.5.tgz", - "integrity": "sha512-/AuWwMP+YqiPbsJx5D6TfgRTc4kTLjsh5SOcd4bLsfUg2RcEXrFMJl1DGgdHy2aCfsIA/cr/1JM0xcB2GZji8g==", - "license": "ISC", - "peerDependencies": { - "zod": "^3.24.1" - } - } - } -} diff --git a/browserbase/package.json b/browserbase/package.json deleted file mode 100644 index 0725c98..0000000 --- a/browserbase/package.json +++ /dev/null @@ -1,61 +0,0 @@ -{ - "name": "@browserbasehq/mcp", - "version": "1.0.6", - "description": "MCP server for browser automation using browserbase", - "author": "Browserbase, Inc. (https://browserbase.com)", - "homepage": "https://browserbase.com", - "module": "./src/index.ts", - "type": "module", - "main": "./cli.js", - "engines": { - "node": ">=18" - }, - "files": [ - "../assets/browserbase-mcp.png", - "dist", - "cli.js", - "index.d.ts", - "index.js", - "config.d.ts", - "config.js" - ], - "scripts": { - "build": "tsc && shx chmod +x dist/*.js && shx chmod +x cli.js", - "prepare": "npm run build", - "watch": "tsc --watch", - "smithery": "npx @smithery/cli dev", - "inspector": "npx @modelcontextprotocol/inspector build/index.js", - "test-local": "npm pack && npm install -g $(pwd)/$(ls -t *.tgz | head -1) && mcp-server-browserbase" - }, - "exports": { - "./package.json": "./package.json", - ".": { - "types": "./index.d.ts", - "default": "./cli.js" - } - }, - "dependencies": { - "@browserbasehq/sdk": "^2.5.0", - "@modelcontextprotocol/sdk": "^1.10.2", - "@types/yaml": "^1.9.6", - "chromium-bidi": "^5.3.1", - "commander": "^13.1.0", - "dotenv": "^16.5.0", - "playwright": "^1.52.0", - "yaml": "^2.7.1", - "zod": "^3.24.3", - "zod-to-json-schema": "^3.24.5" - }, - "devDependencies": { - "@smithery/cli": "^1.2.4", - "shx": "^0.3.4", - "tsx": "^4.19.4", - "typescript": "^5.6.2" - }, - "bin": { - "mcp-server-browserbase": "cli.js" - }, - "publishConfig": { - "access": "public" - } -} diff --git a/browserbase/playwright.config.ts b/browserbase/playwright.config.ts deleted file mode 100644 index a747d67..0000000 --- a/browserbase/playwright.config.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { defineConfig } from '@playwright/test'; - -/** - * Basic Playwright config - primarily useful if adding actual - * tests later - */ -export default defineConfig({ - testDir: './tests', - fullyParallel: true, - forbidOnly: !!process.env.CI, - retries: process.env.CI ? 2 : 0, - workers: process.env.CI ? 1 : undefined, - reporter: 'html', - use: { - trace: 'on-first-retry', - // Base URL to use in actions like `await page.goto('/')` - // baseURL: 'http://127.0.0.1:3000', - }, - - /* Configure projects for major browsers */ - // projects: [ - // { - // name: 'chromium', - // use: { ...devices['Desktop Chrome'] }, - // }, - // ], - - /* Run your local dev server before starting the tests */ - // webServer: { - // command: 'npm run start', - // url: 'http://127.0.0.1:3000', - // reuseExistingServer: !process.env.CI, - // }, -}); \ No newline at end of file diff --git a/browserbase/src/config.ts b/browserbase/src/config.ts deleted file mode 100644 index be94737..0000000 --- a/browserbase/src/config.ts +++ /dev/null @@ -1,161 +0,0 @@ -import os from 'os'; -import fs from 'fs'; -import path from 'path'; -import { sanitizeForFilePath } from './tools/utils.js'; -import type { Cookie } from "playwright-core"; - -export type ToolCapability = 'core' | string; - -export interface Config { - browserbaseApiKey?: string; - browserbaseProjectId?: string; - server?: { - port?: number; - host?: string; - }; - proxies?: boolean; - advancedStealth?: boolean; - context?: { - contextId?: string; - persist?: boolean; - }; - viewPort?: { - browserWidth?: number; - browserHeight?: number; - }; - cookies?: Cookie[]; -} - -// Define Command Line Options Structure -export type CLIOptions = { - browserbaseApiKey?: string; - browserbaseProjectId?: string; - proxies?: boolean; - advancedStealth?: boolean; - contextId?: string; - persist?: boolean; - port?: number; - host?: string; - cookies?: Cookie[]; - browserWidth?: number; - browserHeight?: number; -}; - -// Default Configuration Values -const defaultConfig: Config = { - browserbaseApiKey: process.env.BROWSERBASE_API_KEY, - browserbaseProjectId: process.env.BROWSERBASE_PROJECT_ID, - proxies: false, - server: { - port: undefined, - host: undefined, - }, - viewPort: { - browserWidth: 1024, - browserHeight: 768, - }, - cookies: undefined, -}; - -// Resolve final configuration by merging defaults, file config, and CLI options -export async function resolveConfig(cliOptions: CLIOptions): Promise { - const cliConfig = await configFromCLIOptions(cliOptions); - // Order: Defaults < File Config < CLI Overrides - const mergedConfig = mergeConfig(defaultConfig, cliConfig); - - // --- Add Browserbase Env Vars --- - // Ensure env vars are read *after* dotenv potentially runs (in index.ts) - if (!mergedConfig.browserbaseApiKey) { - mergedConfig.browserbaseApiKey = process.env.BROWSERBASE_API_KEY; - } - if (!mergedConfig.browserbaseProjectId) { - mergedConfig.browserbaseProjectId = process.env.BROWSERBASE_PROJECT_ID; - } - // -------------------------------- - - // Basic validation for Browserbase keys - if (!mergedConfig.browserbaseApiKey) { - console.warn("Warning: BROWSERBASE_API_KEY environment variable not set."); - } - if (!mergedConfig.browserbaseProjectId) { - console.warn("Warning: BROWSERBASE_PROJECT_ID environment variable not set."); - } - - return mergedConfig; -} - -// Create Config structure based on CLI options -export async function configFromCLIOptions(cliOptions: CLIOptions): Promise { - return { - browserbaseApiKey: cliOptions.browserbaseApiKey, - browserbaseProjectId: cliOptions.browserbaseProjectId, - server: { - port: cliOptions.port, - host: cliOptions.host, - }, - proxies: cliOptions.proxies, - context: { - contextId: cliOptions.contextId, - persist: cliOptions.persist, - }, - viewPort: { - browserWidth: cliOptions.browserWidth, - browserHeight: cliOptions.browserHeight, - }, - advancedStealth: cliOptions.advancedStealth, - cookies: cliOptions.cookies, - }; -} - -// Create an output file path within the configured output directory -export async function outputFile(config: Config, name: string): Promise { - const outputDir = os.tmpdir(); - await fs.promises.mkdir(outputDir, { recursive: true }); - const sanitizedName = sanitizeForFilePath(name); - return path.join(outputDir, sanitizedName); -} - -// Helper function to merge config objects, excluding undefined values -function pickDefined(obj: T | undefined): Partial { - if (!obj) return {}; - return Object.fromEntries( - Object.entries(obj).filter(([_, v]) => v !== undefined) - ) as Partial; -} - -// Merge two configuration objects (overrides takes precedence) -function mergeConfig(base: Config, overrides: Config): Config { - const baseFiltered = pickDefined(base); - const overridesFiltered = pickDefined(overrides); - - // Create the result object - const result = { ...baseFiltered } as Config; - - // For each property in overrides - for (const [key, value] of Object.entries(overridesFiltered)) { - if (key === 'context' && value && result.context) { - // Special handling for context object to ensure deep merge - result.context = { - ...result.context, - ...(value as Config['context']) - }; - } else if ( - value && - typeof value === 'object' && - !Array.isArray(value) && - result[key as keyof Config] && - typeof result[key as keyof Config] === 'object' - ) { - // Deep merge for other nested objects - result[key as keyof Config] = { - ...(result[key as keyof Config] as object), - ...value - } as any; - } else { - // Simple override for primitives, arrays, etc. - result[key as keyof Config] = value as any; - } - } - - return result; -} \ No newline at end of file diff --git a/browserbase/src/context.ts b/browserbase/src/context.ts deleted file mode 100644 index e315990..0000000 --- a/browserbase/src/context.ts +++ /dev/null @@ -1,601 +0,0 @@ -import type { Server } from "@modelcontextprotocol/sdk/server/index.js"; -import type { BrowserSession } from "./sessionManager.js"; -import { - getSession, - defaultSessionId, - getSessionReadOnly, -} from "./sessionManager.js"; -import type { Tool, ToolResult } from "./tools/tool.js"; -import type { Config } from "../config.js"; -import { - Resource, - CallToolResult, - TextContent, - ImageContent, -} from "@modelcontextprotocol/sdk/types.js"; -import { z } from "zod"; -import { PageSnapshot } from "./pageSnapshot.js"; -import type { Page, Locator } from "playwright"; - -export type ToolActionResult = - | { content?: (ImageContent | TextContent)[] } - | undefined - | void; - -/** - * Manages the context for tool execution within a specific Browserbase session. - */ - -export class Context { - private server: Server; - public readonly config: Config; - public currentSessionId: string = defaultSessionId; - private latestSnapshots = new Map(); - private screenshotResources = new Map< - string, - { format: string; bytes: string; uri: string } - >(); - - constructor(server: Server, config: Config) { - this.server = server; - this.config = config; - this.screenshotResources = new Map(); - } - - // --- Snapshot State Handling (Using PageSnapshot) --- - - /** - * Returns the latest PageSnapshot for the currently active session. - * Throws an error if no snapshot is available for the active session. - */ - snapshotOrDie(): PageSnapshot { - const snapshot = this.latestSnapshots.get(this.currentSessionId); - if (!snapshot) { - throw new Error( - `No snapshot available for the current session (${this.currentSessionId}). Capture a snapshot first.` - ); - } - return snapshot; - } - - /** - * Clears the snapshot for the currently active session. - */ - clearLatestSnapshot(): void { - this.latestSnapshots.delete(this.currentSessionId); - } - - /** - * Captures a new PageSnapshot for the currently active session and stores it. - * Returns the captured snapshot or undefined if capture failed. - */ - async captureSnapshot(): Promise { - const logPrefix = `[Context.captureSnapshot] ${new Date().toISOString()} Session ${ - this.currentSessionId - }:`; - let page; - try { - page = await this.getActivePage(); - } catch (error) { - this.clearLatestSnapshot(); - return undefined; - } - - if (!page) { - this.clearLatestSnapshot(); - return undefined; - } - - try { - await this.waitForTimeout(100); // Small delay for UI settlement - const snapshot = await PageSnapshot.create(page); - this.latestSnapshots.set(this.currentSessionId, snapshot); - return snapshot; - } catch (error) { - process.stderr.write( - `${logPrefix} Failed to capture snapshot: ${ - error instanceof Error ? error.message : String(error) - }\\n` - ); // Enhanced logging - this.clearLatestSnapshot(); - return undefined; - } - } - - // --- Resource Handling Methods --- - - listResources(): Resource[] { - const resources: Resource[] = []; - for (const [name, data] of this.screenshotResources.entries()) { - resources.push({ - uri: data.uri, - mimeType: `image/${data.format}`, // Ensure correct mime type - name: `Screenshot: ${name}`, - }); - } - return resources; - } - - readResource(uri: string): { uri: string; mimeType: string; blob: string } { - const prefix = "mcp://screenshots/"; - if (uri.startsWith(prefix)) { - const name = uri.split("/").pop() || ""; - const data = this.screenshotResources.get(name); - if (data) { - return { - uri, - mimeType: `image/${data.format}`, // Ensure correct mime type - blob: data.bytes, - }; - } else { - throw new Error(`Screenshot resource not found: ${name}`); - } - } else { - throw new Error(`Resource URI format not recognized: ${uri}`); - } - } - - addScreenshot(name: string, format: "png" | "jpeg", bytes: string): void { - const uri = `mcp://screenshots/${name}`; - this.screenshotResources.set(name, { format, bytes, uri }); - this.server.notification({ - method: "resources/list_changed", - params: {}, - }); - } - - // --- Session and Tool Execution --- - - public async getActivePage(): Promise { - const session = await getSession(this.currentSessionId, this.config); - if (!session || !session.page || session.page.isClosed()) { - try { - // getSession does not support a refresh flag currently. - // If a session is invalid, it needs to be recreated or re-established upstream. - // For now, just return null if the fetched session is invalid. - const currentSession = await getSession( - this.currentSessionId, - this.config - ); - if ( - !currentSession || - !currentSession.page || - currentSession.page.isClosed() - ) { - return null; - } - return currentSession.page; - } catch (refreshError) { - return null; - } - } - return session.page; - } - - public async getActiveBrowser(): Promise { - const session = await getSession(this.currentSessionId, this.config); - if (!session || !session.browser || !session.browser.isConnected()) { - try { - // getSession does not support a refresh flag currently. - const currentSession = await getSession( - this.currentSessionId, - this.config - ); - if ( - !currentSession || - !currentSession.browser || - !currentSession.browser.isConnected() - ) { - return null; - } - return currentSession.browser; - } catch (refreshError) { - return null; - } - } - return session.browser; - } - - /** - * Get the active browser without triggering session creation. - * This is a read-only operation used when we need to check for an existing browser - * without side effects (e.g., during close operations). - * @returns The browser if it exists and is connected, null otherwise - */ - public getActiveBrowserReadOnly(): BrowserSession["browser"] | null { - const session = getSessionReadOnly(this.currentSessionId); - if (!session || !session.browser || !session.browser.isConnected()) { - return null; - } - return session.browser; - } - - /** - * Get the active page without triggering session creation. - * This is a read-only operation used when we need to check for an existing page - * without side effects. - * @returns The page if it exists and is not closed, null otherwise - */ - public getActivePageReadOnly(): BrowserSession["page"] | null { - const session = getSessionReadOnly(this.currentSessionId); - if (!session || !session.page || session.page.isClosed()) { - return null; - } - return session.page; - } - - public async waitForTimeout(timeoutMillis: number): Promise { - return new Promise((resolve) => setTimeout(resolve, timeoutMillis)); - } - - private createErrorResult(message: string, toolName: string): CallToolResult { - return { - content: [{ type: "text", text: `Error: ${message}` }], - isError: true, - }; - } - - // --- Refactored Action Execution with Retries --- - private async executeRefAction( - toolName: string, - validatedArgs: any, - actionFn: ( - page: Page, - identifier: string | undefined, - args: any, - locator: Locator | undefined, - identifierType: "ref" | "selector" | "none" - ) => Promise, - requiresIdentifier: boolean = true - ): Promise<{ resultText: string; actionResult?: ToolActionResult | void }> { - let lastError: Error | null = null; - let page: Page | null = null; - let actionResult: ToolActionResult | void | undefined; - let resultText = ""; - let identifier: string | undefined = undefined; - let identifierType: "ref" | "selector" | "none" = "none"; - - // --- Get page and snapshot BEFORE the loop --- - page = await this.getActivePage(); - if (!page) { - throw new Error("Failed to get active page before action attempts."); - } - - // Get the CURRENT latest snapshot - DO NOT capture a new one here. - const snapshot = this.latestSnapshots.get(this.currentSessionId); - const initialSnapshotIdentifier = - snapshot?.text().substring(0, 60).replace(/\\n/g, "\\\\n") ?? - "[No Snapshot]"; - - let locator: Locator | undefined; - - // --- Resolve locator: Prioritize selector, then ref --- - if (validatedArgs?.selector) { - identifier = validatedArgs.selector; - identifierType = "selector"; - if (!identifier) { - throw new Error( - `Missing required 'selector' argument for tool ${toolName}.` - ); - } - try { - locator = page.locator(identifier); - } catch (locatorError) { - throw new Error( - `Failed to create locator for selector '${identifier}': ${ - locatorError instanceof Error - ? locatorError.message - : String(locatorError) - }` - ); - } - } else if (validatedArgs?.ref) { - identifier = validatedArgs.ref; - identifierType = "ref"; - if (!identifier) { - throw new Error( - `Missing required 'ref' argument for tool ${toolName}.` - ); - } - if (!snapshot) { - throw new Error( - `Cannot resolve ref '${identifier}' because no snapshot is available for session ${this.currentSessionId}. Capture a snapshot or ensure one exists.` - ); - } - try { - // Resolve using the snapshot we just retrieved - locator = snapshot.refLocator(identifier); - } catch (locatorError) { - // Use the existing snapshot identifier in the error - throw new Error( - `Failed to resolve ref ${identifier} using existing snapshot ${initialSnapshotIdentifier} before action attempt: ${ - locatorError instanceof Error - ? locatorError.message - : String(locatorError) - }` - ); - } - } else if (requiresIdentifier) { - // If neither ref nor selector is provided, but one is required - throw new Error( - `Missing required 'ref' or 'selector' argument for tool ${toolName}.` - ); - } else { - // No identifier needed or provided - identifierType = "none"; // Explicitly set to none - } - - // --- Single Attempt --- - try { - // Pass page, the used identifier (selector or ref), args, the resolved locator, and identifierType - const actionFnResult = await actionFn( - page, - identifier, - validatedArgs, - locator, - identifierType - ); - - if (typeof actionFnResult === "string") { - resultText = actionFnResult; - actionResult = undefined; - } else { - actionResult = actionFnResult; - const content = actionResult?.content; - if (Array.isArray(content) && content.length > 0) { - resultText = - content - .map((c: { type: string; text?: string }) => - c.type === "text" ? c.text : `[${c.type}]` - ) - .filter(Boolean) - .join(" ") || `${toolName} action completed.`; - } else { - resultText = `${toolName} action completed successfully.`; - } - } - lastError = null; - return { resultText, actionResult }; - } catch (error: any) { - throw new Error( - `Action ${toolName} failed: ${ - error instanceof Error ? error.message : String(error) - }` - ); - } - } - - async run(tool: Tool, args: any): Promise { - const toolName = tool.schema.name; - let initialPage: Page | null = null; - let initialBrowser: BrowserSession["browser"] | null = null; - let toolResultFromHandle: ToolResult | null = null; // Legacy handle result - let finalResult: CallToolResult = { - // Initialize finalResult here - content: [{ type: "text", text: `Initialization error for ${toolName}` }], - isError: true, - }; - - const logPrefix = `[Context.run ${toolName}] ${new Date().toISOString()}:`; - - let validatedArgs: any; - try { - validatedArgs = tool.schema.inputSchema.parse(args); - } catch (error) { - if (error instanceof z.ZodError) { - const errorMsg = error.issues.map((issue) => issue.message).join(", "); - return this.createErrorResult( - `Input validation failed: ${errorMsg}`, - toolName - ); - } - return this.createErrorResult( - `Input validation failed: ${ - error instanceof Error ? error.message : String(error) - }`, - toolName - ); - } - - const previousSessionId = this.currentSessionId; - if ( - validatedArgs?.sessionId && - validatedArgs.sessionId !== this.currentSessionId - ) { - this.currentSessionId = validatedArgs.sessionId; - this.clearLatestSnapshot(); - } - - if (toolName !== "browserbase_session_create") { - try { - const session = await getSession(this.currentSessionId, this.config); - if ( - !session || - !session.page || - session.page.isClosed() || - !session.browser || - !session.browser.isConnected() - ) { - if (this.currentSessionId !== previousSessionId) { - this.currentSessionId = previousSessionId; - } - throw new Error( - `Session ${this.currentSessionId} is invalid or browser/page is not available.` - ); - } - initialPage = session.page; - initialBrowser = session.browser; - } catch (sessionError) { - return this.createErrorResult( - `Error retrieving or validating session ${this.currentSessionId}: ${ - sessionError instanceof Error - ? sessionError.message - : String(sessionError) - }`, - toolName - ); - } - } - - let toolActionOutput: ToolActionResult | undefined = undefined; // New variable to store direct tool action output - let actionSucceeded = false; - let shouldCaptureSnapshotAfterAction = false; - let postActionSnapshot: PageSnapshot | undefined = undefined; - - try { - let actionToRun: (() => Promise) | undefined = - undefined; - let shouldCaptureSnapshot = false; - - try { - if ("handle" in tool && typeof tool.handle === "function") { - toolResultFromHandle = await tool.handle(this as any, validatedArgs); - actionToRun = toolResultFromHandle?.action; - shouldCaptureSnapshot = - toolResultFromHandle?.captureSnapshot ?? false; - shouldCaptureSnapshotAfterAction = shouldCaptureSnapshot; - } else { - throw new Error( - `Tool ${toolName} could not be handled (no handle method).` - ); - } - - if (actionToRun) { - toolActionOutput = await actionToRun(); - actionSucceeded = true; - } else { - throw new Error(`Tool ${toolName} handled without action.`); - } - } catch (error) { - process.stderr.write( - `${logPrefix} Error executing tool ${toolName}: ${ - error instanceof Error ? error.message : String(error) - }\\n` - ); - if (error instanceof Error && error.stack) { - process.stderr.write(`${logPrefix} Stack Trace: ${error.stack}\\n`); - } - // ----------------------- - finalResult = this.createErrorResult( - `Execution failed: ${ - error instanceof Error ? error.message : String(error) - }`, - toolName - ); - actionSucceeded = false; - shouldCaptureSnapshotAfterAction = false; - if ( - this.currentSessionId !== previousSessionId && - toolName !== "browserbase_session_create" - ) { - this.currentSessionId = previousSessionId; - } - } finally { - if (actionSucceeded && shouldCaptureSnapshotAfterAction) { - const preSnapshotDelay = 500; - await this.waitForTimeout(preSnapshotDelay); - try { - postActionSnapshot = await this.captureSnapshot(); - if (postActionSnapshot) { - process.stderr.write( - `[Context.run ${toolName}] Added snapshot to final result text.\n` - ); - } else { - process.stderr.write( - `[Context.run ${toolName}] WARN: Snapshot was expected after action but failed to capture.\n` - ); // Keep warning - } - } catch (postSnapError) { - process.stderr.write( - `[Context.run ${toolName}] WARN: Error capturing post-action snapshot: ${ - postSnapError instanceof Error - ? postSnapError.message - : String(postSnapError) - }\n` - ); // Keep warning - } - } else if ( - actionSucceeded && - toolName === "browserbase_snapshot" && - !postActionSnapshot - ) { - postActionSnapshot = this.latestSnapshots.get(this.currentSessionId); - } - - if (actionSucceeded) { - const finalContentItems: (TextContent | ImageContent)[] = []; - - // 1. Add content from the tool action itself - if (toolActionOutput?.content && toolActionOutput.content.length > 0) { - finalContentItems.push(...toolActionOutput.content); - } else { - // If toolActionOutput.content is empty/undefined but action succeeded, - // provide a generic success message. - finalContentItems.push({ type: "text", text: `${toolName} action completed successfully.` }); - } - - // 2. Prepare and add additional textual information (URL, Title, Snapshot) - const additionalInfoParts: string[] = []; - // Use read-only version to avoid creating sessions after close - const currentPage = this.getActivePageReadOnly(); - - if (currentPage) { - try { - const url = currentPage.url(); - const title = await currentPage - .title() - .catch(() => "[Error retrieving title]"); - additionalInfoParts.push(`- Page URL: ${url}`); - additionalInfoParts.push(`- Page Title: ${title}`); - } catch (pageStateError) { - additionalInfoParts.push( - "- [Error retrieving page state after action]" - ); - } - } else { - additionalInfoParts.push("- [Page unavailable after action]"); - } - - const snapshotToAdd = postActionSnapshot; - if (snapshotToAdd) { - additionalInfoParts.push( - `- Page Snapshot\n\`\`\`yaml\n${snapshotToAdd.text()}\n\`\`\`\n` - ); - } else { - additionalInfoParts.push( - `- [No relevant snapshot available after action]` - ); - } - - // 3. Add the additional information as a new TextContent item if it's not empty - if (additionalInfoParts.length > 0) { - // Add leading newlines if there's preceding content, to maintain separation - const additionalInfoText = (finalContentItems.length > 0 ? "\\n\\n" : "") + additionalInfoParts.join("\\n"); - finalContentItems.push({ type: "text", text: additionalInfoText }); - } - - finalResult = { - content: finalContentItems, - isError: false, - }; - } else { - // Error result is already set in catch block, but ensure it IS set. - if (!finalResult || !finalResult.isError) { - finalResult = this.createErrorResult( - `Unknown error occurred during ${toolName}`, - toolName - ); - } - } - return finalResult; - } - } catch (error) { - process.stderr.write( - `${logPrefix} Error running tool ${toolName}: ${ - error instanceof Error ? error.message : String(error) - }\n` - ); - throw error; - } - } -} diff --git a/browserbase/src/index.ts b/browserbase/src/index.ts deleted file mode 100644 index 8769336..0000000 --- a/browserbase/src/index.ts +++ /dev/null @@ -1,109 +0,0 @@ -import dotenv from "dotenv"; -dotenv.config(); - -import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js'; -import { z } from 'zod'; -import type { Tool } from "./tools/tool.js"; - -import navigate from "./tools/navigate.js"; -import snapshot from "./tools/snapshot.js"; -import keyboard from "./tools/keyboard.js"; -import getText from "./tools/getText.js"; -import session from "./tools/session.js"; -import common from "./tools/common.js"; -import contextTools from "./tools/context.js"; - -import { Context } from "./context.js"; -import type { Config } from "./config.js"; - -// Configuration schema for Smithery - matches existing Config interface -export const configSchema = z.object({ - browserbaseApiKey: z.string().describe("The Browserbase API Key to use"), - browserbaseProjectId: z.string().describe("The Browserbase Project ID to use"), - proxies: z.boolean().optional().describe("Whether or not to use Browserbase proxies"), - advancedStealth: z.boolean().optional().describe("Use advanced stealth mode. Only available to Browserbase Scale Plan users"), - context: z.object({ - contextId: z.string().optional().describe("The ID of the context to use"), - persist: z.boolean().optional().describe("Whether or not to persist the context") - }).optional(), - viewPort: z.object({ - browserWidth: z.number().optional().describe("The width of the browser"), - browserHeight: z.number().optional().describe("The height of the browser") - }).optional(), - cookies: z.array(z.object({ // Playwright Cookies Type in Zod format - name: z.string(), - value: z.string(), - domain: z.string(), - path: z.string().optional(), - expires: z.number().optional(), - httpOnly: z.boolean().optional(), - secure: z.boolean().optional(), - sameSite: z.enum(['Strict', 'Lax', 'None']).optional() - })).optional().describe("Cookies to inject into the Browserbase context"), - server: z.object({ - port: z.number().optional().describe("The port to listen on for SSE or MCP transport"), - host: z.string().optional().describe("The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces") - }).optional(), - tools: z.object({ - browserbase_take_screenshot: z.object({ - omitBase64: z.boolean().optional().describe("Whether to disable base64-encoded image responses") - }).optional() - }).optional() -}); - -// Default function for Smithery -export default function ({ config }: { config: z.infer }) { - if (!config.browserbaseApiKey) { - throw new Error('browserbaseApiKey is required'); - } - if (!config.browserbaseProjectId) { - throw new Error('browserbaseProjectId is required'); - } - - const server = new McpServer({ - name: 'Browserbase MCP Server', - version: '1.0.6' - }); - - const internalConfig: Config = config as Config; - - // Create the context, passing server instance and config - const context = new Context(server.server, internalConfig); - - const tools: Tool[] = [ - ...common, - ...snapshot, - ...keyboard, - ...getText, - ...navigate, - ...session, - ...contextTools, - ]; - - // Register each tool with the Smithery server - tools.forEach(tool => { - if (tool.schema.inputSchema instanceof z.ZodObject) { - server.tool( - tool.schema.name, - tool.schema.description, - tool.schema.inputSchema.shape, - async (params: z.infer) => { - try { - const result = await context.run(tool, params); - return result; - } catch (error) { - const errorMessage = error instanceof Error ? error.message : String(error); - process.stderr.write(`[Smithery Error] ${new Date().toISOString()} Error running tool ${tool.schema.name}: ${errorMessage}\n`); - throw new Error(`Failed to run tool '${tool.schema.name}': ${errorMessage}`); - } - } - ); - } else { - console.warn( - `Tool "${tool.schema.name}" has an input schema that is not a ZodObject. Schema type: ${tool.schema.inputSchema.constructor.name}` - ); - } - }); - - return server.server; -} \ No newline at end of file diff --git a/browserbase/src/pageSnapshot.ts b/browserbase/src/pageSnapshot.ts deleted file mode 100644 index a32da2e..0000000 --- a/browserbase/src/pageSnapshot.ts +++ /dev/null @@ -1,112 +0,0 @@ -import type { Page, FrameLocator, Locator } from 'playwright-core'; -import yaml from 'yaml'; - -type PageOrFrameLocator = Page | FrameLocator; - -export class PageSnapshot { - private _frameLocators: PageOrFrameLocator[] = []; - private _text!: string; - - constructor() { - } - - static async create(page: Page): Promise { - const snapshot = new PageSnapshot(); - await snapshot._build(page); - return snapshot; - } - - text(): string { - return this._text; - } - - private async _build(page: Page) { - const yamlDocument = await this._snapshotFrame(page); - this._text = [ - `- Page Snapshot`, - '```yaml', - // Generate text directly from the returned document - yamlDocument.toString({ indentSeq: false }).trim(), - '```', - ].join('\n'); - } - - private async _snapshotFrame(frame: Page | FrameLocator) { - const frameIndex = this._frameLocators.push(frame) - 1; - let snapshotString = ''; - try { - snapshotString = await (frame.locator('body') as any).ariaSnapshot({ ref: true, emitGeneric: true }); - } catch (e) { - snapshotString = `error: Could not take snapshot. Error: ${e instanceof Error ? e.message : String(e)}`; - } - - const snapshot = yaml.parseDocument(snapshotString); - - const visit = async (node: any): Promise => { - if (yaml.isPair(node)) { - await Promise.all([ - visit(node.key).then(k => node.key = k), - visit(node.value).then(v => node.value = v) - ]); - } else if (yaml.isSeq(node) || yaml.isMap(node)) { - const items = [...node.items]; - node.items = await Promise.all(items.map(visit)); - } else if (yaml.isScalar(node)) { - if (typeof node.value === 'string') { - const value = node.value; - if (frameIndex > 0) - node.value = value.replace('[ref=', `[ref=f${frameIndex}`); - - if (value.startsWith('iframe ')) { - const ref = value.match(/\[ref=(.*)\]/)?.[1]; - if (ref) { - try { - const childFrameLocator = frame.frameLocator(`aria-ref=${ref}`); - const childSnapshot = await this._snapshotFrame(childFrameLocator); - return snapshot.createPair(node.value, childSnapshot); - } catch (error) { - return snapshot.createPair(node.value, ''); - } - } - } - } - } - return node; - }; - - - if (snapshot.contents) { - await visit(snapshot.contents); - } else { - const emptyMapDoc = yaml.parseDocument('{}'); - snapshot.contents = emptyMapDoc.contents; - } - return snapshot; - } - - refLocator(ref: string): Locator { - let frameIndex = 0; - let frame: PageOrFrameLocator; - let targetRef = ref; - - const match = ref.match(/^f(\d+)(.*)/); - if (match) { - frameIndex = parseInt(match[1], 10); - targetRef = match[2]; - } - - if (this._frameLocators.length === 0) { - throw new Error(`Frame locators not initialized. Cannot find frame for ref '${ref}'.`); - } - - if (frameIndex < 0 || frameIndex >= this._frameLocators.length) { - throw new Error(`Validation Error: Frame index ${frameIndex} derived from ref '${ref}' is out of bounds (found ${this._frameLocators.length} frames).`); - } - frame = this._frameLocators[frameIndex]; - - if (!frame) - throw new Error(`Frame (index ${frameIndex}) could not be determined. Provide ref from the most current snapshot.`); - - return frame.locator(`aria-ref=${targetRef}`); - } -} diff --git a/browserbase/src/program.ts b/browserbase/src/program.ts deleted file mode 100644 index b6dfb8b..0000000 --- a/browserbase/src/program.ts +++ /dev/null @@ -1,69 +0,0 @@ -import { program } from 'commander'; -import * as fs from 'fs'; -import * as path from 'path'; -import { fileURLToPath } from 'url'; - -import createServerFunction from './index.js'; -import { ServerList } from './server.js'; -import { startHttpTransport, startStdioTransport } from './transport.js'; - -import { resolveConfig } from './config.js'; - -let __filename: string; -let __dirname: string; - -try { - // Try ES modules first - __filename = fileURLToPath(import.meta.url); - __dirname = path.dirname(__filename); -} catch { - // Fallback for CommonJS or when import.meta is not available - __filename = (globalThis as any).__filename || process.cwd() + '/dist/program.js'; - __dirname = path.dirname(__filename); -} - -// Load package.json using fs -const packageJSONPath = path.resolve(__dirname, '../package.json'); -const packageJSONBuffer = fs.readFileSync(packageJSONPath); -const packageJSON = JSON.parse(packageJSONBuffer.toString()); - -program - .version('Version ' + packageJSON.version) - .name(packageJSON.name) - .option('--browserbaseApiKey ', 'The Browserbase API Key to use') - .option('--browserbaseProjectId ', 'The Browserbase Project ID to use') - .option('--proxies', 'Use Browserbase proxies.') - .option('--advancedStealth', 'Use advanced stealth mode. Only available to Browserbase Scale Plan users.') - .option('--contextId ', 'Browserbase Context ID to use.') - .option('--persist [boolean]', 'Whether to persist the Browserbase context', true) - .option('--port ', 'Port to listen on for SSE transport.') - .option('--host ', 'Host to bind server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces.') - .option('--cookies [json]', 'JSON array of cookies to inject into the browser. Format: [{"name":"cookie1","value":"val1","domain":"example.com"}, ...]') - .option('--browserWidth ', 'Browser width to use for the browser.') - .option('--browserHeight ', 'Browser height to use for the browser.') - .action(async options => { - const config = await resolveConfig(options); - const serverList = new ServerList(async() => createServerFunction( - { config: config as Required> & typeof config } - )); - setupExitWatchdog(serverList); - - if (options.port) - startHttpTransport(+options.port, options.host, serverList); - else - await startStdioTransport(serverList); - }); - -function setupExitWatchdog(serverList: ServerList) { - const handleExit = async () => { - setTimeout(() => process.exit(0), 15000); - await serverList.closeAll(); - process.exit(0); - }; - - process.stdin.on('close', handleExit); - process.on('SIGINT', handleExit); - process.on('SIGTERM', handleExit); -} - -program.parse(process.argv); \ No newline at end of file diff --git a/browserbase/src/server.ts b/browserbase/src/server.ts deleted file mode 100644 index be2cf13..0000000 --- a/browserbase/src/server.ts +++ /dev/null @@ -1,27 +0,0 @@ -import { Server } from "@modelcontextprotocol/sdk/server/index.js"; - -export class ServerList { - private _servers: Server[] = []; - private _serverFactory: () => Promise; - - constructor(serverFactory: () => Promise) { - this._serverFactory = serverFactory; - } - - async create() { - const server = await this._serverFactory(); - this._servers.push(server); - return server; - } - - async close(server: Server) { - const index = this._servers.indexOf(server); - if (index !== -1) - this._servers.splice(index, 1); - await server.close(); - } - - async closeAll() { - await Promise.all(this._servers.map(server => server.close())); - } -} diff --git a/browserbase/src/sessionManager.ts b/browserbase/src/sessionManager.ts deleted file mode 100644 index 58fe132..0000000 --- a/browserbase/src/sessionManager.ts +++ /dev/null @@ -1,409 +0,0 @@ -import { - chromium, - Browser, - Page, -} from "playwright-core"; -import { Browserbase } from "@browserbasehq/sdk"; -import type { Config } from "./config.js"; -import { SessionCreateParams } from "@browserbasehq/sdk/src/resources/sessions/sessions.js"; -import type { Cookie } from "playwright-core"; - -// Define the type for a session object -export type BrowserSession = { - browser: Browser; - page: Page; - sessionId: string; -}; - -// Global state for managing browser sessions -const browsers = new Map(); - -// Keep track of the default session explicitly -let defaultBrowserSession: BrowserSession | null = null; - -// Define a specific ID for the default session -export const defaultSessionId = "browserbase_session_main"; - -// Keep track of the active session ID. Defaults to the main session. -let activeSessionId: string = defaultSessionId; - -/** - * Sets the active session ID. - * @param id The ID of the session to set as active. - */ -export function setActiveSessionId(id: string): void { - if (browsers.has(id) || id === defaultSessionId) { - activeSessionId = id; - } else { - process.stderr.write( - `[SessionManager] WARN - Set active session failed for non-existent ID: ${id}\n` - ); - } -} - -/** - * Gets the active session ID. - * @returns The active session ID. - */ -export function getActiveSessionId(): string { - return activeSessionId; -} - -/** - * Adds cookies to a browser context - * @param context Playwright browser context - * @param cookies Array of cookies to add - */ -export async function addCookiesToContext(context: any, cookies: Cookie[]): Promise { - if (!cookies || cookies.length === 0) { - return; - } - - try { - process.stderr.write(`[SessionManager] Adding ${cookies.length} cookies to browser context\n`); - await context.addCookies(cookies); - process.stderr.write(`[SessionManager] Successfully added cookies to browser context\n`); - } catch (error) { - process.stderr.write( - `[SessionManager] Error adding cookies to browser context: ${ - error instanceof Error ? error.message : String(error) - }\n` - ); - } -} - -// Function to create a new Browserbase session and connect Playwright -export async function createNewBrowserSession( - newSessionId: string, - config: Config, -): Promise { - if (!config.browserbaseApiKey) { - throw new Error("Browserbase API Key is missing in the configuration."); - } - if (!config.browserbaseProjectId) { - throw new Error("Browserbase Project ID is missing in the configuration."); - } - - const bb = new Browserbase({ - apiKey: config.browserbaseApiKey, - }); - - // Prepare session creation options - const sessionOptions: SessionCreateParams = { - // Use non-null assertion after check - projectId: config.browserbaseProjectId!, - proxies: config.proxies, - browserSettings: { - viewport: { - width: config.viewPort?.browserWidth ?? 1024, - height: config.viewPort?.browserHeight ?? 768, - }, - context: config.context?.contextId ? { - id: config.context?.contextId, - persist: config.context?.persist ?? true, - } : undefined, - advancedStealth: config.advancedStealth ?? undefined, - } - }; - - try { - process.stderr.write( - `[SessionManager] Creating session ${newSessionId}...\n` - ); - const bbSession = await bb.sessions.create(sessionOptions); - process.stderr.write( - `[SessionManager] Browserbase session created: ${bbSession.id}\n` - ); - - const browser = await chromium.connectOverCDP(bbSession.connectUrl); - process.stderr.write( - `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${bbSession.id}\n` - ); - - browser.on("disconnected", () => { - process.stderr.write(`[SessionManager] Disconnected: ${newSessionId}\n`); - browsers.delete(newSessionId); - if (defaultBrowserSession && defaultBrowserSession.browser === browser) { - process.stderr.write( - `[SessionManager] Disconnected (default): ${newSessionId}\n` - ); - defaultBrowserSession = null; - } - if ( - activeSessionId === newSessionId && - newSessionId !== defaultSessionId - ) { - process.stderr.write( - `[SessionManager] WARN - Active session disconnected, resetting to default: ${newSessionId}\n` - ); - setActiveSessionId(defaultSessionId); - } - }); - - let context = browser.contexts()[0]; - if (!context) { - context = await browser.newContext(); - } - - // Add cookies to the context if they are provided in the config - if (config.cookies && Array.isArray(config.cookies) && config.cookies.length > 0) { - await addCookiesToContext(context, config.cookies); - } - - let page = context.pages()[0]; - if (!page) { - page = await context.newPage(); - } - - const sessionObj: BrowserSession = { - browser, - page, - sessionId: bbSession.id, - }; - - browsers.set(newSessionId, sessionObj); - - if (newSessionId === defaultSessionId) { - defaultBrowserSession = sessionObj; - } - - setActiveSessionId(newSessionId); - process.stderr.write( - `[SessionManager] Session created and active: ${newSessionId}\n` - ); - - return sessionObj; - } catch (creationError) { - const errorMessage = - creationError instanceof Error - ? creationError.message - : String(creationError); - process.stderr.write( - `[SessionManager] Creating session ${newSessionId} failed: ${ - creationError instanceof Error - ? creationError.message - : String(creationError) - }` - ); - throw new Error( - `Failed to create/connect session ${newSessionId}: ${errorMessage}` - ); - } -} - -async function closeBrowserGracefully( - session: BrowserSession | undefined | null, - sessionIdToLog: string -): Promise { - if (session?.browser?.isConnected()) { - process.stderr.write( - `[SessionManager] Closing browser for session: ${sessionIdToLog}\n` - ); - try { - await session.browser.close(); - } catch (closeError) { - process.stderr.write( - `[SessionManager] WARN - Error closing browser for session ${sessionIdToLog}: ${ - closeError instanceof Error ? closeError.message : String(closeError) - }\n` - ); - } - } -} - -// Internal function to ensure default session -export async function ensureDefaultSessionInternal( - config: Config -): Promise { - const sessionId = defaultSessionId; - let needsRecreation = false; - - if (!defaultBrowserSession) { - needsRecreation = true; - process.stderr.write( - `[SessionManager] Default session ${sessionId} not found, creating.\n` - ); - } else if ( - !defaultBrowserSession.browser.isConnected() || - defaultBrowserSession.page.isClosed() - ) { - needsRecreation = true; - process.stderr.write( - `[SessionManager] Default session ${sessionId} is stale, recreating.\n` - ); - await closeBrowserGracefully(defaultBrowserSession, sessionId); - defaultBrowserSession = null; - browsers.delete(sessionId); - } - - if (needsRecreation) { - try { - defaultBrowserSession = await createNewBrowserSession(sessionId, config); - return defaultBrowserSession; - } catch (error) { - // Error during initial creation or recreation - process.stderr.write( - `[SessionManager] Initial/Recreation attempt for default session ${sessionId} failed. Error: ${ - error instanceof Error ? error.message : String(error) - }\n` - ); - // Attempt one more time after a failure - process.stderr.write( - `[SessionManager] Retrying creation of default session ${sessionId} after error...\n` - ); - try { - defaultBrowserSession = await createNewBrowserSession(sessionId, config); - return defaultBrowserSession; - } catch (retryError) { - const finalErrorMessage = - retryError instanceof Error - ? retryError.message - : String(retryError); - process.stderr.write( - `[SessionManager] Failed to recreate default session ${sessionId} after retry: ${finalErrorMessage}\n` - ); - throw new Error( - `Failed to ensure default session ${sessionId} after initial error and retry: ${finalErrorMessage}` - ); - } - } - } - - // If we reached here, the existing default session is considered okay. - setActiveSessionId(sessionId); // Ensure default is marked active - return defaultBrowserSession!; // Non-null assertion: logic ensures it's not null here -} - -// Get a specific session by ID -export async function getSession( - sessionId: string, - config: Config -): Promise { - if (sessionId === defaultSessionId) { - try { - return await ensureDefaultSessionInternal(config); - } catch (error) { - // ensureDefaultSessionInternal already logs extensively - process.stderr.write( - `[SessionManager] Failed to get default session due to error in ensureDefaultSessionInternal for ${sessionId}. See previous messages for details.\n` - ); - return null; // Or rethrow if getSession failing for default is critical - } - } - - // For non-default sessions - process.stderr.write(`[SessionManager] Getting session: ${sessionId}\n`); - let sessionObj = browsers.get(sessionId); - - if (!sessionObj) { - process.stderr.write( - `[SessionManager] WARN - Session not found in map: ${sessionId}\n` - ); - return null; - } - - // Validate the found session - if (!sessionObj.browser.isConnected() || sessionObj.page.isClosed()) { - process.stderr.write( - `[SessionManager] WARN - Found session ${sessionId} is stale, removing.\n` - ); - await closeBrowserGracefully(sessionObj, sessionId); - browsers.delete(sessionId); - if (activeSessionId === sessionId) { - process.stderr.write( - `[SessionManager] WARN - Invalidated active session ${sessionId}, resetting to default.\n` - ); - setActiveSessionId(defaultSessionId); - } - return null; - } - - // Session appears valid, make it active - setActiveSessionId(sessionId); - process.stderr.write(`[SessionManager] Using valid session: ${sessionId}\n`); - return sessionObj; -} - -/** - * Get a session by ID without creating new sessions. - * This is a read-only operation that never triggers session creation. - * Used for operations like closing sessions where we don't want side effects. - * @param sessionId The session ID to retrieve - * @returns The session if it exists and is valid, null otherwise - */ -export function getSessionReadOnly(sessionId: string): BrowserSession | null { - // Check if it's the default session - if (sessionId === defaultSessionId && defaultBrowserSession) { - // Only return if it's actually connected and valid - if (defaultBrowserSession.browser.isConnected() && !defaultBrowserSession.page.isClosed()) { - return defaultBrowserSession; - } - return null; - } - - // For non-default sessions, check the browsers map - const sessionObj = browsers.get(sessionId); - if (!sessionObj) { - return null; - } - - // Validate the session is still active - if (!sessionObj.browser.isConnected() || sessionObj.page.isClosed()) { - return null; - } - - return sessionObj; -} - -/** - * Clean up a session by removing it from tracking. - * This is called after a browser is closed to ensure proper cleanup. - * @param sessionId The session ID to clean up - */ -export function cleanupSession(sessionId: string): void { - process.stderr.write( - `[SessionManager] Cleaning up session: ${sessionId}\n` - ); - - // Remove from browsers map - browsers.delete(sessionId); - - // Clear default session reference if this was the default - if (sessionId === defaultSessionId && defaultBrowserSession) { - defaultBrowserSession = null; - } - - // Reset active session to default if this was the active one - if (activeSessionId === sessionId) { - process.stderr.write( - `[SessionManager] Cleaned up active session ${sessionId}, resetting to default.\n` - ); - setActiveSessionId(defaultSessionId); - } -} - -// Function to close all managed browser sessions gracefully -export async function closeAllSessions(): Promise { - process.stderr.write(`[SessionManager] Closing all sessions...\n`); - const closePromises: Promise[] = []; - for (const [id, session] of browsers.entries()) { - process.stderr.write(`[SessionManager] Closing session: ${id}\n`); - closePromises.push( - // Use the helper for consistent logging/error handling - closeBrowserGracefully(session, id) - ); - } - try { - await Promise.all(closePromises); - } catch(e) { - // Individual errors are caught and logged by closeBrowserGracefully - process.stderr.write( - `[SessionManager] WARN - Some errors occurred during batch session closing. See individual messages.\n` - ); - } - - browsers.clear(); - defaultBrowserSession = null; - setActiveSessionId(defaultSessionId); // Reset active session to default - process.stderr.write(`[SessionManager] All sessions closed and cleared.\n`); -} diff --git a/browserbase/src/tools/common.ts b/browserbase/src/tools/common.ts deleted file mode 100644 index acc06a1..0000000 --- a/browserbase/src/tools/common.ts +++ /dev/null @@ -1,111 +0,0 @@ -export {}; // Ensure file is treated as a module - -import { z } from 'zod'; -import type { Tool, ToolSchema, ToolResult } from "./tool.js"; -import type { Context } from '../context.js'; -import type { ToolActionResult } from '../context.js'; - -// --- Tool: Wait --- -const WaitInputSchema = z.object({ - time: z.number().describe("Time in seconds") -}); -type WaitInput = z.infer; - -const waitSchema: ToolSchema = { - name: "browserbase_wait", - description: "Wait for a specified time in seconds", - inputSchema: WaitInputSchema, -}; - -// Handle function for Wait -async function handleWait(context: Context, params: WaitInput): Promise { // Uses Context, returns ToolResult - const action = async (): Promise => { - await new Promise(resolve => setTimeout(resolve, params.time * 1000)); - return { content: [{ type: 'text', text: `Waited for ${params.time} seconds.` }] }; - }; - return { action, code: [], captureSnapshot: false, waitForNetwork: false }; -} - -// Define tool using handle -const waitTool: Tool = { - capability: 'core', - schema: waitSchema, - handle: handleWait, -}; - - -// --- Tool: Close --- -const CloseInputSchema = z.object({ - random_string: z.string().optional().describe("Dummy parameter") -}); -type CloseInput = z.infer; - -const closeSchema: ToolSchema = { - name: "browserbase_close", - description: "Close the current page...", - inputSchema: CloseInputSchema, -}; - -// Handle function for Close -async function handleClose(context: Context, params: CloseInput): Promise { - const action = async (): Promise => { - const page = await context.getActivePage(); - if (page && !page.isClosed()) { - await page.close(); - return { content: [{ type: 'text', text: `Page closed.` }] }; - } else { - return { content: [{ type: 'text', text: `No active page to close.` }] }; - } - }; - return { action, code: [], captureSnapshot: false, waitForNetwork: false }; -} - -// Define tool using handle -const closeTool: Tool = { - capability: 'core', // Add capability - schema: closeSchema, - handle: handleClose, -}; - - -// --- Tool: Resize --- -const ResizeInputSchema = z.object({ - width: z.number(), - height: z.number() -}); -type ResizeInput = z.infer; - -const resizeSchema: ToolSchema = { - name: "browserbase_resize", - description: "Resize window...", - inputSchema: ResizeInputSchema, -}; - -// Handle function for Resize -async function handleResize(context: Context, params: ResizeInput): Promise { - const action = async (): Promise => { - const page = await context.getActivePage(); - if (page && !page.isClosed()) { - await page.setViewportSize({ width: params.width, height: params.height }); - return { content: [{ type: 'text', text: `Resized page to ${params.width}x${params.height}.` }] }; - } else { - return { content: [{ type: 'text', text: `No active page to resize.` }] }; - } - }; - return { action, code: [], captureSnapshot: true, waitForNetwork: false }; -} - -// Define tool using handle -const resizeTool: Tool = { - capability: 'core', // Add capability - schema: resizeSchema, - handle: handleResize, -}; - - -// Export array of tools directly -export default [ - waitTool, - closeTool, - resizeTool, -]; \ No newline at end of file diff --git a/browserbase/src/tools/context.ts b/browserbase/src/tools/context.ts deleted file mode 100644 index 95b3422..0000000 --- a/browserbase/src/tools/context.ts +++ /dev/null @@ -1,198 +0,0 @@ -import { z } from "zod"; -import type { Tool, ToolSchema, ToolResult } from "./tool.js"; -import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; -import { Browserbase } from "@browserbasehq/sdk"; - -// Store contexts in memory -const contexts = new Map(); - -// --- Tool: Create Context --- -const CreateContextInputSchema = z.object({ - name: z - .string() - .optional() - .describe("Optional friendly name to reference this context later (otherwise, you'll need to use the returned ID)"), -}); -type CreateContextInput = z.infer; - -const createContextSchema: ToolSchema = { - name: "browserbase_context_create", - description: "Create a new Browserbase context for reusing cookies, authentication, and cached data across browser sessions", - inputSchema: CreateContextInputSchema, -}; - -async function handleCreateContext( - context: Context, - params: CreateContextInput -): Promise { - try { - const config = context.config; - - if (!config.browserbaseApiKey || !config.browserbaseProjectId) { - throw new Error("Browserbase API Key or Project ID is missing in the configuration"); - } - - const bb = new Browserbase({ - apiKey: config.browserbaseApiKey, - }); - - console.error("Creating new Browserbase context"); - const bbContext = await bb.contexts.create({ - projectId: config.browserbaseProjectId, - }); - - console.error(`Successfully created context: ${bbContext.id}`); - - // Store context ID with optional name if provided - const contextName = params.name || bbContext.id; - contexts.set(contextName, bbContext.id); - - const result: ToolActionResult = { - content: [ - { - type: "text", - text: `Created new Browserbase context with ID: ${bbContext.id}${params.name ? ` and name: ${params.name}` : ''}`, - }, - ], - }; - - return { - resultOverride: result, - action: async () => { - console.error("Create Context action"); - return result; - }, - code: [], - captureSnapshot: false, - waitForNetwork: false, - }; - } catch (error: any) { - console.error(`CreateContext handle failed: ${error.message || error}`); - throw new Error(`Failed to create Browserbase context: ${error.message || error}`); - } -} - -// --- Tool: Delete Context --- -const DeleteContextInputSchema = z.object({ - contextId: z - .string() - .optional() - .describe("The context ID to delete (required if name not provided)"), - name: z - .string() - .optional() - .describe("The friendly name of the context to delete (required if contextId not provided)"), -}); -type DeleteContextInput = z.infer; - -const deleteContextSchema: ToolSchema = { - name: "browserbase_context_delete", - description: "Delete a Browserbase context when you no longer need it", - inputSchema: DeleteContextInputSchema, -}; - -async function handleDeleteContext( - context: Context, - params: DeleteContextInput -): Promise { - try { - const config = context.config; - - if (!config.browserbaseApiKey) { - throw new Error("Browserbase API Key is missing in the configuration"); - } - - if (!params.contextId && !params.name) { - throw new Error("Missing required argument: either contextId or name must be provided"); - } - - // Resolve context ID either directly or by name - let contextId = params.contextId; - if (!contextId && params.name) { - contextId = contexts.get(params.name); - if (!contextId) { - throw new Error(`Context with name "${params.name}" not found`); - } - } - - console.error(`Deleting Browserbase context: ${contextId}`); - - // Delete using Browserbase API - const response = await fetch(`https://api.browserbase.com/v1/contexts/${contextId}`, { - method: 'DELETE', - headers: { - 'X-BB-API-Key': config.browserbaseApiKey, - }, - }); - - if (response.status !== 204) { - const errorText = await response.text(); - throw new Error(`Failed to delete context with status ${response.status}: ${errorText}`); - } - - // Remove from local store - if (params.name) { - contexts.delete(params.name); - } - - // Delete by ID too (in case it was stored multiple ways) - for (const [name, id] of contexts.entries()) { - if (id === contextId) { - contexts.delete(name); - } - } - - console.error(`Successfully deleted context: ${contextId}`); - - const result: ToolActionResult = { - content: [ - { - type: "text", - text: `Deleted Browserbase context with ID: ${contextId}`, - }, - ], - }; - - return { - resultOverride: result, - action: async () => { - console.error("Delete Context action"); - return result; - }, - code: [], - captureSnapshot: false, - waitForNetwork: false, - }; - } catch (error: any) { - console.error(`DeleteContext handle failed: ${error.message || error}`); - throw new Error(`Failed to delete Browserbase context: ${error.message || error}`); - } -} - -// Helper function to get a context ID from name or direct ID (exported for use by session.ts) -export function getContextId(nameOrId: string): string | undefined { - // First check if it's a direct context ID - if (nameOrId.length == 32) { // 32 char uuid - return nameOrId; - } - - // Otherwise, look it up by name - return contexts.get(nameOrId); -} - -// Define tools -const createContextTool: Tool = { - capability: "core", - schema: createContextSchema, - handle: handleCreateContext, -}; - -const deleteContextTool: Tool = { - capability: "core", - schema: deleteContextSchema, - handle: handleDeleteContext, -}; - -// Export as an array of tools -export default [createContextTool, deleteContextTool]; \ No newline at end of file diff --git a/browserbase/src/tools/getText.ts b/browserbase/src/tools/getText.ts deleted file mode 100644 index c1f6ec6..0000000 --- a/browserbase/src/tools/getText.ts +++ /dev/null @@ -1,54 +0,0 @@ -import { z } from 'zod'; -import type { Tool, ToolSchema, ToolResult } from "./tool.js"; -import type { Context } from '../context.js'; -import type { ToolActionResult } from '../context.js'; - -// --- Tool: Get Text --- -const GetTextInputSchema = z.object({ - selector: z.string().optional().describe("Optional CSS selector to get text from. If omitted, gets text from the whole body."), -}); -type GetTextInput = z.infer; - -const getTextSchema: ToolSchema = { - name: "browserbase_get_text", - description: "Extract text content from the page or a specific element.", - inputSchema: GetTextInputSchema, -}; - -// Handle function for GetText -async function handleGetText(context: Context, params: GetTextInput): Promise { - const action = async (): Promise => { - const page = await context.getActivePage(); - if (!page) { - throw new Error('No active page found for getText'); - } - try { - let textContent: string | null; - if (params.selector) { - textContent = await page.textContent(params.selector, { timeout: 10000 }); - } else { - textContent = await page.textContent('body', { timeout: 10000 }); - } - return { content: [{ type: 'text', text: textContent ?? "" }] }; - } catch (error) { - console.error(`GetText action failed: ${error}`); - throw error; // Rethrow to be caught by Context.run's try/catch around handle/action - } - }; - - return { - action, - code: [], - captureSnapshot: false, - waitForNetwork: false, - }; -} - -// Define tool using handle -const getTextTool: Tool = { - capability: 'core', // Add capability - schema: getTextSchema, - handle: handleGetText, -}; - -export default [getTextTool]; \ No newline at end of file diff --git a/browserbase/src/tools/hover.ts b/browserbase/src/tools/hover.ts deleted file mode 100644 index a01265c..0000000 --- a/browserbase/src/tools/hover.ts +++ /dev/null @@ -1,8 +0,0 @@ -import type { Tool } from "./tool.js"; - -// Placeholder function for hover tool, accepting the flag -export function hover(captureSnapshot: boolean): Tool[] { - // TODO: Implement hoverTool and potentially use flag - return []; -} -export default hover; \ No newline at end of file diff --git a/browserbase/src/tools/keyboard.ts b/browserbase/src/tools/keyboard.ts deleted file mode 100644 index f989426..0000000 --- a/browserbase/src/tools/keyboard.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { z } from 'zod'; -import { defineTool, type ToolFactory } from './tool.js'; - -const pressKey: ToolFactory = captureSnapshot => defineTool({ - capability: 'core', - - schema: { - name: 'browserbase_press_key', - description: 'Press a key on the keyboard', - inputSchema: z.object({ - key: z.string().describe('Name of the key to press or a character to generate, such as `ArrowLeft` or `a`'), - }), - }, - - handle: async (context, params) => { - const page = await context.getActivePage(); - if (!page) { - throw new Error('No active page found for pressKey'); - } - - const code = [ - `// Press ${params.key}`, - `await page.keyboard.press('${params.key.replace(/'/g, "\\'")}');`, - ]; - - const action = () => page.keyboard.press(params.key); // Changed from tab.page to page - - return { - code, - action, - captureSnapshot, - waitForNetwork: true - }; - }, -}); - -const captureSnapshotValue = true; - -export default [ - pressKey(captureSnapshotValue), -]; \ No newline at end of file diff --git a/browserbase/src/tools/navigate.ts b/browserbase/src/tools/navigate.ts deleted file mode 100644 index f925c51..0000000 --- a/browserbase/src/tools/navigate.ts +++ /dev/null @@ -1,106 +0,0 @@ -import { z } from 'zod'; -import { defineTool, type ToolFactory } from './tool.js'; -import type { ToolActionResult } from '../context.js'; - -const navigate: ToolFactory = captureSnapshot => defineTool({ - capability: 'core', - - schema: { - name: 'browserbase_navigate', - description: 'Navigate to a URL', - inputSchema: z.object({ - url: z.string().describe('The URL to navigate to'), - }), - }, - - handle: async (context, params) => { - const page = await context.getActivePage(); - if (!page) { - throw new Error('No active page found for navigate'); - } - const action = async (): Promise => { - await page.goto(params.url); - return { content: [{ type: 'text', text: `Navigated to ${params.url}` }] }; - }; - - const code = [ - `// Navigate to ${params.url}`, - `await page.goto('${params.url}');`, - ]; - - return { - action, - code, - captureSnapshot, - waitForNetwork: false, - }; - }, -}); - -const goBack: ToolFactory = captureSnapshot => defineTool({ - capability: 'history', - schema: { - name: 'browserbase_navigate_back', - description: 'Go back to the previous page', - inputSchema: z.object({}), - }, - - handle: async context => { - const page = await context.getActivePage(); - if (!page) { - throw new Error('No active page found for goBack'); - } - const action = async (): Promise => { - await page.goBack(); - return { content: [{ type: 'text', text: 'Navigated back' }] }; - }; - const code = [ - `// Navigate back`, - `await page.goBack();`, - ]; - - return { - action, - code, - captureSnapshot, - waitForNetwork: true, - }; - }, -}); - -const goForward: ToolFactory = captureSnapshot => defineTool({ - capability: 'history', - schema: { - name: 'browserbase_navigate_forward', - description: 'Go forward to the next page', - inputSchema: z.object({}), - }, - handle: async context => { - const page = await context.getActivePage(); - if (!page) { - throw new Error('No active page found for goForward'); - } - const action = async (): Promise => { - await page.goForward(); - return { content: [{ type: 'text', text: 'Navigated forward' }] }; - }; - const code = [ - `// Navigate forward`, - `await page.goForward();`, - ]; - return { - action, - code, - captureSnapshot, - waitForNetwork: true, - }; - }, -}); - -const captureSnapshotValue = true; - -export default [ - navigate(captureSnapshotValue), - goBack(captureSnapshotValue), - goForward(captureSnapshotValue), -]; \ No newline at end of file diff --git a/browserbase/src/tools/selectOption.ts b/browserbase/src/tools/selectOption.ts deleted file mode 100644 index 66ff6d9..0000000 --- a/browserbase/src/tools/selectOption.ts +++ /dev/null @@ -1,8 +0,0 @@ -import type { Tool } from "./tool.js"; - -// Placeholder function for select option tool, accepting the flag -export function selectOption(captureSnapshot: boolean): Tool[] { - // TODO: Implement selectOptionTool and potentially use flag - return []; -} -export default selectOption; \ No newline at end of file diff --git a/browserbase/src/tools/session.ts b/browserbase/src/tools/session.ts deleted file mode 100644 index 7565822..0000000 --- a/browserbase/src/tools/session.ts +++ /dev/null @@ -1,239 +0,0 @@ -import { z } from "zod"; -import type { Tool, ToolSchema, ToolResult } from "./tool.js"; -import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; - -// Import SessionManager functions -import { - createNewBrowserSession, - defaultSessionId, - ensureDefaultSessionInternal, - cleanupSession, - type BrowserSession, -} from "../sessionManager.js"; - -// --- Tool: Create Session --- -const CreateSessionInputSchema = z.object({ - // Keep sessionId optional, but clarify its role - sessionId: z - .string() - .optional() - .describe( - "Optional session ID to use/reuse. If not provided or invalid, a new session is created." - ), -}); -type CreateSessionInput = z.infer; - -const createSessionSchema: ToolSchema = { - name: "browserbase_session_create", - description: - "Create or reuse a cloud browser session using Browserbase. Updates the active session.", - inputSchema: CreateSessionInputSchema, -}; - - -// Handle function for CreateSession using SessionManager -async function handleCreateSession( - context: Context, - params: CreateSessionInput -): Promise { - const action = async (): Promise => { - try { - const config = context.config; // Get config from context - let targetSessionId: string; - - if (params.sessionId) { - const projectId = config.browserbaseProjectId || ''; - targetSessionId = `${params.sessionId}_${projectId}`; - process.stderr.write( - `[tool.createSession] Attempting to create/assign session with specified ID: ${targetSessionId}` - ); - } else { - targetSessionId = defaultSessionId; - } - - let session: BrowserSession; - if (targetSessionId === defaultSessionId) { - session = await ensureDefaultSessionInternal(config); - } else { - session = await createNewBrowserSession(targetSessionId, config); - } - - if (!session || !session.browser || !session.page || !session.sessionId) { - throw new Error( - `SessionManager failed to return a valid session object with actualSessionId for ID: ${targetSessionId}` - ); - } - - context.currentSessionId = targetSessionId; - process.stderr.write( - `[tool.connected] Successfully connected to Browserbase session. Internal ID: ${targetSessionId}, Actual ID: ${session.sessionId}` - ); - - process.stderr.write(`[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.sessionId}`); - - return { - content: [ - { - type: "text", - text: `https://www.browserbase.com/sessions/${session.sessionId}`, - }, - ], - }; - } catch (error: any) { - process.stderr.write( - `[tool.createSession] Action failed: ${ - error.message || String(error) - }` - ); - // Re-throw to be caught by Context.run's error handling for actions - throw new Error( - `Failed to create Browserbase session: ${ - error.message || String(error) - }` - ); - } - }; - - // Return the ToolResult structure expected by Context.run - return { - action: action, - captureSnapshot: false, - code: [], - waitForNetwork: false, - }; -} - -// Define tool using handle -const createSessionTool: Tool = { - capability: "core", // Add capability - schema: createSessionSchema, - handle: handleCreateSession, -}; - -// --- Tool: Close Session --- -const CloseSessionInputSchema = z.object({ - random_string: z - .string() - .optional() - .describe("Dummy parameter to ensure consistent tool call format."), -}); -type CloseSessionInput = z.infer; - -const closeSessionSchema: ToolSchema = { - name: "browserbase_session_close", - description: - "Closes the current Browserbase session by disconnecting the Playwright browser. This will terminate the recording for the session.", - inputSchema: CloseSessionInputSchema, -}; - -async function handleCloseSession( - context: Context, - _params: CloseSessionInput -): Promise { - const code = [`// Attempting to close the current Browserbase session.`]; - - const action = async (): Promise => { - // Store the current session ID before it's potentially changed. - // This allows us to reference the original session ID later if needed. - const previousSessionId = context.currentSessionId; // Capture the ID before any changes - let browser: BrowserSession["browser"] | null = null; - let browserClosedSuccessfully = false; - let browserCloseErrorMessage = ""; - - // Step 1: Attempt to get the active browser instance WITHOUT creating a new one - try { - // Use read-only version to avoid creating new sessions - browser = context.getActiveBrowserReadOnly(); - } catch (error: any) { - process.stderr.write( - `[tool.closeSession] Error retrieving active browser (session ID was ${previousSessionId || 'default/unknown'}): ${error.message || String(error)}` - ); - // If we can't even get the browser, we can't close it. - // We will still proceed to reset context. - } - - // Step 2: If a browser instance was retrieved, attempt to close it - if (browser) { - try { - process.stderr.write( - `[tool.closeSession] Attempting to close browser for session: ${previousSessionId || 'default (actual might differ)'}` - ); - await browser.close(); - browserClosedSuccessfully = true; - process.stderr.write( - `[tool.closeSession] Browser connection for session (was ${previousSessionId}) closed.` - ); - - // Clean up the session from tracking - cleanupSession(previousSessionId); - - process.stderr.write( - `[tool.closeSession] View session replay at https://www.browserbase.com/sessions/${previousSessionId}` - ); - - } catch (error: any) { - browserCloseErrorMessage = error.message || String(error); - process.stderr.write( - `[tool.closeSession] Error during browser.close() for session (was ${previousSessionId}): ${browserCloseErrorMessage}` - ); - } - } else { - process.stderr.write( - `[tool.closeSession] No active browser instance found to close. (Session ID in context was: ${previousSessionId || 'default/unknown'}).` - ); - } - - // Step 3: Always reset the context's current session ID to default - // and clear snapshot if the previous session was a specific one. - const oldContextSessionId = context.currentSessionId; // This should effectively be 'previousSessionId' - context.currentSessionId = defaultSessionId; - if (oldContextSessionId && oldContextSessionId !== defaultSessionId) { - context.clearLatestSnapshot(); - process.stderr.write( - `[tool.closeSession] Snapshot cleared for previous session: ${oldContextSessionId}.` - ); - } - process.stderr.write( - `[tool.closeSession] Session context reset to default. Previous context session ID was ${oldContextSessionId || 'default/unknown'}.` - ); - - // Step 4: Determine the result message - if (browser && !browserClosedSuccessfully) { // An attempt was made to close, but it failed - throw new Error( - `Failed to close the Browserbase browser (session ID in context was ${previousSessionId || 'default/unknown'}). Error: ${browserCloseErrorMessage}. Session context has been reset to default.` - ); - } - - if (browserClosedSuccessfully) { // Browser was present and closed - let successMessage = `Browserbase session (associated with context ID ${previousSessionId || 'default'}) closed successfully. Context reset to default.`; - if (previousSessionId && previousSessionId !== defaultSessionId) { - successMessage += ` If this was a uniquely named session (${previousSessionId}), view replay (if available) at https://browserbase.com/sessions`; - } - return { content: [{ type: "text", text: successMessage }] }; - } - - // No browser was found, or browser was null initially. - let infoMessage = "No active browser instance was found to close. Session context has been reset to default."; - if (previousSessionId && previousSessionId !== defaultSessionId) { - // This means a specific session was in context, but no browser for it. - infoMessage = `No active browser found for session ID '${previousSessionId}' in context. The context has been reset to default.`; - } - return { content: [{ type: "text", text: infoMessage }] }; - }; - - return { - action: action, - code: code, - captureSnapshot: false, - waitForNetwork: false, - }; -} - -const closeSessionTool: Tool = { - capability: "core", - schema: closeSessionSchema, - handle: handleCloseSession, -}; - -export default [createSessionTool, closeSessionTool]; \ No newline at end of file diff --git a/browserbase/src/tools/snapshot.ts b/browserbase/src/tools/snapshot.ts deleted file mode 100644 index 5ec80e5..0000000 --- a/browserbase/src/tools/snapshot.ts +++ /dev/null @@ -1,499 +0,0 @@ -import { z } from "zod"; -import type { - TextContent, - ImageContent, -} from "@modelcontextprotocol/sdk/types.js"; -import type { Locator, PageScreenshotOptions } from "playwright-core"; - -import { defineTool, type ToolResult, } from "./tool.js"; -import type { Context, ToolActionResult } from "../context.js"; -import { PageSnapshot } from "../pageSnapshot.js"; -import { outputFile } from "../config.js"; - -// --- Tool: Snapshot --- -const SnapshotInputSchema = z.object({}); -type SnapshotInput = z.infer; - -const snapshot = defineTool({ - capability: "core", - schema: { - name: "browserbase_snapshot", - description: - "Capture a new accessibility snapshot of the current page state. Use this if the page has changed to ensure subsequent actions use an up-to-date page representation.", - inputSchema: SnapshotInputSchema, - }, - - handle: async ( - context: Context, - params: SnapshotInput - ): Promise => { - const action = async (): Promise => { - const content: (TextContent | ImageContent)[] = [ - { type: "text", text: "Accessibility snapshot captured." }, - ]; - return { content }; - }; - - return { - action, - code: [`// Request accessibility snapshot`], - captureSnapshot: true, - waitForNetwork: false, - resultOverride: { - content: [{ type: "text", text: "Accessibility snapshot initiated." }], - }, - }; - }, -}); - -// --- Element Schema & Types --- -const elementSchema = z.object({ - element: z.string().describe("Human-readable element description"), - ref: z - .string() - .describe("Exact target element reference from the page snapshot"), -}); -type ElementInput = z.infer; - -// --- Tool: Click (Adapted Handle, Example Action) --- -const click = defineTool({ - capability: "core", - schema: { - name: "browserbase_click", - description: "Perform click on a web page using ref", - inputSchema: elementSchema, - }, - handle: async ( - context: Context, - params: ElementInput - ): Promise => { - // Get locator directly from snapshot - const snapshot = context.snapshotOrDie(); - const locator = snapshot.refLocator(params.ref); - - const code = [ - `// Click ${params.element}`, - // Use generateLocator for code string - `// await page.${await generateLocator(locator)}.click();`, - ]; - - const action = async (): Promise => { - try { - // Use the locator directly for the action - await locator.click({ force: true, timeout: 30000 }); // Increased timeout like logs - } catch (actionError) { - const errorMessage = - actionError instanceof Error - ? actionError.message - : String(actionError); - throw new Error( - `Failed to click element '${params.element}'. Error: ${errorMessage}` - ); - } - return { - content: [{ type: "text", text: `Clicked ${params.element}` }], - }; - }; - - return { - code, - action, - captureSnapshot: true, - waitForNetwork: true, - }; - }, -}); - -// --- Tool: Drag (Adapted Handle, Example Action) --- -const dragInputSchema = z.object({ - startElement: z.string().describe("Source element description"), - startRef: z - .string() - .describe("Exact source element reference from the page snapshot"), - endElement: z.string().describe("Target element description"), - endRef: z - .string() - .describe("Exact target element reference from the page snapshot"), -}); -type DragInput = z.infer; - -const drag = defineTool({ - capability: "core", - schema: { - name: "browserbase_drag", - description: "Perform drag and drop between two elements using ref.", - inputSchema: dragInputSchema, - }, - handle: async (context: Context, params: DragInput): Promise => { - // Get locators directly from snapshot - const snapshot = context.snapshotOrDie(); - const startLocator = snapshot.refLocator(params.startRef); - const endLocator = snapshot.refLocator(params.endRef); - - const code = [ - `// Drag ${params.startElement} to ${params.endElement}`, - // Use generateLocator for code string - `// await page.${await generateLocator( - startLocator - )}.dragTo(page.${await generateLocator(endLocator)});`, - ]; - - const action = async (): Promise => { - try { - // Use locators directly for the action - await startLocator.dragTo(endLocator, { timeout: 5000 }); - } catch (dragError) { - const errorMsg = - dragError instanceof Error ? dragError.message : String(dragError); - throw new Error( - `Failed to drag '${params.startElement}' to '${params.endElement}'. Error: ${errorMsg}` - ); - } - return { - content: [ - { - type: "text", - text: `Dragged ${params.startElement} to ${params.endElement}`, - }, - ], - }; - }; - - return { action, code, captureSnapshot: true, waitForNetwork: true }; - }, -}); - -// --- Tool: Hover (Adapted Handle, Example Action) --- -const hover = defineTool({ - capability: "core", - schema: { - name: "browserbase_hover", - description: "Hover over element on page using ref.", - inputSchema: elementSchema, - }, - handle: async ( - context: Context, - params: ElementInput - ): Promise => { - // Get locator directly from snapshot - const snapshot = context.snapshotOrDie(); - const locator = snapshot.refLocator(params.ref); - - const code = [ - `// Hover over ${params.element}`, - // Use generateLocator for code string - `// await page.${await generateLocator(locator)}.hover();`, - ]; - - const action = async (): Promise => { - try { - // Use locator directly for the action - await locator.hover({ timeout: 5000 }); - } catch (hoverError) { - const errorMsg = - hoverError instanceof Error ? hoverError.message : String(hoverError); - throw new Error( - `Failed to hover over element '${params.element}'. Error: ${errorMsg}` - ); - } - return { - content: [{ type: "text", text: `Hovered over: ${params.element}` }], - }; - }; - - return { action, code, captureSnapshot: true, waitForNetwork: true }; - }, -}); - -// --- Tool: Type (Adapted Handle, Example Action) --- -const typeSchema = elementSchema.extend({ - text: z.string().describe("Text to type into the element"), - submit: z - .boolean() - .optional() - .describe("Whether to submit entered text (press Enter after)"), - slowly: z - .boolean() - .optional() - .default(true) - .describe("Whether to type one character at a time."), -}); -type TypeInput = z.infer; - -const type = defineTool({ - capability: "core", - schema: { - name: "browserbase_type", - description: "Type text into editable element using ref.", - inputSchema: typeSchema, - }, - handle: async (context: Context, params: TypeInput): Promise => { - // Get locator directly from snapshot - const snapshot = context.snapshotOrDie(); - const locator = snapshot.refLocator(params.ref); - - const code: string[] = []; - const steps: (() => Promise)[] = []; - - if (params.slowly) { - code.push( - `// Press "${params.text}" sequentially into "${params.element}"` - ); - code.push( - `// await page.${await generateLocator( - locator - )}.pressSequentially('${params.text.replace(/'/g, "\\'")}');` - ); - steps.push(() => - locator.pressSequentially(params.text, { delay: 50 }) - ); - } else { - code.push(`// Fill "${params.text}" into "${params.element}"`); - code.push( - `// await page.${await generateLocator( - locator - )}.fill('${params.text.replace(/'/g, "\\'")}');` - ); - steps.push(async () => { - await locator.waitFor({ state: "visible"}); - if (!(await locator.isEditable())) { - throw new Error( - `Element '${params.element}' was visible but not editable.` - ); - } - await locator.fill("", { force: true, timeout: 5000 }); // Force empty fill first - await locator.fill(params.text, { force: true, timeout: 5000 }); // Force fill with text - }); - } - - if (params.submit) { - code.push(`// Submit text`); - code.push( - `// await page.${await generateLocator(locator)}.press('Enter');` - ); - steps.push(() => locator.press("Enter", { timeout: 5000 })); - } - - const action = async (): Promise => { - try { - // Execute the steps sequentially - await steps.reduce((acc, step) => acc.then(step), Promise.resolve()); - } catch (typeError) { - const errorMsg = - typeError instanceof Error ? typeError.message : String(typeError); - throw new Error( - `Failed to type into or submit element '${params.element}'. Error: ${errorMsg}` - ); - } - return { - content: [ - { - type: "text", - text: `Typed "${params.text}" into: ${params.element}${ - params.submit ? " and submitted" : "" - }`, - }, - ], - }; - }; - - return { action, code, captureSnapshot: true, waitForNetwork: true }; - }, -}); - -// --- Tool: Select Option (Adapted Handle, Example Action) --- -const selectOptionSchema = elementSchema.extend({ - values: z - .array(z.string()) - .describe("Array of values to select in the dropdown."), -}); -type SelectOptionInput = z.infer; - -const selectOption = defineTool({ - capability: "core", - schema: { - name: "browserbase_select_option", - description: "Select an option in a dropdown using ref.", - inputSchema: selectOptionSchema, - }, - handle: async ( - context: Context, - params: SelectOptionInput - ): Promise => { - // Get locator directly from snapshot - const snapshot = context.snapshotOrDie(); - const locator = snapshot.refLocator(params.ref); - - const code = [ - `// Select options [${params.values.join(", ")}] in ${params.element}`, - // Remove javascript.formatObject, use simple JSON.stringify for code comment - `// await page.${await generateLocator( - locator - )}.selectOption(${JSON.stringify(params.values)});`, - ]; - - const action = async (): Promise => { - try { - // Use locator directly for the action - await locator.waitFor({ state: "visible", timeout: 5000 }); - await locator.selectOption(params.values, { timeout: 5000 }); - } catch (selectError) { - const errorMsg = - selectError instanceof Error - ? selectError.message - : String(selectError); - throw new Error( - `Failed to select option(s) in element '${params.element}'. Error: ${errorMsg}` - ); - } - return { - content: [ - { type: "text", text: `Selected options in: ${params.element}` }, - ], - }; - }; - - return { action, code, captureSnapshot: true, waitForNetwork: true }; - }, -}); - -// --- Tool: Screenshot (Adapted Handle, Example Action) --- -const screenshotSchema = z.object({ - raw: z - .boolean() - .optional() - .describe( - "Whether to return without compression (PNG). Default is false (JPEG)." - ), - element: z - .string() - .optional() - .describe("Human-readable element description."), - ref: z - .string() - .optional() - .describe("Exact target element reference from the page snapshot.") -}); - -type ScreenshotInput = z.infer; - -const screenshot = defineTool({ - capability: "core", - schema: { - name: "browserbase_take_screenshot", - description: `Take a screenshot of the current page or element using ref.`, - inputSchema: screenshotSchema, - }, - handle: async ( - context: Context, - params: ScreenshotInput - ): Promise => { - if (!!params.element !== !!params.ref) { - throw new Error("Both element and ref must be provided or neither."); - } - - const page = await context.getActivePage(); - if (!page) { - throw new Error("No active page found for screenshot"); - } - // Conditionally get snapshot only if ref is provided - let pageSnapshot: PageSnapshot | null = null; - if (params.ref) { - pageSnapshot = context.snapshotOrDie(); - } - const fileType = params.raw ? "png" : "jpeg"; - const fileName = await outputFile( - context.config, - `screenshot-${Date.now()}.${fileType}` - ); - - const baseOptions: PageScreenshotOptions = { - scale: "css", - timeout: 15000, // Kept existing timeout - }; - - let options: PageScreenshotOptions; - - if (fileType === "jpeg") { - options = { - ...baseOptions, - type: "jpeg", - quality: 50, // Quality is only for jpeg - path: fileName, - }; - } else { - options = { - ...baseOptions, - type: "png", - path: fileName, - }; - } - - const isElementScreenshot = params.element && params.ref; - const code: string[] = []; - code.push( - `// Screenshot ${ - isElementScreenshot ? params.element : "viewport" - } and save it as ${fileName}` - ); - - // Conditionally get locator only if ref and snapshot are available - const locator = - params.ref && pageSnapshot ? pageSnapshot.refLocator(params.ref) : null; - - // Use JSON.stringify for code generation as javascript.formatObject is not available - const optionsForCode = { ...options }; - // delete optionsForCode.path; // Path is an internal detail for saving, not usually part of the "command" log - - if (locator) { - code.push( - `// await page.${await generateLocator( - locator - )}.screenshot(${JSON.stringify(optionsForCode)});` - ); - } else { - code.push(`// await page.screenshot(${JSON.stringify(optionsForCode)});`); - } - - const action = async (): Promise => { - // Access config via context.config - const includeBase64 = - !context.config.tools?.browserbase_take_screenshot?.omitBase64; - - // Use the page directly for full page screenshots if locator is null - const screenshotBuffer = locator - ? await locator.screenshot(options) - : await page.screenshot(options); - - if (includeBase64) { - const rawBase64 = screenshotBuffer.toString("base64"); - return { - content: [ - { - type: "image", - format: fileType, // format might be redundant if mimeType is present, but kept for now - mimeType: fileType === "png" ? `image/png` : `image/jpeg`, - data: rawBase64, - }, - ], - }; - } else { - // If base64 is not included, return an empty content array - return { content: [] }; - } - }; - - return { - code, - action, - captureSnapshot: true, - waitForNetwork: false, - }; - }, -}); - -export async function generateLocator(locator: Locator): Promise { - return (locator as any)._generateLocatorString(); -} - -export default [snapshot, click, drag, hover, type, selectOption, screenshot]; \ No newline at end of file diff --git a/browserbase/src/tools/tool.ts b/browserbase/src/tools/tool.ts deleted file mode 100644 index 197b01c..0000000 --- a/browserbase/src/tools/tool.ts +++ /dev/null @@ -1,67 +0,0 @@ -import type { ImageContent, TextContent } from '@modelcontextprotocol/sdk/types.js'; -import type { z } from 'zod'; -import type { Context } from '../context.js'; -import type * as playwright from 'playwright'; -import type { ToolCapability } from '../config.js'; -import type { BrowserSession } from '../sessionManager.js'; -import type { Server } from '@modelcontextprotocol/sdk/server/index.js'; -import type { Config } from '../config.js'; - -export type ToolSchema = { - name: string; - description: string; - inputSchema: Input; -}; - -// Export InputType -export type InputType = z.Schema; - -export type FileUploadModalState = { - type: 'fileChooser'; - description: string; - fileChooser: playwright.FileChooser; -}; - -export type DialogModalState = { - type: 'dialog'; - description: string; - dialog: playwright.Dialog; -}; - -export type ModalState = FileUploadModalState | DialogModalState; - -export type ToolActionResult = { content?: (ImageContent | TextContent)[] } | undefined | void; - -export type ToolResult = { - code: string[]; - action?: () => Promise; - captureSnapshot: boolean; - waitForNetwork: boolean; - resultOverride?: ToolActionResult; -}; - -export type Tool = { - capability: ToolCapability; - schema: ToolSchema; - clearsModalState?: ModalState['type']; - handle: (context: Context, params: z.output) => Promise; - }; - - export type ToolFactory = (snapshot: boolean) => Tool; - - export function defineTool(tool: Tool): Tool { - return tool; - } - -export {}; // Ensure this is treated as a module - -// Represents the execution context for a tool -// Might include the page, server instance for notifications, etc. -export interface ToolContext { - page: BrowserSession['page']; - browser: BrowserSession['browser']; - server: Server; - sessionId: string; - config: Config; - context: Context; // The main context instance -} \ No newline at end of file diff --git a/browserbase/src/tools/toolUtils.ts b/browserbase/src/tools/toolUtils.ts deleted file mode 100644 index fd09fc9..0000000 --- a/browserbase/src/tools/toolUtils.ts +++ /dev/null @@ -1,31 +0,0 @@ -import { CallToolResult, TextContent } from "@modelcontextprotocol/sdk/types.js"; - -/** - * Creates a standardized error result for tool calls. - * @param message The error message text. - * @param toolName Optional tool name for logging/context. - * @returns CallToolResult object indicating an error. - */ -export function createErrorResult(message: string, toolName?: string): CallToolResult { - const prefix = toolName ? `[${toolName}] Error: ` : "Error: "; - // console.error(prefix + message); - return { - content: [{ type: "text", text: prefix + message } as TextContent], - isError: true, - }; -} - -/** - * Creates a standardized success result with text content. - * @param message The success message text. - * @param toolName Optional tool name for logging/context. - * @returns CallToolResult object indicating success. - */ -export function createSuccessResult(message: string, toolName?: string): CallToolResult { - const prefix = toolName ? `[${toolName}] Success: ` : "Success: "; - // console.log(prefix + message); // Log success - return { - content: [{ type: "text", text: message } as TextContent], - isError: false, - }; -} \ No newline at end of file diff --git a/browserbase/src/tools/utils.ts b/browserbase/src/tools/utils.ts deleted file mode 100644 index 4cdc7e3..0000000 --- a/browserbase/src/tools/utils.ts +++ /dev/null @@ -1,59 +0,0 @@ -import type * as playwright from 'playwright'; -import type { Context } from '../context.js'; - -export async function waitForCompletion(context: Context, page: playwright.Page, callback: () => Promise): Promise { - const requests = new Set(); - let frameNavigated = false; - let waitCallback: () => void = () => {}; - const waitBarrier = new Promise(f => { waitCallback = f; }); - - const requestListener = (request: playwright.Request) => requests.add(request); - const requestFinishedListener = (request: playwright.Request) => { - requests.delete(request); - if (!requests.size) - waitCallback(); - }; - - const frameNavigateListener = (frame: playwright.Frame) => { - if (frame.parentFrame()) - return; - frameNavigated = true; - dispose(); - clearTimeout(timeout); - void frame.waitForLoadState('load').then(() => { - waitCallback(); - }); - }; - - const onTimeout = () => { - dispose(); - waitCallback(); - }; - - page.on('request', requestListener); - page.on('requestfinished', requestFinishedListener); - page.on('framenavigated', frameNavigateListener); - const timeout = setTimeout(onTimeout, 10000); - - const dispose = () => { - page.off('request', requestListener); - page.off('requestfinished', requestFinishedListener); - page.off('framenavigated', frameNavigateListener); - clearTimeout(timeout); - }; - - try { - const result = await callback(); - if (!requests.size && !frameNavigated) - waitCallback(); - await waitBarrier; - await context.waitForTimeout(1000); - return result; - } finally { - dispose(); - } -} - -export function sanitizeForFilePath(s: string) { - return s.replace(/[^a-zA-Z0-9_.-]/g, '_'); // More robust sanitization -} \ No newline at end of file diff --git a/browserbase/src/transport.ts b/browserbase/src/transport.ts deleted file mode 100644 index 82a703a..0000000 --- a/browserbase/src/transport.ts +++ /dev/null @@ -1,118 +0,0 @@ -import http from 'node:http'; -import assert from 'node:assert'; -import crypto from 'node:crypto'; - -import { ServerList } from './server.js'; -import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js'; -import { SSEServerTransport } from '@modelcontextprotocol/sdk/server/sse.js'; -import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js'; - -export async function startStdioTransport(serverList: ServerList) { - const server = await serverList.create(); - await server.connect(new StdioServerTransport()); -} - -async function handleSSE(req: http.IncomingMessage, res: http.ServerResponse, url: URL, serverList: ServerList, sessions: Map) { - if (req.method === 'POST') { - const sessionId = url.searchParams.get('sessionId'); - if (!sessionId) { - res.statusCode = 400; - return res.end('Missing sessionId'); - } - - const transport = sessions.get(sessionId); - if (!transport) { - res.statusCode = 404; - return res.end('Session not found'); - } - - return await transport.handlePostMessage(req, res); - } else if (req.method === 'GET') { - const transport = new SSEServerTransport('/sse', res); - sessions.set(transport.sessionId, transport); - const server = await serverList.create(); - res.on('close', () => { - sessions.delete(transport.sessionId); - serverList.close(server).catch(e => { - // eslint-disable-next-line no-console - // console.error(e); - }); - }); - return await server.connect(transport); - } - - res.statusCode = 405; - res.end('Method not allowed'); -} - -async function handleStreamable(req: http.IncomingMessage, res: http.ServerResponse, serverList: ServerList, sessions: Map) { - const sessionId = req.headers['mcp-session-id'] as string | undefined; - if (sessionId) { - const transport = sessions.get(sessionId); - if (!transport) { - res.statusCode = 404; - res.end('Session not found'); - return; - } - return await transport.handleRequest(req, res); - } - - if (req.method === 'POST') { - const transport = new StreamableHTTPServerTransport({ - sessionIdGenerator: () => crypto.randomUUID(), - onsessioninitialized: sessionId => { - sessions.set(sessionId, transport); - } - }); - transport.onclose = () => { - if (transport.sessionId) - sessions.delete(transport.sessionId); - }; - const server = await serverList.create(); - await server.connect(transport); - return await transport.handleRequest(req, res); - } - - res.statusCode = 400; - res.end('Invalid request'); -} - -export function startHttpTransport(port: number, hostname: string | undefined, serverList: ServerList) { - const sseSessions = new Map(); - const streamableSessions = new Map(); - const httpServer = http.createServer(async (req, res) => { - const url = new URL(`http://localhost${req.url}`); - if (url.pathname.startsWith('/mcp')) - await handleStreamable(req, res, serverList, streamableSessions); - else - await handleSSE(req, res, url, serverList, sseSessions); - }); - httpServer.listen(port, hostname, () => { - const address = httpServer.address(); - assert(address, 'Could not bind server socket'); - let url: string; - if (typeof address === 'string') { - url = address; - } else { - const resolvedPort = address.port; - let resolvedHost = address.family === 'IPv4' ? address.address : `[${address.address}]`; - if (resolvedHost === '0.0.0.0' || resolvedHost === '[::]') - resolvedHost = 'localhost'; - url = `http://${resolvedHost}:${resolvedPort}`; - } - const message = [ - `Listening on ${url}`, - 'Put this in your client config:', - JSON.stringify({ - 'mcpServers': { - 'browserbase': { - 'url': `${url}/sse` - } - } - }, undefined, 2), - 'If your client supports streamable HTTP, you can use the /mcp endpoint instead.', - ].join('\n'); - // eslint-disable-next-line no-console - console.log(message); - }); -} \ No newline at end of file diff --git a/browserbase/tests/.gitkeep b/browserbase/tests/.gitkeep deleted file mode 100644 index 5c3383d..0000000 --- a/browserbase/tests/.gitkeep +++ /dev/null @@ -1 +0,0 @@ -# Placeholder for tests \ No newline at end of file diff --git a/browserbase/tsconfig.json b/browserbase/tsconfig.json deleted file mode 100644 index 3067ef0..0000000 --- a/browserbase/tsconfig.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "compilerOptions": { - "target": "ES2022", - "module": "NodeNext", - "moduleResolution": "NodeNext", - "strict": true, - "esModuleInterop": true, - "skipLibCheck": true, - "forceConsistentCasingInFileNames": true, - "resolveJsonModule": true, - "outDir": "dist", - "rootDir": "src" - }, - "include": ["src/**/*.ts"], - "exclude": ["node_modules"] -} \ No newline at end of file diff --git a/browserbase/utils/.gitkeep b/browserbase/utils/.gitkeep deleted file mode 100644 index 00b6d7b..0000000 --- a/browserbase/utils/.gitkeep +++ /dev/null @@ -1 +0,0 @@ -# Placeholder for utility scripts \ No newline at end of file diff --git a/browserbase/cli.js b/cli.js similarity index 100% rename from browserbase/cli.js rename to cli.js diff --git a/stagehand/config.d.ts b/config.d.ts similarity index 100% rename from stagehand/config.d.ts rename to config.d.ts diff --git a/browserbase/index.d.ts b/index.d.ts similarity index 100% rename from browserbase/index.d.ts rename to index.d.ts diff --git a/browserbase/index.js b/index.js similarity index 100% rename from browserbase/index.js rename to index.js diff --git a/stagehand/package-lock.json b/package-lock.json similarity index 99% rename from stagehand/package-lock.json rename to package-lock.json index dd0977b..373de43 100644 --- a/stagehand/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "@browserbasehq/mcp", - "version": "0.5.1", + "version": "2.0.0", "lockfileVersion": 3, "requires": true, "packages": { diff --git a/stagehand/package.json b/package.json similarity index 97% rename from stagehand/package.json rename to package.json index 4979040..5a876e4 100644 --- a/stagehand/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@browserbasehq/mcp", - "version": "0.5.1", + "version": "2.0.0", "description": "MCP server for AI web browser automation using Stagehand", "license": "MIT", "author": "Browserbase, Inc. (https://www.browserbase.com/)", diff --git a/browserbase/smithery.config.js b/smithery.config.js similarity index 100% rename from browserbase/smithery.config.js rename to smithery.config.js diff --git a/browserbase/smithery.yaml b/smithery.yaml similarity index 100% rename from browserbase/smithery.yaml rename to smithery.yaml diff --git a/stagehand/src/config.ts b/src/config.ts similarity index 98% rename from stagehand/src/config.ts rename to src/config.ts index 13aad54..ecd65a7 100644 --- a/stagehand/src/config.ts +++ b/src/config.ts @@ -1,7 +1,7 @@ import os from 'os'; import fs from 'fs'; import path from 'path'; -import { sanitizeForFilePath } from './tools/utils.js'; +import { sanitizeForFilePath } from './utils.js'; import type { Cookie } from "playwright-core"; import type { Config } from '../config.js'; import { AvailableModelSchema } from '@browserbasehq/stagehand'; diff --git a/stagehand/src/context.ts b/src/context.ts similarity index 100% rename from stagehand/src/context.ts rename to src/context.ts diff --git a/stagehand/src/index.ts b/src/index.ts similarity index 100% rename from stagehand/src/index.ts rename to src/index.ts diff --git a/stagehand/src/program.ts b/src/program.ts similarity index 100% rename from stagehand/src/program.ts rename to src/program.ts diff --git a/stagehand/src/prompts.ts b/src/prompts.ts similarity index 88% rename from stagehand/src/prompts.ts rename to src/prompts.ts index e9cf6e0..83b6cc9 100644 --- a/stagehand/src/prompts.ts +++ b/src/prompts.ts @@ -1,6 +1,7 @@ /** - * Prompts module for the Stagehand MCP server + * Prompts module for the Browserbase MCP server * Contains prompts definitions and handlers for prompt-related requests + * Docs: https://modelcontextprotocol.io/docs/concepts/prompts */ // Define the prompts diff --git a/stagehand/src/resources.ts b/src/resources.ts similarity index 100% rename from stagehand/src/resources.ts rename to src/resources.ts diff --git a/stagehand/src/server.ts b/src/server.ts similarity index 100% rename from stagehand/src/server.ts rename to src/server.ts diff --git a/stagehand/src/sessionManager.ts b/src/sessionManager.ts similarity index 100% rename from stagehand/src/sessionManager.ts rename to src/sessionManager.ts diff --git a/stagehand/src/tools/act.ts b/src/tools/act.ts similarity index 100% rename from stagehand/src/tools/act.ts rename to src/tools/act.ts diff --git a/stagehand/src/tools/extract.ts b/src/tools/extract.ts similarity index 100% rename from stagehand/src/tools/extract.ts rename to src/tools/extract.ts diff --git a/stagehand/src/tools/index.ts b/src/tools/index.ts similarity index 100% rename from stagehand/src/tools/index.ts rename to src/tools/index.ts diff --git a/stagehand/src/tools/navigate.ts b/src/tools/navigate.ts similarity index 100% rename from stagehand/src/tools/navigate.ts rename to src/tools/navigate.ts diff --git a/stagehand/src/tools/observe.ts b/src/tools/observe.ts similarity index 100% rename from stagehand/src/tools/observe.ts rename to src/tools/observe.ts diff --git a/stagehand/src/tools/screenshot.ts b/src/tools/screenshot.ts similarity index 100% rename from stagehand/src/tools/screenshot.ts rename to src/tools/screenshot.ts diff --git a/stagehand/src/tools/session.ts b/src/tools/session.ts similarity index 100% rename from stagehand/src/tools/session.ts rename to src/tools/session.ts diff --git a/stagehand/src/tools/tool.ts b/src/tools/tool.ts similarity index 100% rename from stagehand/src/tools/tool.ts rename to src/tools/tool.ts diff --git a/stagehand/src/transport.ts b/src/transport.ts similarity index 100% rename from stagehand/src/transport.ts rename to src/transport.ts diff --git a/stagehand/src/utils.ts b/src/utils.ts similarity index 82% rename from stagehand/src/utils.ts rename to src/utils.ts index 47f5036..e35e30e 100644 --- a/stagehand/src/utils.ts +++ b/src/utils.ts @@ -21,4 +21,8 @@ export function sanitizeMessage(message: any): string { id: null, }); } +} + +export function sanitizeForFilePath(s: string) { + return s.replace(/[^a-zA-Z0-9_.-]/g, '_'); // More robust sanitization } \ No newline at end of file diff --git a/stagehand/README.md b/stagehand/README.md deleted file mode 100644 index 0b2f8dc..0000000 --- a/stagehand/README.md +++ /dev/null @@ -1,510 +0,0 @@ -# Browserbase MCP Server - -![cover](../assets/browserbase-mcp.png) - -The Model Context Protocol (MCP) is an open protocol that enables seamless integration between LLM applications and external data sources and tools. Whether you're building an AI-powered IDE, enhancing a chat interface, or creating custom AI workflows, MCP provides a standardized way to connect LLMs with the context they need. - - - -## How to Setup - -### Quickstarts: - -[![Install MCP Server](https://cursor.com/deeplink/mcp-install-dark.png)](cursor://anysphere.cursor-deeplink/mcp/install?name=browserbase&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyJAYnJvd3NlcmJhc2VocS9tY3AiXSwiZW52Ijp7IkJST1dTRVJCQVNFX0FQSV9LRVkiOiIiLCJCUk9XU0VSQkFTRV9QUk9KRUNUX0lEIjoiIn19) - -You can either use our Server hosted on NPM or run it completely locally by cloning this repo. - -### To run on NPM (Recommended) - -Go into your MCP Config JSON and add the Browserbase Server: - -```json -{ - "mcpServers": { - "browserbase": { - "command": "npx", - "args" : ["@browserbasehq/mcp"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -Thats it! Reload your MCP client and Claude will be able to use Browserbase. - -### To run 100% local: - -```bash -# Clone the Repo -git clone https://github.com/browserbase/mcp-server-browserbase.git - -# Install the dependencies in the proper directory and build the project -cd stagehand -npm install && npm run build - -``` - -Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. - -### STDIO: - -To your MCP Config JSON file add the following: - -```json -{ -"mcpServers": { - "browserbase": { - "command" : "node", - "args" : ["/path/to/mcp-server-browserbase/stagehand/cli.js"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### SSE: - -Run the following command in your terminal. You can add any flags (see options below) that you see fit to customize your configuration. - -```bash - node cli.js --port 8931 -``` - -Then in your MCP Config JSON file put the following: - -```json - { - "mcpServers": { - "browserbase": { - "url": "http://localhost:8931/sse", - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } - } -``` - -Then reload your MCP client and you should be good to go! - -## Flags Explained: - -The Browserbase MCP server accepts the following command-line flags: - -| Flag | Description | -|------|-------------| -| `--browserbaseApiKey ` | Your Browserbase API key for authentication | -| `--browserbaseProjectId ` | Your Browserbase project ID | -| `--proxies` | Enable Browserbase proxies for the session | -| `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | -| `--contextId ` | Specify a Browserbase Context ID to use | -| `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | -| `--port ` | Port to listen on for HTTP/SSE transport | -| `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | -| `--cookies [json]` | JSON array of cookies to inject into the browser | -| `--browserWidth ` | Browser viewport width (default: 1024) | -| `--browserHeight ` | Browser viewport height (default: 768) | -| `--modelName ` | The model to use for Stagehand (default: google/gemini-2.0-flash) | - -These flags can be passed directly to the CLI or configured in your MCP configuration file. - -### NOTE: - -Currently, these flags can only be used with the local server (npx @browserbasehq/mcp). - -____ - -## Flags & Example Configs - -### Proxies - -Here are our docs on [Proxies](https://docs.browserbase.com/features/proxies). - -To use proxies in STDIO, set the --proxies flag in your MCP Config: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--proxies"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` -### Advanced Stealth - -Here are our docs on [Advanced Stealth](https://docs.browserbase.com/features/stealth-mode#advanced-stealth-mode). - -To use proxies in STDIO, set the --advancedStealth flag in your MCP Config: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--advancedStealth"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Contexts - -Here are our docs on [Contexts](https://docs.browserbase.com/features/contexts) - -To use contexts in STDIO, set the --contextId flag in your MCP Config: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--contextId", ""], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Cookie Injection - -Why would you need to inject cookies? Our context API currently works on persistent cookies, but not session cookies. So sometimes our persistent auth might not work (we're working hard to add this functionality). - -You can flag cookies into the MCP by adding the cookies.json to your MCP Config. - -To use proxies in STDIO, set the --proxies flag in your MCP Config. Your cookies JSON must be in the type of [Playwright Cookies](https://playwright.dev/docs/api/class-browsercontext#browser-context-cookies) - -```json -{ - "mcpServers": { - "browserbase" { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", "--cookies", - '{ - "cookies": json, - }' - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Browser Viewport Sizing - -The default viewport sizing for a browser session is 1024 x 768. You can adjust the Browser viewport sizing with browserWidth and browserHeight flags. - -Here's how to use it for custom browser sizing. We recommend to stick with 16:9 aspect ratios (ie: 1920 x 1080, 1280, 720, 1024 x 768) - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", - "--browserHeight 1080", - "--browserWidth 1920", - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -### Model Configuration - -Stagehand defaults to using Google's Gemini 2.0 Flash model, but you can configure it to use other models like GPT-4o, Claude, or other providers. - -Here's how to configure different models: - -```json -{ - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", - "--modelName", "gpt-4o", - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } - } -} -``` - -Available models include: -- **Gemini**: `google/gemini-2.0-flash` (default), `google/gemini-1.5-pro`, `google/gemini-1.5-flash` -- **OpenAI**: `gpt-4o`, `gpt-4o-mini`, `o1-mini`, `o1-preview`, `o3-mini` -- **Claude**: `claude-3-5-sonnet-latest`, `claude-3-7-sonnet-latest` -- **Other providers**: Cerebras, Groq, and more - -* Note: -The model must be supported in Stagehand. Checkout the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms). - -## Structure - -* `src/`: TypeScript source code - * `index.ts`: Main entry point and Smithery default export function - * `config.ts`: Configuration management and CLI option parsing - * `context.ts`: Context class managing Stagehand instances and tool execution - * `logging.ts`: Comprehensive logging system with file rotation - * `program.ts`: CLI program setup using Commander.js - * `prompts.ts`: Prompt templates for MCP clients - * `resources.ts`: Resource management for screenshots - * `server.ts`: Server list management for multiple server instances - * `sessionManager.ts`: Browserbase session creation and lifecycle management - * `transport.ts`: HTTP/SSE and STDIO transport handlers - * `utils.ts`: Utility functions for message sanitization - * `tools/`: Tool definitions and implementations - * `act.ts`: Stagehand action execution tool - * `extract.ts`: Page content extraction tool - * `navigate.ts`: URL navigation tool - * `observe.ts`: Element observation tool - * `screenshot.ts`: Screenshot capture tool - * `session.ts`: Session management tools (create/close) - * `tool.ts`: Tool type definitions and interfaces - * `utils.ts`: Tool utility functions -* `dist/`: Compiled JavaScript output -* `tests/`: Placeholder for tests (coming soon) -* `cli.js`: Executable entry point for CLI usage -* `config.d.ts`: TypeScript type definitions for configuration -* `index.d.ts` & `index.js`: Module exports for programmatic usage -* `package.json`: Package metadata and dependencies -* `smithery.config.js` & `smithery.yaml`: Smithery configuration files -* `tsconfig.json`: TypeScript compiler configuration -* Configuration files (`.json`, `.ts`, `.mjs`, `.npmignore`) - -## Tools - -### Stagehand Tools (Browserbase MCP) - -- **stagehand_navigate** - - Navigate to any URL in the browser - - Input: - - `url` (string): The URL to navigate to - -- **stagehand_act** - - Perform an action on the web page - - Inputs: - - `action` (string): The action to perform (e.g., "click the login button") - - `variables` (object, optional): Variables used in the action template - -- **stagehand_extract** - - Extract all text content from the current page (filters out CSS and JavaScript) - - No inputs required - -- **stagehand_observe** - - Observe actions that can be performed on the web page - - Input: - - `instruction` (string): Specific instruction for observation (e.g., "find the login button") - -- **screenshot** - - Capture a PNG screenshot of the current page - - Output: - - `text`: Friendly confirmation message with the screenshot name - - `image`: Base-64 encoded PNG data - -### Session Management Tools - -- **browserbase_session_create** - - Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand - - Applies all configuration flags (proxies, stealth, viewport, cookies, etc.) - - Initializes Stagehand instance connected to the browser session - - Input: - - `sessionId` (string, optional): Optional session ID to use/reuse. If not provided, creates new session - - Output: - - Live debugger URL for the Browserbase session - -- **browserbase_session_close** - - Close the current Browserbase session, disconnect the browser, and cleanup Stagehand instance - - Input: - - `random_string` (string, optional): Dummy parameter for consistent tool call format - - Output: - - Confirmation message and session replay URL - -### Resources - -The server provides access to screenshot resources: - -1. **Screenshots** (`screenshot://`) - - PNG images of captured screenshots - -## File Structure - -The Stagehand MCP server codebase is organized into the following key modules: - -- **index.ts**: Smithery default export function that creates and configures the MCP server -- **config.ts**: Configuration management, CLI option parsing, and environment variable handling -- **context.ts**: Context class that manages Stagehand instances, tool execution, and browser sessions -- **program.ts**: CLI program setup using Commander.js with all command-line options -- **server.ts**: Server list management for handling multiple server instances -- **sessionManager.ts**: Browserbase session creation, lifecycle management, and cleanup -- **transport.ts**: HTTP/SSE and STDIO transport handlers for different connection types -- **logging.ts**: Comprehensive logging system with file rotation and in-memory logs -- **prompts.ts**: Prompt templates for MCP clients -- **resources.ts**: Screenshot resource management and URI handling -- **utils.ts**: Message sanitization utilities -- **tools/**: Individual tool implementations with type-safe schemas - -## Module Descriptions - -### index.ts - -The Smithery default export function that: -- Defines the configuration schema with Zod validation -- Creates the MCP server instance with proper metadata -- Registers all tools with their schemas and handlers -- Returns the configured server for use by Smithery or direct imports - -### config.ts - -Configuration management module that: -- Defines CLI option types and default values -- Resolves configuration from environment variables, CLI args, and defaults -- Provides utility functions for file paths and config merging -- Handles Browserbase API key and project ID validation - -### context.ts - -The main Context class that: -- Manages Stagehand instances per session with lifecycle handling -- Executes tool actions with proper error handling and logging -- Provides access to active browser pages and sessions -- Handles resource listing and reading for screenshots -- Coordinates between tools, sessions, and the MCP server - -### program.ts - -CLI program setup using Commander.js that: -- Defines all command-line options and flags -- Parses arguments and resolves final configuration -- Sets up exit handlers for graceful shutdown -- Starts either HTTP/SSE or STDIO transport based on options - -### server.ts - -Server list management that: -- Maintains multiple server instances for different connections -- Provides factory pattern for server creation -- Handles server lifecycle and cleanup -- Manages concurrent server connections - -### sessionManager.ts - -Browserbase session management that: -- Creates and connects to Browserbase sessions via CDP -- Manages session lifecycle with automatic cleanup -- Handles default and custom session IDs -- Provides cookie injection and context management -- Tracks active sessions and handles disconnections - -### transport.ts - -Transport layer implementations for: -- STDIO transport for direct MCP communication -- HTTP/SSE transport for web-based connections -- Streamable HTTP transport for advanced clients -- Session management across different transport types - -### prompts.ts - -Prompt template definitions: -- Exports available prompts list -- Provides `click_search_button` template -- Handles prompt retrieval by name with validation - -### resources.ts - -Resource management for the MCP protocol: -- Manages screenshot storage in memory -- Provides resource listing for available screenshots -- Handles resource URI resolution and content retrieval -- Returns base64-encoded PNG data for screenshot resources - -### utils.ts - -Message sanitization utilities: -- `sanitizeMessage`: Ensures proper JSON formatting for MCP messages -- Error handling for malformed JSON with fallback responses - -### tools/ Directory - -Individual tool implementations with: -- **act.ts**: Stagehand action execution with variable support -- **extract.ts**: Page content extraction with CSS/JS filtering -- **navigate.ts**: URL navigation with network waiting -- **observe.ts**: Element observation with specific instructions -- **screenshot.ts**: Screenshot capture with base64 encoding -- **session.ts**: Session create/close tools with Browserbase integration -- **tool.ts**: Type definitions and interfaces for all tools -- **utils.ts**: Shared utility functions for file path sanitization - -## Key Features - -- AI-powered web automation -- Perform actions on web pages -- Extract structured data from web pages -- Observe possible actions on web pages -- Simple and extensible API -- Model-agnostic support for various LLM providers - -## Environment Variables - -- `BROWSERBASE_API_KEY`: API key for BrowserBase authentication -- `BROWSERBASE_PROJECT_ID`: Project ID for BrowserBase -- `DEBUG`: Enable debug logging - -## MCP Capabilities - -This server implements the following MCP capabilities: - -- **Tools**: Provides 7 tools for browser automation: - - Stagehand tools: navigate, act, extract, observe, screenshot - - Session management: create and close Browserbase sessions -- **Prompts**: Provides prompt templates (click_search_button) -- **Resources**: Screenshot resource management with URI-based access -- **Logging**: Comprehensive logging with file rotation and MCP integration - -For more information about the Model Context Protocol, visit: -- [MCP Documentation](https://modelcontextprotocol.io/docs) -- [MCP Specification](https://spec.modelcontextprotocol.io/) - -## License - -Licensed under the MIT License. - -Copyright 2025 Browserbase, Inc. \ No newline at end of file diff --git a/stagehand/cli.js b/stagehand/cli.js deleted file mode 100755 index 9610f3e..0000000 --- a/stagehand/cli.js +++ /dev/null @@ -1,2 +0,0 @@ -#!/usr/bin/env node -import './dist/program.js'; \ No newline at end of file diff --git a/stagehand/index.d.ts b/stagehand/index.d.ts deleted file mode 100644 index f499530..0000000 --- a/stagehand/index.d.ts +++ /dev/null @@ -1,6 +0,0 @@ -import type { Server } from '@modelcontextprotocol/sdk/server/index.js'; - -import type { Config } from './config'; - -export declare function createServer(config?: Config): Promise; -export {}; \ No newline at end of file diff --git a/stagehand/index.js b/stagehand/index.js deleted file mode 100644 index cecbc9e..0000000 --- a/stagehand/index.js +++ /dev/null @@ -1,2 +0,0 @@ -import { createServer } from './dist/index.js'; -export default { createServer }; \ No newline at end of file diff --git a/stagehand/smithery.config.js b/stagehand/smithery.config.js deleted file mode 100644 index e2dfe2e..0000000 --- a/stagehand/smithery.config.js +++ /dev/null @@ -1,10 +0,0 @@ -/** - * @type {import('esbuild').BuildOptions} - */ -export default { - esbuild: { - // Mark playwright-core as external to prevent bundling - // This avoids the relative path resolution issue in Docker - external: ["playwright-core"], - } -} diff --git a/stagehand/smithery.yaml b/stagehand/smithery.yaml deleted file mode 100644 index 8fa57d3..0000000 --- a/stagehand/smithery.yaml +++ /dev/null @@ -1 +0,0 @@ -runtime: "typescript" \ No newline at end of file diff --git a/stagehand/src/tools/utils.ts b/stagehand/src/tools/utils.ts deleted file mode 100644 index 3f72c64..0000000 --- a/stagehand/src/tools/utils.ts +++ /dev/null @@ -1,3 +0,0 @@ -export function sanitizeForFilePath(s: string) { - return s.replace(/[^a-zA-Z0-9_.-]/g, '_'); // More robust sanitization -} \ No newline at end of file diff --git a/tests/.gitkeep b/tests/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/stagehand/tsconfig.json b/tsconfig.json similarity index 100% rename from stagehand/tsconfig.json rename to tsconfig.json From f1d7dece4102915feea565c097171999a16fce66 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 25 Jun 2025 18:21:15 -0700 Subject: [PATCH 08/32] change to structured extract, better prompts for tools --- src/sessionManager.ts | 1 - src/tools/extract.ts | 68 +++++++++++++++++++++++------------------ src/tools/observe.ts | 24 +++++++++++++-- src/tools/screenshot.ts | 8 +++-- 4 files changed, 65 insertions(+), 36 deletions(-) diff --git a/src/sessionManager.ts b/src/sessionManager.ts index 2b366a6..9c1bc70 100644 --- a/src/sessionManager.ts +++ b/src/sessionManager.ts @@ -6,7 +6,6 @@ import { AvailableModel, Stagehand } from "@browserbasehq/stagehand"; import type { Config } from "../config.js"; import type { Cookie } from "playwright-core"; -// Define the type for a session object export type BrowserSession = { browser: Browser; page: Page; diff --git a/src/tools/extract.ts b/src/tools/extract.ts index 79f9f12..17d58f2 100644 --- a/src/tools/extract.ts +++ b/src/tools/extract.ts @@ -4,14 +4,37 @@ import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; const ExtractInputSchema = z.object({ - random_string: z.string().optional().describe("Dummy parameter for no-parameter tools"), + instruction: z.string().describe( + "The specific instruction for what information to extract from the current page. " + + "Be as detailed and specific as possible about what you want to extract. For example: " + + "'Extract all product names and prices from the listing page' or 'Get the article title, " + + "author, and publication date from this blog post'. The more specific your instruction, " + + "the better the extraction results will be. Avoid vague instructions like 'get everything' " + + "or 'extract the data'. Instead, be explicit about the exact elements, text, or information you need." + ), + schema: z.string().describe( + "A JSON schema string that defines the exact structure and format of the data you want to extract. " + + "This schema should be a valid JSON string that describes the expected output format. For example: " + + "'{\"type\": \"object\", \"properties\": {\"title\": {\"type\": \"string\"}, \"price\": {\"type\": \"number\"}}}' " + + "or '{\"type\": \"array\", \"items\": {\"type\": \"object\", \"properties\": {\"name\": {\"type\": \"string\"}, " + + "\"description\": {\"type\": \"string\"}}}}'. The schema helps ensure the extracted data is properly " + + "formatted and structured. If the schema is invalid JSON, extraction will proceed without schema validation. " + + "Use this to specify exactly how you want the extracted information organized and typed." + ), }); type ExtractInput = z.infer; const extractSchema: ToolSchema = { name: "stagehand_extract", - description: "Extracts all of the text from the current page.", + description: + "Extracts structured information and text content from the current web page based on specific instructions " + + "and a defined schema. This tool is ideal for scraping data, gathering information, or pulling specific " + + "content from web pages. Use this tool when you need to get text content, data, or information from a page " + + "rather than interacting with elements. For interactive elements like buttons, forms, or clickable items, " + + "use the observe tool instead. The extraction works best when you provide clear, specific instructions " + + "about what to extract and a well-defined JSON schema for the expected output format. This ensures " + + "the extracted data is properly structured and usable.", inputSchema: ExtractInputSchema, }; @@ -21,40 +44,25 @@ async function handleExtract( ): Promise { const action = async (): Promise => { try { - const page = await context.getActivePage(); - if (!page) { - throw new Error("No active page available"); - } + const stagehand = await context.getStagehand(); + + let parsedSchema = null; + try { + parsedSchema = JSON.parse(params.schema); + } catch (error) { + throw new Error(`Invalid schema format: ${error instanceof Error ? error.message : 'Unknown error'}`); + } - const bodyText = await page.evaluate(() => document.body.innerText); - - const content = bodyText - .split("\n") - .map((line) => line.trim()) - .filter((line) => { - if (!line) return false; - - if ( - (line.includes("{") && line.includes("}")) || - line.includes("@keyframes") || // Remove CSS animations - line.match(/^\.[a-zA-Z0-9_-]+\s*{/) || // Remove CSS lines starting with .className { - line.match(/^[a-zA-Z-]+:[a-zA-Z0-9%\s\(\)\.,-]+;$/) // Remove lines like "color: blue;" or "margin: 10px;" - ) { - return false; - } - return true; - }) - .map((line) => { - return line.replace(/\\u([0-9a-fA-F]{4})/g, (_, hex) => - String.fromCharCode(parseInt(hex, 16)) - ); - }); + const extraction = await stagehand.page.extract({ + instruction: params.instruction, + schema: parsedSchema // If schema not properly formatted, will just extract without given schema + }); return { content: [ { type: "text", - text: `Extracted content:\n${content.join("\n")}`, + text: `Extracted content:\n${extraction.join("\n")}`, }, ], }; diff --git a/src/tools/observe.ts b/src/tools/observe.ts index cd876b7..064e1cc 100644 --- a/src/tools/observe.ts +++ b/src/tools/observe.ts @@ -5,7 +5,18 @@ import type { ToolActionResult } from "../context.js"; const ObserveInputSchema = z.object({ instruction: z.string().describe( - "Instruction for observation (e.g., 'find the login button'). This instruction must be extremely specific." + "Detailed instruction for what specific elements or components to observe on the web page. " + + "This instruction must be extremely specific and descriptive. For example: 'Find the red login button " + + "in the top right corner', 'Locate the search input field with placeholder text', or 'Identify all " + + "clickable product cards on the page'. The more specific and detailed your instruction, the better " + + "the observation results will be. Avoid generic instructions like 'find buttons' or 'see elements'. " + + "Instead, describe the visual characteristics, location, text content, or functionality of the elements " + + "you want to observe. This tool is designed to help you identify interactive elements that you can " + + "later use with the act tool for performing actions like clicking, typing, or form submission." + ), + returnAction: z.boolean().optional().describe( + "Whether to return the action to perform on the element. If true, the action will be returned as a string. " + + "If false, the action will not be returned." ), }); @@ -14,7 +25,14 @@ type ObserveInput = z.infer; const observeSchema: ToolSchema = { name: "stagehand_observe", description: - "Observes elements on the web page. Use this tool to observe elements that you can later use in an action. Use observe instead of extract when dealing with actionable (interactable) elements rather than text. More often than not, you'll want to use extract instead of observe when dealing with scraping or extracting structured text.", + "Observes and identifies specific interactive elements on the current web page that can be used for subsequent actions. " + + "This tool is specifically designed for finding actionable (interactable) elements such as buttons, links, form fields, " + + "dropdowns, checkboxes, and other UI components that you can interact with. Use this tool when you need to locate " + + "elements before performing actions with the act tool. DO NOT use this tool for extracting text content or data - " + + "use the extract tool instead for that purpose. The observe tool returns detailed information about the identified " + + "elements including their properties, location, and interaction capabilities. This information can then be used " + + "to craft precise actions. The more specific your observation instruction, the more accurate the element identification " + + "will be. Think of this as your 'eyes' on the page to find exactly what you need to interact with.", inputSchema: ObserveInputSchema, }; @@ -28,7 +46,7 @@ async function handleObserve( const observations = await stagehand.page.observe({ instruction: params.instruction, - returnAction: false, + returnAction: params.returnAction, }); return { diff --git a/src/tools/screenshot.ts b/src/tools/screenshot.ts index 0b66074..0c0b2a6 100644 --- a/src/tools/screenshot.ts +++ b/src/tools/screenshot.ts @@ -5,7 +5,7 @@ import type { ToolActionResult } from "../context.js"; import { screenshots } from "../resources.js"; const ScreenshotInputSchema = z.object({ - random_string: z.string().optional().describe("Dummy parameter for no-parameter tools"), + name: z.string().optional().describe("The name of the screenshot"), }); type ScreenshotInput = z.infer; @@ -34,7 +34,11 @@ async function handleScreenshot( // Convert buffer to base64 string and store in memory const screenshotBase64 = screenshotBuffer.toString("base64"); - const name = `screenshot-${new Date() + const name = + `screenshot-${params.name}-${new Date() + .toISOString() + .replace(/:/g, "-")}` || + `screenshot-${new Date() .toISOString() .replace(/:/g, "-")}`; screenshots.set(name, screenshotBase64); From 91e313fbfaa042fc7bc76fe63380cf2be4f07ef3 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 25 Jun 2025 19:10:27 -0700 Subject: [PATCH 09/32] better extract + update tool names + add pnpm prettier lint --- README.md | 280 +-- cli.js | 2 +- config.d.ts | 130 +- eslint.config.js | 31 + index.d.ts | 6 +- index.js | 4 +- package-lock.json | 2 +- package.json | 20 +- pnpm-lock.yaml | 5041 +++++++++++++++++++++++++++++++++++++++ smithery.config.js | 4 +- smithery.yaml | 2 +- src/config.ts | 61 +- src/context.ts | 69 +- src/index.ts | 184 +- src/program.ts | 99 +- src/prompts.ts | 19 +- src/resources.ts | 7 +- src/server.ts | 5 +- src/sessionManager.ts | 150 +- src/tools/act.ts | 45 +- src/tools/extract.ts | 49 +- src/tools/index.ts | 2 +- src/tools/navigate.ts | 8 +- src/tools/observe.ts | 39 +- src/tools/screenshot.ts | 18 +- src/tools/session.ts | 96 +- src/tools/tool.ts | 33 +- src/transport.ts | 111 +- src/utils.ts | 16 +- tsconfig.json | 3 +- 30 files changed, 5895 insertions(+), 641 deletions(-) create mode 100644 eslint.config.js create mode 100644 pnpm-lock.yaml diff --git a/README.md b/README.md index 844fedd..5fbaa24 100644 --- a/README.md +++ b/README.md @@ -10,15 +10,15 @@ This server provides cloud browser automation capabilities using [Browserbase](h ## Features -| Feature | Description | -| ------------------- | -------------------------------------------------------------- | -| Browser Automation | Control and orchestrate cloud browsers via Browserbase | -| Data Extraction | Extract structured data from any webpage | -| Web Interaction | Navigate, click, and fill forms with ease | -| Screenshots | Capture full-page and element screenshots | -| Model Flexibility | Supports multiple models (OpenAI, Claude, Gemini, and more) | -| Vision Support | Use annotated screenshots for complex DOMs | -| Session Management | Create, manage, and close browser sessions | +| Feature | Description | +| ------------------ | ----------------------------------------------------------- | +| Browser Automation | Control and orchestrate cloud browsers via Browserbase | +| Data Extraction | Extract structured data from any webpage | +| Web Interaction | Navigate, click, and fill forms with ease | +| Screenshots | Capture full-page and element screenshots | +| Model Flexibility | Supports multiple models (OpenAI, Claude, Gemini, and more) | +| Vision Support | Use annotated screenshots for complex DOMs | +| Session Management | Create, manage, and close browser sessions | ### Alternative Installation Methods @@ -26,11 +26,11 @@ This server provides cloud browser automation capabilities using [Browserbase](h ## How to Setup -### Quickstarts: +### Quickstarts: [![Install MCP Server](https://cursor.com/deeplink/mcp-install-dark.png)](cursor://anysphere.cursor-deeplink/mcp/install?name=browserbase&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyJAYnJvd3NlcmJhc2VocS9tY3AiXSwiZW52Ijp7IkJST1dTRVJCQVNFX0FQSV9LRVkiOiIiLCJCUk9XU0VSQkFTRV9QUk9KRUNUX0lEIjoiIn19) -You can either use our Server hosted on NPM or run it completely locally by cloning this repo. +You can either use our Server hosted on NPM or run it completely locally by cloning this repo. ### To run on NPM (Recommended) @@ -38,25 +38,25 @@ Go into your MCP Config JSON and add the Browserbase Server: ```json { - "mcpServers": { - "browserbase": { - "command": "npx", - "args" : ["@browserbasehq/mcp"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": ["@browserbasehq/mcp"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` -That's it! Reload your MCP client and Claude will be able to use Browserbase. +That's it! Reload your MCP client and Claude will be able to use Browserbase. -### To run 100% local: +### To run 100% local: ```bash -# Clone the Repo +# Clone the Repo git clone https://github.com/browserbase/mcp-server-browserbase.git cd mcp-server-browserbase @@ -64,49 +64,49 @@ cd mcp-server-browserbase npm install && npm run build ``` -Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. +Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. -### STDIO: +### STDIO: -To your MCP Config JSON file add the following: +To your MCP Config JSON file add the following: ```json { -"mcpServers": { - "browserbase": { - "command" : "node", - "args" : ["/path/to/mcp-server-browserbase/cli.js"], + "mcpServers": { + "browserbase": { + "command": "node", + "args": ["/path/to/mcp-server-browserbase/cli.js"], "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` -### SSE: +### SSE: -Run the following command in your terminal. You can add any flags (see options below) that you see fit to customize your configuration. +Run the following command in your terminal. You can add any flags (see options below) that you see fit to customize your configuration. ```bash node cli.js --port 8931 ``` -Then in your MCP Config JSON file put the following: +Then in your MCP Config JSON file put the following: ```json - { - "mcpServers": { - "browserbase": { - "url": "http://localhost:8931/sse", - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } - } +{ + "mcpServers": { + "browserbase": { + "url": "http://localhost:8931/sse", + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } +} ``` Then reload your MCP client and you should be good to go! @@ -115,26 +115,26 @@ Then reload your MCP client and you should be good to go! The Browserbase MCP server accepts the following command-line flags: -| Flag | Description | -|------|-------------| -| `--browserbaseApiKey ` | Your Browserbase API key for authentication | -| `--browserbaseProjectId ` | Your Browserbase project ID | -| `--proxies` | Enable Browserbase proxies for the session | -| `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | -| `--contextId ` | Specify a Browserbase Context ID to use | -| `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | -| `--port ` | Port to listen on for HTTP/SSE transport | -| `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | -| `--cookies [json]` | JSON array of cookies to inject into the browser | -| `--browserWidth ` | Browser viewport width (default: 1024) | -| `--browserHeight ` | Browser viewport height (default: 768) | -| `--modelName ` | The model to use for Stagehand (default: google/gemini-2.0-flash) | +| Flag | Description | +| ----------------------------- | --------------------------------------------------------------------------- | +| `--browserbaseApiKey ` | Your Browserbase API key for authentication | +| `--browserbaseProjectId ` | Your Browserbase project ID | +| `--proxies` | Enable Browserbase proxies for the session | +| `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | +| `--contextId ` | Specify a Browserbase Context ID to use | +| `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | +| `--port ` | Port to listen on for HTTP/SSE transport | +| `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | +| `--cookies [json]` | JSON array of cookies to inject into the browser | +| `--browserWidth ` | Browser viewport width (default: 1024) | +| `--browserHeight ` | Browser viewport height (default: 768) | +| `--modelName ` | The model to use for Stagehand (default: google/gemini-2.0-flash) | These flags can be passed directly to the CLI or configured in your MCP configuration file. -### NOTE: +### NOTE: -Currently, these flags can only be used with the local server (npx @browserbasehq/mcp). +Currently, these flags can only be used with the local server (npx @browserbasehq/mcp). ## Configuration Examples @@ -146,20 +146,20 @@ To use proxies, set the --proxies flag in your MCP Config: ```json { - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--proxies"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": ["@browserbasehq/mcp", "--proxies"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` -### Advanced Stealth +### Advanced Stealth Here are our docs on [Advanced Stealth](https://docs.browserbase.com/features/stealth-mode#advanced-stealth-mode). @@ -167,16 +167,16 @@ To use advanced stealth, set the --advancedStealth flag in your MCP Config: ```json { - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--advancedStealth"], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": ["@browserbasehq/mcp", "--advancedStealth"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` @@ -188,69 +188,70 @@ To use contexts, set the --contextId flag in your MCP Config: ```json { - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : ["@browserbasehq/mcp", "--contextId", ""], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": ["@browserbasehq/mcp", "--contextId", ""], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` ### Cookie Injection -Why would you need to inject cookies? Our context API currently works on persistent cookies, but not session cookies. So sometimes our persistent auth might not work (we're working hard to add this functionality). +Why would you need to inject cookies? Our context API currently works on persistent cookies, but not session cookies. So sometimes our persistent auth might not work (we're working hard to add this functionality). You can inject cookies into the MCP by adding them to your MCP Config. Your cookies JSON must be in the format of [Playwright Cookies](https://playwright.dev/docs/api/class-browsercontext#browser-context-cookies) ```json { - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", "--cookies", - '[{"name": "session", "value": "abc123", "domain": ".example.com"}]' - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": [ + "@browserbasehq/mcp", + "--cookies", + "[{\"name\": \"session\", \"value\": \"abc123\", \"domain\": \".example.com\"}]" + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` -### Browser Viewport Sizing +### Browser Viewport Sizing -The default viewport sizing for a browser session is 1024 x 768. You can adjust the Browser viewport sizing with browserWidth and browserHeight flags. +The default viewport sizing for a browser session is 1024 x 768. You can adjust the Browser viewport sizing with browserWidth and browserHeight flags. Here's how to use it for custom browser sizing. We recommend to stick with 16:9 aspect ratios (ie: 1920 x 1080, 1280 x 720, 1024 x 768) ```json { - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", - "--browserHeight 1080", - "--browserWidth 1920", - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": [ + "@browserbasehq/mcp", + "--browserHeight 1080", + "--browserWidth 1920" + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` -### Model Configuration +### Model Configuration Stagehand defaults to using Google's Gemini 2.0 Flash model, but you can configure it to use other models like GPT-4o, Claude, or other providers. @@ -258,29 +259,27 @@ Here's how to configure different models: ```json { - "mcpServers": { - "browserbase": { - "command" : "npx", - "args" : [ - "@browserbasehq/mcp", - "--modelName", "gpt-4o" - ], - "env": { - "BROWSERBASE_API_KEY": "", - "BROWSERBASE_PROJECT_ID": "" - } + "mcpServers": { + "browserbase": { + "command": "npx", + "args": ["@browserbasehq/mcp", "--modelName", "gpt-4o"], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" } - } + } + } } ``` Available models include: + - **Gemini**: `google/gemini-2.0-flash` (default), `google/gemini-1.5-pro`, `google/gemini-1.5-flash` - **OpenAI**: `gpt-4o`, `gpt-4o-mini`, `o1-mini`, `o1-preview`, `o3-mini` - **Claude**: `claude-3-5-sonnet-latest`, `claude-3-7-sonnet-latest` - **Other providers**: Cerebras, Groq, and more -*Note: The model must be supported in Stagehand. Check out the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms).* +_Note: The model must be supported in Stagehand. Check out the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms)._ ## Tools @@ -288,28 +287,28 @@ The Browserbase MCP server provides the following tools for browser automation: ### Browser Automation Tools -- **stagehand_navigate** +- **browserbase_stagehand_navigate** - Navigate to any URL in the browser - Input: - `url` (string): The URL to navigate to -- **stagehand_act** +- **browserbase_stagehand_act** - Perform an action on the web page using natural language - Inputs: - `action` (string): The action to perform (e.g., "click the login button") - `variables` (object, optional): Variables used in the action template for sensitive data -- **stagehand_extract** +- **browserbase_stagehand_extract** - Extract all text content from the current page (filters out CSS and JavaScript) - No inputs required -- **stagehand_observe** +- **browserbase_stagehand_observe** - Observe and find actionable elements on the web page - Input: - `instruction` (string): Specific instruction for observation (e.g., "find the login button") -- **screenshot** - - Capture a PNG screenshot of the current page +- **browserbase_screenshot** + - Capture a PNG screenshot of the current page - No inputs required - Output: - `text`: Friendly confirmation message with the screenshot name @@ -433,6 +432,7 @@ This server implements the following MCP capabilities: - **Context Persistence**: Maintain authentication and state across sessions For more information about the Model Context Protocol, visit: + - [MCP Documentation](https://modelcontextprotocol.io/docs) - [MCP Specification](https://spec.modelcontextprotocol.io/) @@ -440,4 +440,4 @@ For more information about the Model Context Protocol, visit: Licensed under the MIT License. -Copyright 2025 Browserbase, Inc. \ No newline at end of file +Copyright 2025 Browserbase, Inc. diff --git a/cli.js b/cli.js index 9610f3e..1a2c54a 100755 --- a/cli.js +++ b/cli.js @@ -1,2 +1,2 @@ #!/usr/bin/env node -import './dist/program.js'; \ No newline at end of file +import "./dist/program.js"; diff --git a/config.d.ts b/config.d.ts index f6e1725..d77566b 100644 --- a/config.d.ts +++ b/config.d.ts @@ -2,80 +2,80 @@ import type { Cookie } from "playwright-core"; import type { AvailableModelSchema } from "@browserbasehq/stagehand"; export type Config = { + /** + * The Browserbase API Key to use + */ + browserbaseApiKey?: string; + /** + * The Browserbase Project ID to use + */ + browserbaseProjectId?: string; + /** + * Whether or not to use Browserbase proxies + * https://docs.browserbase.com/features/proxies + * + * @default false + */ + proxies?: boolean; + /** + * Use advanced stealth mode. Only available to Browserbase Scale Plan users. + * + * @default false + */ + advancedStealth?: boolean; + /** + * Potential Browserbase Context to use + * Would be a context ID + */ + context?: { /** - * The Browserbase API Key to use + * The ID of the context to use */ - browserbaseApiKey?: string; + contextId?: string; /** - * The Browserbase Project ID to use + * Whether or not to persist the context + * + * @default true */ - browserbaseProjectId?: string; - /** - * Whether or not to use Browserbase proxies - * https://docs.browserbase.com/features/proxies - * - * @default false - */ - proxies?: boolean; - /** - * Use advanced stealth mode. Only available to Browserbase Scale Plan users. - * - * @default false - */ - advancedStealth?: boolean; - /** - * Potential Browserbase Context to use - * Would be a context ID - */ - context?: { - /** - * The ID of the context to use - */ - contextId?: string; - /** - * Whether or not to persist the context - * - * @default true - */ - persist?: boolean; - }; + persist?: boolean; + }; + /** + * + */ + viewPort?: { /** - * + * The width of the browser */ - viewPort?: { - /** - * The width of the browser - */ - browserWidth?: number; - /** - * The height of the browser - */ - browserHeight?: number; - }; + browserWidth?: number; /** - * Cookies to inject into the Browserbase context - * Format: Array of cookie objects with name, value, domain, and optional path, expires, httpOnly, secure, sameSite + * The height of the browser */ - cookies?: Cookie[]; + browserHeight?: number; + }; + /** + * Cookies to inject into the Browserbase context + * Format: Array of cookie objects with name, value, domain, and optional path, expires, httpOnly, secure, sameSite + */ + cookies?: Cookie[]; + /** + * Whether or not to port to a server + * + */ + server?: { /** - * Whether or not to port to a server - * + * The port to listen on for SSE or MCP transport. */ - server?: { - /** - * The port to listen on for SSE or MCP transport. - */ - port?: number; - /** - * The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces. - */ - host?: string; - }; + port?: number; /** - * The Model that Stagehand uses - * Available models: OpenAI, Claude, Gemini, Cerebras, Groq, and other providers - * - * @default "google/gemini-2.0-flash" + * The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces. */ - modelName?: AvailableModelSchema; -}; \ No newline at end of file + host?: string; + }; + /** + * The Model that Stagehand uses + * Available models: OpenAI, Claude, Gemini, Cerebras, Groq, and other providers + * + * @default "google/gemini-2.0-flash" + */ + modelName?: AvailableModelSchema; +}; diff --git a/eslint.config.js b/eslint.config.js new file mode 100644 index 0000000..786dae4 --- /dev/null +++ b/eslint.config.js @@ -0,0 +1,31 @@ +import js from "@eslint/js"; +import globals from "globals"; +import tseslint from "typescript-eslint"; +import { defineConfig } from "eslint/config"; + +export default defineConfig([ + { + files: ["**/*.{js,mjs,cjs,ts,mts,cts}"], + plugins: { js }, + extends: ["js/recommended"], + ignores: ["dist/**/*"], + }, + { + files: ["**/*.{js,mjs,cjs,ts,mts,cts}"], + languageOptions: { globals: { ...globals.browser, ...globals.node } }, + ignores: ["dist/**/*"], + }, + tseslint.configs.recommended, + { + files: ["**/*.{ts,mts,cts}"], + rules: { + "@typescript-eslint/no-explicit-any": "off", + "@typescript-eslint/no-unused-vars": "off", + "@typescript-eslint/ban-ts-comment": "off", + }, + ignores: ["dist/**/*"], + }, + { + ignores: ["dist/**/*", "node_modules/**/*"], + }, +]); diff --git a/index.d.ts b/index.d.ts index f499530..fea6154 100644 --- a/index.d.ts +++ b/index.d.ts @@ -1,6 +1,6 @@ -import type { Server } from '@modelcontextprotocol/sdk/server/index.js'; +import type { Server } from "@modelcontextprotocol/sdk/server/index.js"; -import type { Config } from './config'; +import type { Config } from "./config"; export declare function createServer(config?: Config): Promise; -export {}; \ No newline at end of file +export {}; diff --git a/index.js b/index.js index cecbc9e..d918704 100644 --- a/index.js +++ b/index.js @@ -1,2 +1,2 @@ -import { createServer } from './dist/index.js'; -export default { createServer }; \ No newline at end of file +import { createServer } from "./dist/index.js"; +export default { createServer }; diff --git a/package-lock.json b/package-lock.json index 373de43..76b4bc8 100644 --- a/package-lock.json +++ b/package-lock.json @@ -6,7 +6,7 @@ "packages": { "": { "name": "@browserbasehq/mcp", - "version": "0.5.1", + "version": "2.0.0", "license": "MIT", "dependencies": { "@browserbasehq/stagehand": "^2.4.0", diff --git a/package.json b/package.json index 5a876e4..5535c16 100644 --- a/package.json +++ b/package.json @@ -2,9 +2,9 @@ "name": "@browserbasehq/mcp", "version": "2.0.0", "description": "MCP server for AI web browser automation using Stagehand", - "license": "MIT", + "license": "Apache-2.0", "author": "Browserbase, Inc. (https://www.browserbase.com/)", - "homepage": "https://modelcontextprotocol.io", + "homepage": "https://www.browserbase.com", "bugs": "https://github.com/modelcontextprotocol/servers/issues", "type": "module", "main": "./cli.js", @@ -21,7 +21,10 @@ "scripts": { "build": "tsc && shx chmod +x dist/*.js", "prepare": "npm run build", - "watch": "tsc --watch" + "watch": "tsc --watch", + "lint": "eslint . --ext .ts", + "prettier:check": "prettier --check .", + "prettier:fix": "prettier --write ." }, "dependencies": { "@browserbasehq/stagehand": "^2.4.0", @@ -30,7 +33,14 @@ "commander": "^14.0.0" }, "devDependencies": { + "@eslint/js": "^9.29.0", + "eslint": "^9.29.0", + "eslint-plugin-react": "^7.37.5", + "globals": "^16.2.0", + "prettier": "^3.6.1", "shx": "^0.3.4", - "typescript": "^5.6.2" - } + "typescript": "^5.6.2", + "typescript-eslint": "^8.35.0" + }, + "packageManager": "pnpm@10.10.0+sha512.d615db246fe70f25dcfea6d8d73dee782ce23e2245e3c4f6f888249fb568149318637dca73c2c5c8ef2a4ca0d5657fb9567188bfab47f566d1ee6ce987815c39" } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml new file mode 100644 index 0000000..9cdb651 --- /dev/null +++ b/pnpm-lock.yaml @@ -0,0 +1,5041 @@ +lockfileVersion: "9.0" + +settings: + autoInstallPeers: true + excludeLinksFromLockfile: false + +importers: + .: + dependencies: + "@browserbasehq/stagehand": + specifier: ^2.4.0 + version: 2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67) + "@modelcontextprotocol/sdk": + specifier: ^1.13.1 + version: 1.13.1 + "@playwright/test": + specifier: ^1.49.0 + version: 1.53.1 + commander: + specifier: ^14.0.0 + version: 14.0.0 + devDependencies: + "@eslint/js": + specifier: ^9.29.0 + version: 9.29.0 + eslint: + specifier: ^9.29.0 + version: 9.29.0 + eslint-plugin-react: + specifier: ^7.37.5 + version: 7.37.5(eslint@9.29.0) + globals: + specifier: ^16.2.0 + version: 16.2.0 + prettier: + specifier: ^3.6.1 + version: 3.6.1 + shx: + specifier: ^0.3.4 + version: 0.3.4 + typescript: + specifier: ^5.6.2 + version: 5.8.3 + typescript-eslint: + specifier: ^8.35.0 + version: 8.35.0(eslint@9.29.0)(typescript@5.8.3) + +packages: + "@ai-sdk/anthropic@1.2.12": + resolution: + { + integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/azure@1.3.23": + resolution: + { + integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/cerebras@0.2.14": + resolution: + { + integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/deepseek@0.2.14": + resolution: + { + integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/google@1.2.19": + resolution: + { + integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/groq@1.2.9": + resolution: + { + integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/mistral@1.2.8": + resolution: + { + integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/openai-compatible@0.2.14": + resolution: + { + integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/openai@1.3.22": + resolution: + { + integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/perplexity@1.1.9": + resolution: + { + integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/provider-utils@2.2.8": + resolution: + { + integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.23.8 + + "@ai-sdk/provider@1.1.3": + resolution: + { + integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==, + } + engines: { node: ">=18" } + + "@ai-sdk/react@1.2.12": + resolution: + { + integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==, + } + engines: { node: ">=18" } + peerDependencies: + react: ^18 || ^19 || ^19.0.0-rc + zod: ^3.23.8 + peerDependenciesMeta: + zod: + optional: true + + "@ai-sdk/togetherai@0.2.14": + resolution: + { + integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@ai-sdk/ui-utils@1.2.11": + resolution: + { + integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.23.8 + + "@ai-sdk/xai@1.2.16": + resolution: + { + integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + + "@anthropic-ai/sdk@0.39.0": + resolution: + { + integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==, + } + + "@browserbasehq/sdk@2.6.0": + resolution: + { + integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==, + } + + "@browserbasehq/stagehand@2.4.0": + resolution: + { + integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==, + } + peerDependencies: + deepmerge: ^4.3.1 + dotenv: ^16.4.5 + zod: ^3.23.8 + + "@eslint-community/eslint-utils@4.7.0": + resolution: + { + integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==, + } + engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } + peerDependencies: + eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 + + "@eslint-community/regexpp@4.12.1": + resolution: + { + integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==, + } + engines: { node: ^12.0.0 || ^14.0.0 || >=16.0.0 } + + "@eslint/config-array@0.20.1": + resolution: + { + integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/config-helpers@0.2.3": + resolution: + { + integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/core@0.14.0": + resolution: + { + integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/core@0.15.1": + resolution: + { + integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/eslintrc@3.3.1": + resolution: + { + integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/js@9.29.0": + resolution: + { + integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/object-schema@2.1.6": + resolution: + { + integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/plugin-kit@0.3.3": + resolution: + { + integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@google/genai@0.8.0": + resolution: + { + integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==, + } + engines: { node: ">=18.0.0" } + + "@humanfs/core@0.19.1": + resolution: + { + integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==, + } + engines: { node: ">=18.18.0" } + + "@humanfs/node@0.16.6": + resolution: + { + integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==, + } + engines: { node: ">=18.18.0" } + + "@humanwhocodes/module-importer@1.0.1": + resolution: + { + integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==, + } + engines: { node: ">=12.22" } + + "@humanwhocodes/retry@0.3.1": + resolution: + { + integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==, + } + engines: { node: ">=18.18" } + + "@humanwhocodes/retry@0.4.3": + resolution: + { + integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==, + } + engines: { node: ">=18.18" } + + "@modelcontextprotocol/sdk@1.13.1": + resolution: + { + integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==, + } + engines: { node: ">=18" } + + "@nodelib/fs.scandir@2.1.5": + resolution: + { + integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==, + } + engines: { node: ">= 8" } + + "@nodelib/fs.stat@2.0.5": + resolution: + { + integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==, + } + engines: { node: ">= 8" } + + "@nodelib/fs.walk@1.2.8": + resolution: + { + integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==, + } + engines: { node: ">= 8" } + + "@opentelemetry/api@1.9.0": + resolution: + { + integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==, + } + engines: { node: ">=8.0.0" } + + "@playwright/test@1.53.1": + resolution: + { + integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==, + } + engines: { node: ">=18" } + hasBin: true + + "@types/diff-match-patch@1.0.36": + resolution: + { + integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==, + } + + "@types/estree@1.0.8": + resolution: + { + integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==, + } + + "@types/json-schema@7.0.15": + resolution: + { + integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==, + } + + "@types/node-fetch@2.6.12": + resolution: + { + integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==, + } + + "@types/node@18.19.112": + resolution: + { + integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==, + } + + "@typescript-eslint/eslint-plugin@8.35.0": + resolution: + { + integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + "@typescript-eslint/parser": ^8.35.0 + eslint: ^8.57.0 || ^9.0.0 + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/parser@8.35.0": + resolution: + { + integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + eslint: ^8.57.0 || ^9.0.0 + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/project-service@8.35.0": + resolution: + { + integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/scope-manager@8.35.0": + resolution: + { + integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@typescript-eslint/tsconfig-utils@8.35.0": + resolution: + { + integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/type-utils@8.35.0": + resolution: + { + integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + eslint: ^8.57.0 || ^9.0.0 + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/types@8.35.0": + resolution: + { + integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@typescript-eslint/typescript-estree@8.35.0": + resolution: + { + integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/utils@8.35.0": + resolution: + { + integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + eslint: ^8.57.0 || ^9.0.0 + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/visitor-keys@8.35.0": + resolution: + { + integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + abort-controller@3.0.0: + resolution: + { + integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==, + } + engines: { node: ">=6.5" } + + accepts@2.0.0: + resolution: + { + integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==, + } + engines: { node: ">= 0.6" } + + acorn-jsx@5.3.2: + resolution: + { + integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==, + } + peerDependencies: + acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 + + acorn@8.15.0: + resolution: + { + integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==, + } + engines: { node: ">=0.4.0" } + hasBin: true + + agent-base@7.1.3: + resolution: + { + integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==, + } + engines: { node: ">= 14" } + + agentkeepalive@4.6.0: + resolution: + { + integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==, + } + engines: { node: ">= 8.0.0" } + + ai@4.3.16: + resolution: + { + integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==, + } + engines: { node: ">=18" } + peerDependencies: + react: ^18 || ^19 || ^19.0.0-rc + zod: ^3.23.8 + peerDependenciesMeta: + react: + optional: true + + ajv@6.12.6: + resolution: + { + integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==, + } + + ansi-styles@4.3.0: + resolution: + { + integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==, + } + engines: { node: ">=8" } + + argparse@2.0.1: + resolution: + { + integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==, + } + + array-buffer-byte-length@1.0.2: + resolution: + { + integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==, + } + engines: { node: ">= 0.4" } + + array-includes@3.1.9: + resolution: + { + integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==, + } + engines: { node: ">= 0.4" } + + array.prototype.findlast@1.2.5: + resolution: + { + integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==, + } + engines: { node: ">= 0.4" } + + array.prototype.flat@1.3.3: + resolution: + { + integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==, + } + engines: { node: ">= 0.4" } + + array.prototype.flatmap@1.3.3: + resolution: + { + integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==, + } + engines: { node: ">= 0.4" } + + array.prototype.tosorted@1.1.4: + resolution: + { + integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==, + } + engines: { node: ">= 0.4" } + + arraybuffer.prototype.slice@1.0.4: + resolution: + { + integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==, + } + engines: { node: ">= 0.4" } + + async-function@1.0.0: + resolution: + { + integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==, + } + engines: { node: ">= 0.4" } + + asynckit@0.4.0: + resolution: + { + integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==, + } + + atomic-sleep@1.0.0: + resolution: + { + integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==, + } + engines: { node: ">=8.0.0" } + + available-typed-arrays@1.0.7: + resolution: + { + integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==, + } + engines: { node: ">= 0.4" } + + balanced-match@1.0.2: + resolution: + { + integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==, + } + + base64-js@1.5.1: + resolution: + { + integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==, + } + + bignumber.js@9.3.0: + resolution: + { + integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==, + } + + body-parser@2.2.0: + resolution: + { + integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==, + } + engines: { node: ">=18" } + + brace-expansion@1.1.12: + resolution: + { + integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==, + } + + brace-expansion@2.0.2: + resolution: + { + integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==, + } + + braces@3.0.3: + resolution: + { + integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==, + } + engines: { node: ">=8" } + + buffer-equal-constant-time@1.0.1: + resolution: + { + integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==, + } + + bytes@3.1.2: + resolution: + { + integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==, + } + engines: { node: ">= 0.8" } + + call-bind-apply-helpers@1.0.2: + resolution: + { + integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==, + } + engines: { node: ">= 0.4" } + + call-bind@1.0.8: + resolution: + { + integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==, + } + engines: { node: ">= 0.4" } + + call-bound@1.0.4: + resolution: + { + integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==, + } + engines: { node: ">= 0.4" } + + callsites@3.1.0: + resolution: + { + integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==, + } + engines: { node: ">=6" } + + chalk@4.1.2: + resolution: + { + integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==, + } + engines: { node: ">=10" } + + chalk@5.4.1: + resolution: + { + integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==, + } + engines: { node: ^12.17.0 || ^14.13 || >=16.0.0 } + + color-convert@2.0.1: + resolution: + { + integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==, + } + engines: { node: ">=7.0.0" } + + color-name@1.1.4: + resolution: + { + integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==, + } + + colorette@2.0.20: + resolution: + { + integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==, + } + + combined-stream@1.0.8: + resolution: + { + integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==, + } + engines: { node: ">= 0.8" } + + commander@14.0.0: + resolution: + { + integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==, + } + engines: { node: ">=20" } + + concat-map@0.0.1: + resolution: + { + integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==, + } + + content-disposition@1.0.0: + resolution: + { + integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==, + } + engines: { node: ">= 0.6" } + + content-type@1.0.5: + resolution: + { + integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==, + } + engines: { node: ">= 0.6" } + + cookie-signature@1.2.2: + resolution: + { + integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==, + } + engines: { node: ">=6.6.0" } + + cookie@0.7.2: + resolution: + { + integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==, + } + engines: { node: ">= 0.6" } + + cors@2.8.5: + resolution: + { + integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==, + } + engines: { node: ">= 0.10" } + + cross-spawn@7.0.6: + resolution: + { + integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==, + } + engines: { node: ">= 8" } + + data-view-buffer@1.0.2: + resolution: + { + integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==, + } + engines: { node: ">= 0.4" } + + data-view-byte-length@1.0.2: + resolution: + { + integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==, + } + engines: { node: ">= 0.4" } + + data-view-byte-offset@1.0.1: + resolution: + { + integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==, + } + engines: { node: ">= 0.4" } + + dateformat@4.6.3: + resolution: + { + integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==, + } + + debug@4.4.1: + resolution: + { + integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==, + } + engines: { node: ">=6.0" } + peerDependencies: + supports-color: "*" + peerDependenciesMeta: + supports-color: + optional: true + + deep-is@0.1.4: + resolution: + { + integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==, + } + + deepmerge@4.3.1: + resolution: + { + integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==, + } + engines: { node: ">=0.10.0" } + + define-data-property@1.1.4: + resolution: + { + integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==, + } + engines: { node: ">= 0.4" } + + define-properties@1.2.1: + resolution: + { + integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==, + } + engines: { node: ">= 0.4" } + + delayed-stream@1.0.0: + resolution: + { + integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==, + } + engines: { node: ">=0.4.0" } + + depd@2.0.0: + resolution: + { + integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==, + } + engines: { node: ">= 0.8" } + + dequal@2.0.3: + resolution: + { + integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==, + } + engines: { node: ">=6" } + + devtools-protocol@0.0.1464554: + resolution: + { + integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==, + } + + diff-match-patch@1.0.5: + resolution: + { + integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==, + } + + doctrine@2.1.0: + resolution: + { + integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==, + } + engines: { node: ">=0.10.0" } + + dotenv@16.5.0: + resolution: + { + integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==, + } + engines: { node: ">=12" } + + dunder-proto@1.0.1: + resolution: + { + integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==, + } + engines: { node: ">= 0.4" } + + ecdsa-sig-formatter@1.0.11: + resolution: + { + integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==, + } + + ee-first@1.1.1: + resolution: + { + integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==, + } + + encodeurl@2.0.0: + resolution: + { + integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==, + } + engines: { node: ">= 0.8" } + + end-of-stream@1.4.5: + resolution: + { + integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==, + } + + es-abstract@1.24.0: + resolution: + { + integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==, + } + engines: { node: ">= 0.4" } + + es-define-property@1.0.1: + resolution: + { + integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==, + } + engines: { node: ">= 0.4" } + + es-errors@1.3.0: + resolution: + { + integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==, + } + engines: { node: ">= 0.4" } + + es-iterator-helpers@1.2.1: + resolution: + { + integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==, + } + engines: { node: ">= 0.4" } + + es-object-atoms@1.1.1: + resolution: + { + integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==, + } + engines: { node: ">= 0.4" } + + es-set-tostringtag@2.1.0: + resolution: + { + integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==, + } + engines: { node: ">= 0.4" } + + es-shim-unscopables@1.1.0: + resolution: + { + integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==, + } + engines: { node: ">= 0.4" } + + es-to-primitive@1.3.0: + resolution: + { + integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==, + } + engines: { node: ">= 0.4" } + + escape-html@1.0.3: + resolution: + { + integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==, + } + + escape-string-regexp@4.0.0: + resolution: + { + integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==, + } + engines: { node: ">=10" } + + eslint-plugin-react@7.37.5: + resolution: + { + integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==, + } + engines: { node: ">=4" } + peerDependencies: + eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 + + eslint-scope@8.4.0: + resolution: + { + integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + eslint-visitor-keys@3.4.3: + resolution: + { + integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==, + } + engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } + + eslint-visitor-keys@4.2.1: + resolution: + { + integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + eslint@9.29.0: + resolution: + { + integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + hasBin: true + peerDependencies: + jiti: "*" + peerDependenciesMeta: + jiti: + optional: true + + espree@10.4.0: + resolution: + { + integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + esquery@1.6.0: + resolution: + { + integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==, + } + engines: { node: ">=0.10" } + + esrecurse@4.3.0: + resolution: + { + integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==, + } + engines: { node: ">=4.0" } + + estraverse@5.3.0: + resolution: + { + integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==, + } + engines: { node: ">=4.0" } + + esutils@2.0.3: + resolution: + { + integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==, + } + engines: { node: ">=0.10.0" } + + etag@1.8.1: + resolution: + { + integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==, + } + engines: { node: ">= 0.6" } + + event-target-shim@5.0.1: + resolution: + { + integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==, + } + engines: { node: ">=6" } + + eventsource-parser@3.0.3: + resolution: + { + integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==, + } + engines: { node: ">=20.0.0" } + + eventsource@3.0.7: + resolution: + { + integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==, + } + engines: { node: ">=18.0.0" } + + express-rate-limit@7.5.1: + resolution: + { + integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==, + } + engines: { node: ">= 16" } + peerDependencies: + express: ">= 4.11" + + express@5.1.0: + resolution: + { + integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==, + } + engines: { node: ">= 18" } + + extend@3.0.2: + resolution: + { + integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==, + } + + fast-copy@3.0.2: + resolution: + { + integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==, + } + + fast-deep-equal@3.1.3: + resolution: + { + integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==, + } + + fast-glob@3.3.3: + resolution: + { + integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==, + } + engines: { node: ">=8.6.0" } + + fast-json-stable-stringify@2.1.0: + resolution: + { + integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==, + } + + fast-levenshtein@2.0.6: + resolution: + { + integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==, + } + + fast-redact@3.5.0: + resolution: + { + integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==, + } + engines: { node: ">=6" } + + fast-safe-stringify@2.1.1: + resolution: + { + integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==, + } + + fastq@1.19.1: + resolution: + { + integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==, + } + + fetch-cookie@3.1.0: + resolution: + { + integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==, + } + + file-entry-cache@8.0.0: + resolution: + { + integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==, + } + engines: { node: ">=16.0.0" } + + fill-range@7.1.1: + resolution: + { + integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==, + } + engines: { node: ">=8" } + + finalhandler@2.1.0: + resolution: + { + integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==, + } + engines: { node: ">= 0.8" } + + find-up@5.0.0: + resolution: + { + integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==, + } + engines: { node: ">=10" } + + flat-cache@4.0.1: + resolution: + { + integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==, + } + engines: { node: ">=16" } + + flatted@3.3.3: + resolution: + { + integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==, + } + + for-each@0.3.5: + resolution: + { + integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==, + } + engines: { node: ">= 0.4" } + + form-data-encoder@1.7.2: + resolution: + { + integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==, + } + + form-data@4.0.3: + resolution: + { + integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==, + } + engines: { node: ">= 6" } + + formdata-node@4.4.1: + resolution: + { + integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==, + } + engines: { node: ">= 12.20" } + + forwarded@0.2.0: + resolution: + { + integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==, + } + engines: { node: ">= 0.6" } + + fresh@2.0.0: + resolution: + { + integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==, + } + engines: { node: ">= 0.8" } + + fs.realpath@1.0.0: + resolution: + { + integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==, + } + + fsevents@2.3.2: + resolution: + { + integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==, + } + engines: { node: ^8.16.0 || ^10.6.0 || >=11.0.0 } + os: [darwin] + + function-bind@1.1.2: + resolution: + { + integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==, + } + + function.prototype.name@1.1.8: + resolution: + { + integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==, + } + engines: { node: ">= 0.4" } + + functions-have-names@1.2.3: + resolution: + { + integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==, + } + + gaxios@6.7.1: + resolution: + { + integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==, + } + engines: { node: ">=14" } + + gcp-metadata@6.1.1: + resolution: + { + integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==, + } + engines: { node: ">=14" } + + get-intrinsic@1.3.0: + resolution: + { + integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==, + } + engines: { node: ">= 0.4" } + + get-proto@1.0.1: + resolution: + { + integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==, + } + engines: { node: ">= 0.4" } + + get-symbol-description@1.1.0: + resolution: + { + integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==, + } + engines: { node: ">= 0.4" } + + glob-parent@5.1.2: + resolution: + { + integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==, + } + engines: { node: ">= 6" } + + glob-parent@6.0.2: + resolution: + { + integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==, + } + engines: { node: ">=10.13.0" } + + glob@7.2.3: + resolution: + { + integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==, + } + deprecated: Glob versions prior to v9 are no longer supported + + globals@14.0.0: + resolution: + { + integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==, + } + engines: { node: ">=18" } + + globals@16.2.0: + resolution: + { + integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==, + } + engines: { node: ">=18" } + + globalthis@1.0.4: + resolution: + { + integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==, + } + engines: { node: ">= 0.4" } + + google-auth-library@9.15.1: + resolution: + { + integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==, + } + engines: { node: ">=14" } + + google-logging-utils@0.0.2: + resolution: + { + integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==, + } + engines: { node: ">=14" } + + gopd@1.2.0: + resolution: + { + integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==, + } + engines: { node: ">= 0.4" } + + graphemer@1.4.0: + resolution: + { + integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==, + } + + gtoken@7.1.0: + resolution: + { + integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==, + } + engines: { node: ">=14.0.0" } + + has-bigints@1.1.0: + resolution: + { + integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==, + } + engines: { node: ">= 0.4" } + + has-flag@4.0.0: + resolution: + { + integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==, + } + engines: { node: ">=8" } + + has-property-descriptors@1.0.2: + resolution: + { + integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==, + } + + has-proto@1.2.0: + resolution: + { + integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==, + } + engines: { node: ">= 0.4" } + + has-symbols@1.1.0: + resolution: + { + integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==, + } + engines: { node: ">= 0.4" } + + has-tostringtag@1.0.2: + resolution: + { + integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==, + } + engines: { node: ">= 0.4" } + + hasown@2.0.2: + resolution: + { + integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==, + } + engines: { node: ">= 0.4" } + + help-me@5.0.0: + resolution: + { + integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==, + } + + http-errors@2.0.0: + resolution: + { + integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==, + } + engines: { node: ">= 0.8" } + + https-proxy-agent@7.0.6: + resolution: + { + integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==, + } + engines: { node: ">= 14" } + + humanize-ms@1.2.1: + resolution: + { + integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==, + } + + iconv-lite@0.6.3: + resolution: + { + integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==, + } + engines: { node: ">=0.10.0" } + + ignore@5.3.2: + resolution: + { + integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==, + } + engines: { node: ">= 4" } + + ignore@7.0.5: + resolution: + { + integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==, + } + engines: { node: ">= 4" } + + import-fresh@3.3.1: + resolution: + { + integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==, + } + engines: { node: ">=6" } + + imurmurhash@0.1.4: + resolution: + { + integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==, + } + engines: { node: ">=0.8.19" } + + inflight@1.0.6: + resolution: + { + integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==, + } + deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. + + inherits@2.0.4: + resolution: + { + integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==, + } + + internal-slot@1.1.0: + resolution: + { + integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==, + } + engines: { node: ">= 0.4" } + + interpret@1.4.0: + resolution: + { + integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==, + } + engines: { node: ">= 0.10" } + + ipaddr.js@1.9.1: + resolution: + { + integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==, + } + engines: { node: ">= 0.10" } + + is-array-buffer@3.0.5: + resolution: + { + integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==, + } + engines: { node: ">= 0.4" } + + is-async-function@2.1.1: + resolution: + { + integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==, + } + engines: { node: ">= 0.4" } + + is-bigint@1.1.0: + resolution: + { + integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==, + } + engines: { node: ">= 0.4" } + + is-boolean-object@1.2.2: + resolution: + { + integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==, + } + engines: { node: ">= 0.4" } + + is-callable@1.2.7: + resolution: + { + integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==, + } + engines: { node: ">= 0.4" } + + is-core-module@2.16.1: + resolution: + { + integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==, + } + engines: { node: ">= 0.4" } + + is-data-view@1.0.2: + resolution: + { + integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==, + } + engines: { node: ">= 0.4" } + + is-date-object@1.1.0: + resolution: + { + integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==, + } + engines: { node: ">= 0.4" } + + is-extglob@2.1.1: + resolution: + { + integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==, + } + engines: { node: ">=0.10.0" } + + is-finalizationregistry@1.1.1: + resolution: + { + integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==, + } + engines: { node: ">= 0.4" } + + is-generator-function@1.1.0: + resolution: + { + integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==, + } + engines: { node: ">= 0.4" } + + is-glob@4.0.3: + resolution: + { + integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==, + } + engines: { node: ">=0.10.0" } + + is-map@2.0.3: + resolution: + { + integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==, + } + engines: { node: ">= 0.4" } + + is-negative-zero@2.0.3: + resolution: + { + integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==, + } + engines: { node: ">= 0.4" } + + is-number-object@1.1.1: + resolution: + { + integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==, + } + engines: { node: ">= 0.4" } + + is-number@7.0.0: + resolution: + { + integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==, + } + engines: { node: ">=0.12.0" } + + is-promise@4.0.0: + resolution: + { + integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==, + } + + is-regex@1.2.1: + resolution: + { + integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==, + } + engines: { node: ">= 0.4" } + + is-set@2.0.3: + resolution: + { + integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==, + } + engines: { node: ">= 0.4" } + + is-shared-array-buffer@1.0.4: + resolution: + { + integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==, + } + engines: { node: ">= 0.4" } + + is-stream@2.0.1: + resolution: + { + integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==, + } + engines: { node: ">=8" } + + is-string@1.1.1: + resolution: + { + integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==, + } + engines: { node: ">= 0.4" } + + is-symbol@1.1.1: + resolution: + { + integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==, + } + engines: { node: ">= 0.4" } + + is-typed-array@1.1.15: + resolution: + { + integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==, + } + engines: { node: ">= 0.4" } + + is-weakmap@2.0.2: + resolution: + { + integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==, + } + engines: { node: ">= 0.4" } + + is-weakref@1.1.1: + resolution: + { + integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==, + } + engines: { node: ">= 0.4" } + + is-weakset@2.0.4: + resolution: + { + integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==, + } + engines: { node: ">= 0.4" } + + isarray@2.0.5: + resolution: + { + integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==, + } + + isexe@2.0.0: + resolution: + { + integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==, + } + + iterator.prototype@1.1.5: + resolution: + { + integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==, + } + engines: { node: ">= 0.4" } + + joycon@3.1.1: + resolution: + { + integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==, + } + engines: { node: ">=10" } + + js-tokens@4.0.0: + resolution: + { + integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==, + } + + js-yaml@4.1.0: + resolution: + { + integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==, + } + hasBin: true + + json-bigint@1.0.0: + resolution: + { + integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==, + } + + json-buffer@3.0.1: + resolution: + { + integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==, + } + + json-schema-traverse@0.4.1: + resolution: + { + integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==, + } + + json-schema@0.4.0: + resolution: + { + integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==, + } + + json-stable-stringify-without-jsonify@1.0.1: + resolution: + { + integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==, + } + + jsondiffpatch@0.6.0: + resolution: + { + integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==, + } + engines: { node: ^18.0.0 || >=20.0.0 } + hasBin: true + + jsx-ast-utils@3.3.5: + resolution: + { + integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==, + } + engines: { node: ">=4.0" } + + jwa@2.0.1: + resolution: + { + integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==, + } + + jws@4.0.0: + resolution: + { + integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==, + } + + keyv@4.5.4: + resolution: + { + integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==, + } + + levn@0.4.1: + resolution: + { + integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==, + } + engines: { node: ">= 0.8.0" } + + locate-path@6.0.0: + resolution: + { + integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==, + } + engines: { node: ">=10" } + + lodash.merge@4.6.2: + resolution: + { + integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==, + } + + loose-envify@1.4.0: + resolution: + { + integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==, + } + hasBin: true + + math-intrinsics@1.1.0: + resolution: + { + integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==, + } + engines: { node: ">= 0.4" } + + media-typer@1.1.0: + resolution: + { + integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==, + } + engines: { node: ">= 0.8" } + + merge-descriptors@2.0.0: + resolution: + { + integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==, + } + engines: { node: ">=18" } + + merge2@1.4.1: + resolution: + { + integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==, + } + engines: { node: ">= 8" } + + micromatch@4.0.8: + resolution: + { + integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==, + } + engines: { node: ">=8.6" } + + mime-db@1.52.0: + resolution: + { + integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==, + } + engines: { node: ">= 0.6" } + + mime-db@1.54.0: + resolution: + { + integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==, + } + engines: { node: ">= 0.6" } + + mime-types@2.1.35: + resolution: + { + integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==, + } + engines: { node: ">= 0.6" } + + mime-types@3.0.1: + resolution: + { + integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==, + } + engines: { node: ">= 0.6" } + + minimatch@3.1.2: + resolution: + { + integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==, + } + + minimatch@9.0.5: + resolution: + { + integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==, + } + engines: { node: ">=16 || 14 >=14.17" } + + minimist@1.2.8: + resolution: + { + integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==, + } + + ms@2.1.3: + resolution: + { + integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, + } + + nanoid@3.3.11: + resolution: + { + integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==, + } + engines: { node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1 } + hasBin: true + + natural-compare@1.4.0: + resolution: + { + integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==, + } + + negotiator@1.0.0: + resolution: + { + integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==, + } + engines: { node: ">= 0.6" } + + node-domexception@1.0.0: + resolution: + { + integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==, + } + engines: { node: ">=10.5.0" } + + node-fetch@2.7.0: + resolution: + { + integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==, + } + engines: { node: 4.x || >=6.0.0 } + peerDependencies: + encoding: ^0.1.0 + peerDependenciesMeta: + encoding: + optional: true + + object-assign@4.1.1: + resolution: + { + integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==, + } + engines: { node: ">=0.10.0" } + + object-inspect@1.13.4: + resolution: + { + integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==, + } + engines: { node: ">= 0.4" } + + object-keys@1.1.1: + resolution: + { + integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==, + } + engines: { node: ">= 0.4" } + + object.assign@4.1.7: + resolution: + { + integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==, + } + engines: { node: ">= 0.4" } + + object.entries@1.1.9: + resolution: + { + integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==, + } + engines: { node: ">= 0.4" } + + object.fromentries@2.0.8: + resolution: + { + integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==, + } + engines: { node: ">= 0.4" } + + object.values@1.2.1: + resolution: + { + integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==, + } + engines: { node: ">= 0.4" } + + ollama-ai-provider@1.2.0: + resolution: + { + integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==, + } + engines: { node: ">=18" } + peerDependencies: + zod: ^3.0.0 + peerDependenciesMeta: + zod: + optional: true + + on-exit-leak-free@2.1.2: + resolution: + { + integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==, + } + engines: { node: ">=14.0.0" } + + on-finished@2.4.1: + resolution: + { + integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==, + } + engines: { node: ">= 0.8" } + + once@1.4.0: + resolution: + { + integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==, + } + + openai@4.104.0: + resolution: + { + integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==, + } + hasBin: true + peerDependencies: + ws: ^8.18.0 + zod: ^3.23.8 + peerDependenciesMeta: + ws: + optional: true + zod: + optional: true + + optionator@0.9.4: + resolution: + { + integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==, + } + engines: { node: ">= 0.8.0" } + + own-keys@1.0.1: + resolution: + { + integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==, + } + engines: { node: ">= 0.4" } + + p-limit@3.1.0: + resolution: + { + integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==, + } + engines: { node: ">=10" } + + p-locate@5.0.0: + resolution: + { + integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==, + } + engines: { node: ">=10" } + + parent-module@1.0.1: + resolution: + { + integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==, + } + engines: { node: ">=6" } + + parseurl@1.3.3: + resolution: + { + integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==, + } + engines: { node: ">= 0.8" } + + partial-json@0.1.7: + resolution: + { + integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==, + } + + path-exists@4.0.0: + resolution: + { + integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==, + } + engines: { node: ">=8" } + + path-is-absolute@1.0.1: + resolution: + { + integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==, + } + engines: { node: ">=0.10.0" } + + path-key@3.1.1: + resolution: + { + integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==, + } + engines: { node: ">=8" } + + path-parse@1.0.7: + resolution: + { + integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==, + } + + path-to-regexp@8.2.0: + resolution: + { + integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==, + } + engines: { node: ">=16" } + + picomatch@2.3.1: + resolution: + { + integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==, + } + engines: { node: ">=8.6" } + + pino-abstract-transport@2.0.0: + resolution: + { + integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==, + } + + pino-pretty@13.0.0: + resolution: + { + integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==, + } + hasBin: true + + pino-std-serializers@7.0.0: + resolution: + { + integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==, + } + + pino@9.7.0: + resolution: + { + integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==, + } + hasBin: true + + pkce-challenge@5.0.0: + resolution: + { + integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==, + } + engines: { node: ">=16.20.0" } + + playwright-core@1.53.1: + resolution: + { + integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==, + } + engines: { node: ">=18" } + hasBin: true + + playwright@1.53.1: + resolution: + { + integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==, + } + engines: { node: ">=18" } + hasBin: true + + possible-typed-array-names@1.1.0: + resolution: + { + integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==, + } + engines: { node: ">= 0.4" } + + prelude-ls@1.2.1: + resolution: + { + integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==, + } + engines: { node: ">= 0.8.0" } + + prettier@3.6.1: + resolution: + { + integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==, + } + engines: { node: ">=14" } + hasBin: true + + process-warning@5.0.0: + resolution: + { + integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==, + } + + prop-types@15.8.1: + resolution: + { + integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==, + } + + proxy-addr@2.0.7: + resolution: + { + integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==, + } + engines: { node: ">= 0.10" } + + pump@3.0.3: + resolution: + { + integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==, + } + + punycode@2.3.1: + resolution: + { + integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==, + } + engines: { node: ">=6" } + + qs@6.14.0: + resolution: + { + integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==, + } + engines: { node: ">=0.6" } + + queue-microtask@1.2.3: + resolution: + { + integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==, + } + + quick-format-unescaped@4.0.4: + resolution: + { + integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==, + } + + range-parser@1.2.1: + resolution: + { + integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==, + } + engines: { node: ">= 0.6" } + + raw-body@3.0.0: + resolution: + { + integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==, + } + engines: { node: ">= 0.8" } + + react-is@16.13.1: + resolution: + { + integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==, + } + + react@19.1.0: + resolution: + { + integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==, + } + engines: { node: ">=0.10.0" } + + real-require@0.2.0: + resolution: + { + integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==, + } + engines: { node: ">= 12.13.0" } + + rechoir@0.6.2: + resolution: + { + integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==, + } + engines: { node: ">= 0.10" } + + reflect.getprototypeof@1.0.10: + resolution: + { + integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==, + } + engines: { node: ">= 0.4" } + + regexp.prototype.flags@1.5.4: + resolution: + { + integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==, + } + engines: { node: ">= 0.4" } + + resolve-from@4.0.0: + resolution: + { + integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==, + } + engines: { node: ">=4" } + + resolve@1.22.10: + resolution: + { + integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==, + } + engines: { node: ">= 0.4" } + hasBin: true + + resolve@2.0.0-next.5: + resolution: + { + integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==, + } + hasBin: true + + reusify@1.1.0: + resolution: + { + integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==, + } + engines: { iojs: ">=1.0.0", node: ">=0.10.0" } + + router@2.2.0: + resolution: + { + integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==, + } + engines: { node: ">= 18" } + + run-parallel@1.2.0: + resolution: + { + integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==, + } + + safe-array-concat@1.1.3: + resolution: + { + integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==, + } + engines: { node: ">=0.4" } + + safe-buffer@5.2.1: + resolution: + { + integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==, + } + + safe-push-apply@1.0.0: + resolution: + { + integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==, + } + engines: { node: ">= 0.4" } + + safe-regex-test@1.1.0: + resolution: + { + integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==, + } + engines: { node: ">= 0.4" } + + safe-stable-stringify@2.5.0: + resolution: + { + integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==, + } + engines: { node: ">=10" } + + safer-buffer@2.1.2: + resolution: + { + integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==, + } + + secure-json-parse@2.7.0: + resolution: + { + integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==, + } + + semver@6.3.1: + resolution: + { + integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==, + } + hasBin: true + + semver@7.7.2: + resolution: + { + integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==, + } + engines: { node: ">=10" } + hasBin: true + + send@1.2.0: + resolution: + { + integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==, + } + engines: { node: ">= 18" } + + serve-static@2.2.0: + resolution: + { + integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==, + } + engines: { node: ">= 18" } + + set-cookie-parser@2.7.1: + resolution: + { + integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==, + } + + set-function-length@1.2.2: + resolution: + { + integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==, + } + engines: { node: ">= 0.4" } + + set-function-name@2.0.2: + resolution: + { + integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==, + } + engines: { node: ">= 0.4" } + + set-proto@1.0.0: + resolution: + { + integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==, + } + engines: { node: ">= 0.4" } + + setprototypeof@1.2.0: + resolution: + { + integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==, + } + + shebang-command@2.0.0: + resolution: + { + integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==, + } + engines: { node: ">=8" } + + shebang-regex@3.0.0: + resolution: + { + integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==, + } + engines: { node: ">=8" } + + shelljs@0.8.5: + resolution: + { + integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==, + } + engines: { node: ">=4" } + hasBin: true + + shx@0.3.4: + resolution: + { + integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==, + } + engines: { node: ">=6" } + hasBin: true + + side-channel-list@1.0.0: + resolution: + { + integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==, + } + engines: { node: ">= 0.4" } + + side-channel-map@1.0.1: + resolution: + { + integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==, + } + engines: { node: ">= 0.4" } + + side-channel-weakmap@1.0.2: + resolution: + { + integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==, + } + engines: { node: ">= 0.4" } + + side-channel@1.1.0: + resolution: + { + integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==, + } + engines: { node: ">= 0.4" } + + sonic-boom@4.2.0: + resolution: + { + integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==, + } + + split2@4.2.0: + resolution: + { + integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==, + } + engines: { node: ">= 10.x" } + + statuses@2.0.1: + resolution: + { + integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==, + } + engines: { node: ">= 0.8" } + + statuses@2.0.2: + resolution: + { + integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==, + } + engines: { node: ">= 0.8" } + + stop-iteration-iterator@1.1.0: + resolution: + { + integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==, + } + engines: { node: ">= 0.4" } + + string.prototype.matchall@4.0.12: + resolution: + { + integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==, + } + engines: { node: ">= 0.4" } + + string.prototype.repeat@1.0.0: + resolution: + { + integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==, + } + + string.prototype.trim@1.2.10: + resolution: + { + integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==, + } + engines: { node: ">= 0.4" } + + string.prototype.trimend@1.0.9: + resolution: + { + integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==, + } + engines: { node: ">= 0.4" } + + string.prototype.trimstart@1.0.8: + resolution: + { + integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==, + } + engines: { node: ">= 0.4" } + + strip-json-comments@3.1.1: + resolution: + { + integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==, + } + engines: { node: ">=8" } + + supports-color@7.2.0: + resolution: + { + integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==, + } + engines: { node: ">=8" } + + supports-preserve-symlinks-flag@1.0.0: + resolution: + { + integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==, + } + engines: { node: ">= 0.4" } + + swr@2.3.3: + resolution: + { + integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==, + } + peerDependencies: + react: ^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 + + thread-stream@3.1.0: + resolution: + { + integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==, + } + + throttleit@2.1.0: + resolution: + { + integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==, + } + engines: { node: ">=18" } + + tldts-core@6.1.86: + resolution: + { + integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==, + } + + tldts@6.1.86: + resolution: + { + integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==, + } + hasBin: true + + to-regex-range@5.0.1: + resolution: + { + integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==, + } + engines: { node: ">=8.0" } + + toidentifier@1.0.1: + resolution: + { + integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==, + } + engines: { node: ">=0.6" } + + tough-cookie@5.1.2: + resolution: + { + integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==, + } + engines: { node: ">=16" } + + tr46@0.0.3: + resolution: + { + integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==, + } + + ts-api-utils@2.1.0: + resolution: + { + integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==, + } + engines: { node: ">=18.12" } + peerDependencies: + typescript: ">=4.8.4" + + type-check@0.4.0: + resolution: + { + integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==, + } + engines: { node: ">= 0.8.0" } + + type-is@2.0.1: + resolution: + { + integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==, + } + engines: { node: ">= 0.6" } + + typed-array-buffer@1.0.3: + resolution: + { + integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==, + } + engines: { node: ">= 0.4" } + + typed-array-byte-length@1.0.3: + resolution: + { + integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==, + } + engines: { node: ">= 0.4" } + + typed-array-byte-offset@1.0.4: + resolution: + { + integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==, + } + engines: { node: ">= 0.4" } + + typed-array-length@1.0.7: + resolution: + { + integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==, + } + engines: { node: ">= 0.4" } + + typescript-eslint@8.35.0: + resolution: + { + integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + peerDependencies: + eslint: ^8.57.0 || ^9.0.0 + typescript: ">=4.8.4 <5.9.0" + + typescript@5.8.3: + resolution: + { + integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==, + } + engines: { node: ">=14.17" } + hasBin: true + + unbox-primitive@1.1.0: + resolution: + { + integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==, + } + engines: { node: ">= 0.4" } + + undici-types@5.26.5: + resolution: + { + integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==, + } + + unpipe@1.0.0: + resolution: + { + integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==, + } + engines: { node: ">= 0.8" } + + uri-js@4.4.1: + resolution: + { + integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==, + } + + use-sync-external-store@1.5.0: + resolution: + { + integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==, + } + peerDependencies: + react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 + + uuid@9.0.1: + resolution: + { + integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==, + } + hasBin: true + + vary@1.1.2: + resolution: + { + integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==, + } + engines: { node: ">= 0.8" } + + web-streams-polyfill@4.0.0-beta.3: + resolution: + { + integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==, + } + engines: { node: ">= 14" } + + webidl-conversions@3.0.1: + resolution: + { + integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==, + } + + whatwg-url@5.0.0: + resolution: + { + integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==, + } + + which-boxed-primitive@1.1.1: + resolution: + { + integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==, + } + engines: { node: ">= 0.4" } + + which-builtin-type@1.2.1: + resolution: + { + integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==, + } + engines: { node: ">= 0.4" } + + which-collection@1.0.2: + resolution: + { + integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==, + } + engines: { node: ">= 0.4" } + + which-typed-array@1.1.19: + resolution: + { + integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==, + } + engines: { node: ">= 0.4" } + + which@2.0.2: + resolution: + { + integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==, + } + engines: { node: ">= 8" } + hasBin: true + + word-wrap@1.2.5: + resolution: + { + integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==, + } + engines: { node: ">=0.10.0" } + + wrappy@1.0.2: + resolution: + { + integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==, + } + + ws@8.18.2: + resolution: + { + integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==, + } + engines: { node: ">=10.0.0" } + peerDependencies: + bufferutil: ^4.0.1 + utf-8-validate: ">=5.0.2" + peerDependenciesMeta: + bufferutil: + optional: true + utf-8-validate: + optional: true + + yocto-queue@0.1.0: + resolution: + { + integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==, + } + engines: { node: ">=10" } + + zod-to-json-schema@3.24.6: + resolution: + { + integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==, + } + peerDependencies: + zod: ^3.24.1 + + zod@3.25.67: + resolution: + { + integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==, + } + +snapshots: + "@ai-sdk/anthropic@1.2.12(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/azure@1.3.23(zod@3.25.67)": + dependencies: + "@ai-sdk/openai": 1.3.22(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/cerebras@0.2.14(zod@3.25.67)": + dependencies: + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/deepseek@0.2.14(zod@3.25.67)": + dependencies: + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/google@1.2.19(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/groq@1.2.9(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/mistral@1.2.8(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/openai@1.3.22(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/perplexity@1.1.9(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/provider-utils@2.2.8(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + nanoid: 3.3.11 + secure-json-parse: 2.7.0 + zod: 3.25.67 + + "@ai-sdk/provider@1.1.3": + dependencies: + json-schema: 0.4.0 + + "@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)": + dependencies: + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) + react: 19.1.0 + swr: 2.3.3(react@19.1.0) + throttleit: 2.1.0 + optionalDependencies: + zod: 3.25.67 + + "@ai-sdk/togetherai@0.2.14(zod@3.25.67)": + dependencies: + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@ai-sdk/ui-utils@1.2.11(zod@3.25.67)": + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + zod-to-json-schema: 3.24.6(zod@3.25.67) + + "@ai-sdk/xai@1.2.16(zod@3.25.67)": + dependencies: + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + zod: 3.25.67 + optional: true + + "@anthropic-ai/sdk@0.39.0": + dependencies: + "@types/node": 18.19.112 + "@types/node-fetch": 2.6.12 + abort-controller: 3.0.0 + agentkeepalive: 4.6.0 + form-data-encoder: 1.7.2 + formdata-node: 4.4.1 + node-fetch: 2.7.0 + transitivePeerDependencies: + - encoding + + "@browserbasehq/sdk@2.6.0": + dependencies: + "@types/node": 18.19.112 + "@types/node-fetch": 2.6.12 + abort-controller: 3.0.0 + agentkeepalive: 4.6.0 + form-data-encoder: 1.7.2 + formdata-node: 4.4.1 + node-fetch: 2.7.0 + transitivePeerDependencies: + - encoding + + "@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)": + dependencies: + "@anthropic-ai/sdk": 0.39.0 + "@browserbasehq/sdk": 2.6.0 + "@google/genai": 0.8.0 + ai: 4.3.16(react@19.1.0)(zod@3.25.67) + deepmerge: 4.3.1 + devtools-protocol: 0.0.1464554 + dotenv: 16.5.0 + fetch-cookie: 3.1.0 + openai: 4.104.0(ws@8.18.2)(zod@3.25.67) + pino: 9.7.0 + pino-pretty: 13.0.0 + playwright: 1.53.1 + ws: 8.18.2 + zod: 3.25.67 + zod-to-json-schema: 3.24.6(zod@3.25.67) + optionalDependencies: + "@ai-sdk/anthropic": 1.2.12(zod@3.25.67) + "@ai-sdk/azure": 1.3.23(zod@3.25.67) + "@ai-sdk/cerebras": 0.2.14(zod@3.25.67) + "@ai-sdk/deepseek": 0.2.14(zod@3.25.67) + "@ai-sdk/google": 1.2.19(zod@3.25.67) + "@ai-sdk/groq": 1.2.9(zod@3.25.67) + "@ai-sdk/mistral": 1.2.8(zod@3.25.67) + "@ai-sdk/openai": 1.3.22(zod@3.25.67) + "@ai-sdk/perplexity": 1.1.9(zod@3.25.67) + "@ai-sdk/togetherai": 0.2.14(zod@3.25.67) + "@ai-sdk/xai": 1.2.16(zod@3.25.67) + ollama-ai-provider: 1.2.0(zod@3.25.67) + transitivePeerDependencies: + - bufferutil + - encoding + - react + - supports-color + - utf-8-validate + + "@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)": + dependencies: + eslint: 9.29.0 + eslint-visitor-keys: 3.4.3 + + "@eslint-community/regexpp@4.12.1": {} + + "@eslint/config-array@0.20.1": + dependencies: + "@eslint/object-schema": 2.1.6 + debug: 4.4.1 + minimatch: 3.1.2 + transitivePeerDependencies: + - supports-color + + "@eslint/config-helpers@0.2.3": {} + + "@eslint/core@0.14.0": + dependencies: + "@types/json-schema": 7.0.15 + + "@eslint/core@0.15.1": + dependencies: + "@types/json-schema": 7.0.15 + + "@eslint/eslintrc@3.3.1": + dependencies: + ajv: 6.12.6 + debug: 4.4.1 + espree: 10.4.0 + globals: 14.0.0 + ignore: 5.3.2 + import-fresh: 3.3.1 + js-yaml: 4.1.0 + minimatch: 3.1.2 + strip-json-comments: 3.1.1 + transitivePeerDependencies: + - supports-color + + "@eslint/js@9.29.0": {} + + "@eslint/object-schema@2.1.6": {} + + "@eslint/plugin-kit@0.3.3": + dependencies: + "@eslint/core": 0.15.1 + levn: 0.4.1 + + "@google/genai@0.8.0": + dependencies: + google-auth-library: 9.15.1 + ws: 8.18.2 + transitivePeerDependencies: + - bufferutil + - encoding + - supports-color + - utf-8-validate + + "@humanfs/core@0.19.1": {} + + "@humanfs/node@0.16.6": + dependencies: + "@humanfs/core": 0.19.1 + "@humanwhocodes/retry": 0.3.1 + + "@humanwhocodes/module-importer@1.0.1": {} + + "@humanwhocodes/retry@0.3.1": {} + + "@humanwhocodes/retry@0.4.3": {} + + "@modelcontextprotocol/sdk@1.13.1": + dependencies: + ajv: 6.12.6 + content-type: 1.0.5 + cors: 2.8.5 + cross-spawn: 7.0.6 + eventsource: 3.0.7 + express: 5.1.0 + express-rate-limit: 7.5.1(express@5.1.0) + pkce-challenge: 5.0.0 + raw-body: 3.0.0 + zod: 3.25.67 + zod-to-json-schema: 3.24.6(zod@3.25.67) + transitivePeerDependencies: + - supports-color + + "@nodelib/fs.scandir@2.1.5": + dependencies: + "@nodelib/fs.stat": 2.0.5 + run-parallel: 1.2.0 + + "@nodelib/fs.stat@2.0.5": {} + + "@nodelib/fs.walk@1.2.8": + dependencies: + "@nodelib/fs.scandir": 2.1.5 + fastq: 1.19.1 + + "@opentelemetry/api@1.9.0": {} + + "@playwright/test@1.53.1": + dependencies: + playwright: 1.53.1 + + "@types/diff-match-patch@1.0.36": {} + + "@types/estree@1.0.8": {} + + "@types/json-schema@7.0.15": {} + + "@types/node-fetch@2.6.12": + dependencies: + "@types/node": 18.19.112 + form-data: 4.0.3 + + "@types/node@18.19.112": + dependencies: + undici-types: 5.26.5 + + "@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)": + dependencies: + "@eslint-community/regexpp": 4.12.1 + "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/type-utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/visitor-keys": 8.35.0 + eslint: 9.29.0 + graphemer: 1.4.0 + ignore: 7.0.5 + natural-compare: 1.4.0 + ts-api-utils: 2.1.0(typescript@5.8.3) + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + "@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + dependencies: + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + "@typescript-eslint/visitor-keys": 8.35.0 + debug: 4.4.1 + eslint: 9.29.0 + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + "@typescript-eslint/project-service@8.35.0(typescript@5.8.3)": + dependencies: + "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) + "@typescript-eslint/types": 8.35.0 + debug: 4.4.1 + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + "@typescript-eslint/scope-manager@8.35.0": + dependencies: + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/visitor-keys": 8.35.0 + + "@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)": + dependencies: + typescript: 5.8.3 + + "@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + dependencies: + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + debug: 4.4.1 + eslint: 9.29.0 + ts-api-utils: 2.1.0(typescript@5.8.3) + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + "@typescript-eslint/types@8.35.0": {} + + "@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)": + dependencies: + "@typescript-eslint/project-service": 8.35.0(typescript@5.8.3) + "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/visitor-keys": 8.35.0 + debug: 4.4.1 + fast-glob: 3.3.3 + is-glob: 4.0.3 + minimatch: 9.0.5 + semver: 7.7.2 + ts-api-utils: 2.1.0(typescript@5.8.3) + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + "@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + dependencies: + "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + eslint: 9.29.0 + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + "@typescript-eslint/visitor-keys@8.35.0": + dependencies: + "@typescript-eslint/types": 8.35.0 + eslint-visitor-keys: 4.2.1 + + abort-controller@3.0.0: + dependencies: + event-target-shim: 5.0.1 + + accepts@2.0.0: + dependencies: + mime-types: 3.0.1 + negotiator: 1.0.0 + + acorn-jsx@5.3.2(acorn@8.15.0): + dependencies: + acorn: 8.15.0 + + acorn@8.15.0: {} + + agent-base@7.1.3: {} + + agentkeepalive@4.6.0: + dependencies: + humanize-ms: 1.2.1 + + ai@4.3.16(react@19.1.0)(zod@3.25.67): + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + "@ai-sdk/react": 1.2.12(react@19.1.0)(zod@3.25.67) + "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) + "@opentelemetry/api": 1.9.0 + jsondiffpatch: 0.6.0 + zod: 3.25.67 + optionalDependencies: + react: 19.1.0 + + ajv@6.12.6: + dependencies: + fast-deep-equal: 3.1.3 + fast-json-stable-stringify: 2.1.0 + json-schema-traverse: 0.4.1 + uri-js: 4.4.1 + + ansi-styles@4.3.0: + dependencies: + color-convert: 2.0.1 + + argparse@2.0.1: {} + + array-buffer-byte-length@1.0.2: + dependencies: + call-bound: 1.0.4 + is-array-buffer: 3.0.5 + + array-includes@3.1.9: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-object-atoms: 1.1.1 + get-intrinsic: 1.3.0 + is-string: 1.1.1 + math-intrinsics: 1.1.0 + + array.prototype.findlast@1.2.5: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-errors: 1.3.0 + es-object-atoms: 1.1.1 + es-shim-unscopables: 1.1.0 + + array.prototype.flat@1.3.3: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-shim-unscopables: 1.1.0 + + array.prototype.flatmap@1.3.3: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-shim-unscopables: 1.1.0 + + array.prototype.tosorted@1.1.4: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-errors: 1.3.0 + es-shim-unscopables: 1.1.0 + + arraybuffer.prototype.slice@1.0.4: + dependencies: + array-buffer-byte-length: 1.0.2 + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-errors: 1.3.0 + get-intrinsic: 1.3.0 + is-array-buffer: 3.0.5 + + async-function@1.0.0: {} + + asynckit@0.4.0: {} + + atomic-sleep@1.0.0: {} + + available-typed-arrays@1.0.7: + dependencies: + possible-typed-array-names: 1.1.0 + + balanced-match@1.0.2: {} + + base64-js@1.5.1: {} + + bignumber.js@9.3.0: {} + + body-parser@2.2.0: + dependencies: + bytes: 3.1.2 + content-type: 1.0.5 + debug: 4.4.1 + http-errors: 2.0.0 + iconv-lite: 0.6.3 + on-finished: 2.4.1 + qs: 6.14.0 + raw-body: 3.0.0 + type-is: 2.0.1 + transitivePeerDependencies: + - supports-color + + brace-expansion@1.1.12: + dependencies: + balanced-match: 1.0.2 + concat-map: 0.0.1 + + brace-expansion@2.0.2: + dependencies: + balanced-match: 1.0.2 + + braces@3.0.3: + dependencies: + fill-range: 7.1.1 + + buffer-equal-constant-time@1.0.1: {} + + bytes@3.1.2: {} + + call-bind-apply-helpers@1.0.2: + dependencies: + es-errors: 1.3.0 + function-bind: 1.1.2 + + call-bind@1.0.8: + dependencies: + call-bind-apply-helpers: 1.0.2 + es-define-property: 1.0.1 + get-intrinsic: 1.3.0 + set-function-length: 1.2.2 + + call-bound@1.0.4: + dependencies: + call-bind-apply-helpers: 1.0.2 + get-intrinsic: 1.3.0 + + callsites@3.1.0: {} + + chalk@4.1.2: + dependencies: + ansi-styles: 4.3.0 + supports-color: 7.2.0 + + chalk@5.4.1: {} + + color-convert@2.0.1: + dependencies: + color-name: 1.1.4 + + color-name@1.1.4: {} + + colorette@2.0.20: {} + + combined-stream@1.0.8: + dependencies: + delayed-stream: 1.0.0 + + commander@14.0.0: {} + + concat-map@0.0.1: {} + + content-disposition@1.0.0: + dependencies: + safe-buffer: 5.2.1 + + content-type@1.0.5: {} + + cookie-signature@1.2.2: {} + + cookie@0.7.2: {} + + cors@2.8.5: + dependencies: + object-assign: 4.1.1 + vary: 1.1.2 + + cross-spawn@7.0.6: + dependencies: + path-key: 3.1.1 + shebang-command: 2.0.0 + which: 2.0.2 + + data-view-buffer@1.0.2: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + is-data-view: 1.0.2 + + data-view-byte-length@1.0.2: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + is-data-view: 1.0.2 + + data-view-byte-offset@1.0.1: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + is-data-view: 1.0.2 + + dateformat@4.6.3: {} + + debug@4.4.1: + dependencies: + ms: 2.1.3 + + deep-is@0.1.4: {} + + deepmerge@4.3.1: {} + + define-data-property@1.1.4: + dependencies: + es-define-property: 1.0.1 + es-errors: 1.3.0 + gopd: 1.2.0 + + define-properties@1.2.1: + dependencies: + define-data-property: 1.1.4 + has-property-descriptors: 1.0.2 + object-keys: 1.1.1 + + delayed-stream@1.0.0: {} + + depd@2.0.0: {} + + dequal@2.0.3: {} + + devtools-protocol@0.0.1464554: {} + + diff-match-patch@1.0.5: {} + + doctrine@2.1.0: + dependencies: + esutils: 2.0.3 + + dotenv@16.5.0: {} + + dunder-proto@1.0.1: + dependencies: + call-bind-apply-helpers: 1.0.2 + es-errors: 1.3.0 + gopd: 1.2.0 + + ecdsa-sig-formatter@1.0.11: + dependencies: + safe-buffer: 5.2.1 + + ee-first@1.1.1: {} + + encodeurl@2.0.0: {} + + end-of-stream@1.4.5: + dependencies: + once: 1.4.0 + + es-abstract@1.24.0: + dependencies: + array-buffer-byte-length: 1.0.2 + arraybuffer.prototype.slice: 1.0.4 + available-typed-arrays: 1.0.7 + call-bind: 1.0.8 + call-bound: 1.0.4 + data-view-buffer: 1.0.2 + data-view-byte-length: 1.0.2 + data-view-byte-offset: 1.0.1 + es-define-property: 1.0.1 + es-errors: 1.3.0 + es-object-atoms: 1.1.1 + es-set-tostringtag: 2.1.0 + es-to-primitive: 1.3.0 + function.prototype.name: 1.1.8 + get-intrinsic: 1.3.0 + get-proto: 1.0.1 + get-symbol-description: 1.1.0 + globalthis: 1.0.4 + gopd: 1.2.0 + has-property-descriptors: 1.0.2 + has-proto: 1.2.0 + has-symbols: 1.1.0 + hasown: 2.0.2 + internal-slot: 1.1.0 + is-array-buffer: 3.0.5 + is-callable: 1.2.7 + is-data-view: 1.0.2 + is-negative-zero: 2.0.3 + is-regex: 1.2.1 + is-set: 2.0.3 + is-shared-array-buffer: 1.0.4 + is-string: 1.1.1 + is-typed-array: 1.1.15 + is-weakref: 1.1.1 + math-intrinsics: 1.1.0 + object-inspect: 1.13.4 + object-keys: 1.1.1 + object.assign: 4.1.7 + own-keys: 1.0.1 + regexp.prototype.flags: 1.5.4 + safe-array-concat: 1.1.3 + safe-push-apply: 1.0.0 + safe-regex-test: 1.1.0 + set-proto: 1.0.0 + stop-iteration-iterator: 1.1.0 + string.prototype.trim: 1.2.10 + string.prototype.trimend: 1.0.9 + string.prototype.trimstart: 1.0.8 + typed-array-buffer: 1.0.3 + typed-array-byte-length: 1.0.3 + typed-array-byte-offset: 1.0.4 + typed-array-length: 1.0.7 + unbox-primitive: 1.1.0 + which-typed-array: 1.1.19 + + es-define-property@1.0.1: {} + + es-errors@1.3.0: {} + + es-iterator-helpers@1.2.1: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-errors: 1.3.0 + es-set-tostringtag: 2.1.0 + function-bind: 1.1.2 + get-intrinsic: 1.3.0 + globalthis: 1.0.4 + gopd: 1.2.0 + has-property-descriptors: 1.0.2 + has-proto: 1.2.0 + has-symbols: 1.1.0 + internal-slot: 1.1.0 + iterator.prototype: 1.1.5 + safe-array-concat: 1.1.3 + + es-object-atoms@1.1.1: + dependencies: + es-errors: 1.3.0 + + es-set-tostringtag@2.1.0: + dependencies: + es-errors: 1.3.0 + get-intrinsic: 1.3.0 + has-tostringtag: 1.0.2 + hasown: 2.0.2 + + es-shim-unscopables@1.1.0: + dependencies: + hasown: 2.0.2 + + es-to-primitive@1.3.0: + dependencies: + is-callable: 1.2.7 + is-date-object: 1.1.0 + is-symbol: 1.1.1 + + escape-html@1.0.3: {} + + escape-string-regexp@4.0.0: {} + + eslint-plugin-react@7.37.5(eslint@9.29.0): + dependencies: + array-includes: 3.1.9 + array.prototype.findlast: 1.2.5 + array.prototype.flatmap: 1.3.3 + array.prototype.tosorted: 1.1.4 + doctrine: 2.1.0 + es-iterator-helpers: 1.2.1 + eslint: 9.29.0 + estraverse: 5.3.0 + hasown: 2.0.2 + jsx-ast-utils: 3.3.5 + minimatch: 3.1.2 + object.entries: 1.1.9 + object.fromentries: 2.0.8 + object.values: 1.2.1 + prop-types: 15.8.1 + resolve: 2.0.0-next.5 + semver: 6.3.1 + string.prototype.matchall: 4.0.12 + string.prototype.repeat: 1.0.0 + + eslint-scope@8.4.0: + dependencies: + esrecurse: 4.3.0 + estraverse: 5.3.0 + + eslint-visitor-keys@3.4.3: {} + + eslint-visitor-keys@4.2.1: {} + + eslint@9.29.0: + dependencies: + "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) + "@eslint-community/regexpp": 4.12.1 + "@eslint/config-array": 0.20.1 + "@eslint/config-helpers": 0.2.3 + "@eslint/core": 0.14.0 + "@eslint/eslintrc": 3.3.1 + "@eslint/js": 9.29.0 + "@eslint/plugin-kit": 0.3.3 + "@humanfs/node": 0.16.6 + "@humanwhocodes/module-importer": 1.0.1 + "@humanwhocodes/retry": 0.4.3 + "@types/estree": 1.0.8 + "@types/json-schema": 7.0.15 + ajv: 6.12.6 + chalk: 4.1.2 + cross-spawn: 7.0.6 + debug: 4.4.1 + escape-string-regexp: 4.0.0 + eslint-scope: 8.4.0 + eslint-visitor-keys: 4.2.1 + espree: 10.4.0 + esquery: 1.6.0 + esutils: 2.0.3 + fast-deep-equal: 3.1.3 + file-entry-cache: 8.0.0 + find-up: 5.0.0 + glob-parent: 6.0.2 + ignore: 5.3.2 + imurmurhash: 0.1.4 + is-glob: 4.0.3 + json-stable-stringify-without-jsonify: 1.0.1 + lodash.merge: 4.6.2 + minimatch: 3.1.2 + natural-compare: 1.4.0 + optionator: 0.9.4 + transitivePeerDependencies: + - supports-color + + espree@10.4.0: + dependencies: + acorn: 8.15.0 + acorn-jsx: 5.3.2(acorn@8.15.0) + eslint-visitor-keys: 4.2.1 + + esquery@1.6.0: + dependencies: + estraverse: 5.3.0 + + esrecurse@4.3.0: + dependencies: + estraverse: 5.3.0 + + estraverse@5.3.0: {} + + esutils@2.0.3: {} + + etag@1.8.1: {} + + event-target-shim@5.0.1: {} + + eventsource-parser@3.0.3: {} + + eventsource@3.0.7: + dependencies: + eventsource-parser: 3.0.3 + + express-rate-limit@7.5.1(express@5.1.0): + dependencies: + express: 5.1.0 + + express@5.1.0: + dependencies: + accepts: 2.0.0 + body-parser: 2.2.0 + content-disposition: 1.0.0 + content-type: 1.0.5 + cookie: 0.7.2 + cookie-signature: 1.2.2 + debug: 4.4.1 + encodeurl: 2.0.0 + escape-html: 1.0.3 + etag: 1.8.1 + finalhandler: 2.1.0 + fresh: 2.0.0 + http-errors: 2.0.0 + merge-descriptors: 2.0.0 + mime-types: 3.0.1 + on-finished: 2.4.1 + once: 1.4.0 + parseurl: 1.3.3 + proxy-addr: 2.0.7 + qs: 6.14.0 + range-parser: 1.2.1 + router: 2.2.0 + send: 1.2.0 + serve-static: 2.2.0 + statuses: 2.0.2 + type-is: 2.0.1 + vary: 1.1.2 + transitivePeerDependencies: + - supports-color + + extend@3.0.2: {} + + fast-copy@3.0.2: {} + + fast-deep-equal@3.1.3: {} + + fast-glob@3.3.3: + dependencies: + "@nodelib/fs.stat": 2.0.5 + "@nodelib/fs.walk": 1.2.8 + glob-parent: 5.1.2 + merge2: 1.4.1 + micromatch: 4.0.8 + + fast-json-stable-stringify@2.1.0: {} + + fast-levenshtein@2.0.6: {} + + fast-redact@3.5.0: {} + + fast-safe-stringify@2.1.1: {} + + fastq@1.19.1: + dependencies: + reusify: 1.1.0 + + fetch-cookie@3.1.0: + dependencies: + set-cookie-parser: 2.7.1 + tough-cookie: 5.1.2 + + file-entry-cache@8.0.0: + dependencies: + flat-cache: 4.0.1 + + fill-range@7.1.1: + dependencies: + to-regex-range: 5.0.1 + + finalhandler@2.1.0: + dependencies: + debug: 4.4.1 + encodeurl: 2.0.0 + escape-html: 1.0.3 + on-finished: 2.4.1 + parseurl: 1.3.3 + statuses: 2.0.2 + transitivePeerDependencies: + - supports-color + + find-up@5.0.0: + dependencies: + locate-path: 6.0.0 + path-exists: 4.0.0 + + flat-cache@4.0.1: + dependencies: + flatted: 3.3.3 + keyv: 4.5.4 + + flatted@3.3.3: {} + + for-each@0.3.5: + dependencies: + is-callable: 1.2.7 + + form-data-encoder@1.7.2: {} + + form-data@4.0.3: + dependencies: + asynckit: 0.4.0 + combined-stream: 1.0.8 + es-set-tostringtag: 2.1.0 + hasown: 2.0.2 + mime-types: 2.1.35 + + formdata-node@4.4.1: + dependencies: + node-domexception: 1.0.0 + web-streams-polyfill: 4.0.0-beta.3 + + forwarded@0.2.0: {} + + fresh@2.0.0: {} + + fs.realpath@1.0.0: {} + + fsevents@2.3.2: + optional: true + + function-bind@1.1.2: {} + + function.prototype.name@1.1.8: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + functions-have-names: 1.2.3 + hasown: 2.0.2 + is-callable: 1.2.7 + + functions-have-names@1.2.3: {} + + gaxios@6.7.1: + dependencies: + extend: 3.0.2 + https-proxy-agent: 7.0.6 + is-stream: 2.0.1 + node-fetch: 2.7.0 + uuid: 9.0.1 + transitivePeerDependencies: + - encoding + - supports-color + + gcp-metadata@6.1.1: + dependencies: + gaxios: 6.7.1 + google-logging-utils: 0.0.2 + json-bigint: 1.0.0 + transitivePeerDependencies: + - encoding + - supports-color + + get-intrinsic@1.3.0: + dependencies: + call-bind-apply-helpers: 1.0.2 + es-define-property: 1.0.1 + es-errors: 1.3.0 + es-object-atoms: 1.1.1 + function-bind: 1.1.2 + get-proto: 1.0.1 + gopd: 1.2.0 + has-symbols: 1.1.0 + hasown: 2.0.2 + math-intrinsics: 1.1.0 + + get-proto@1.0.1: + dependencies: + dunder-proto: 1.0.1 + es-object-atoms: 1.1.1 + + get-symbol-description@1.1.0: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + get-intrinsic: 1.3.0 + + glob-parent@5.1.2: + dependencies: + is-glob: 4.0.3 + + glob-parent@6.0.2: + dependencies: + is-glob: 4.0.3 + + glob@7.2.3: + dependencies: + fs.realpath: 1.0.0 + inflight: 1.0.6 + inherits: 2.0.4 + minimatch: 3.1.2 + once: 1.4.0 + path-is-absolute: 1.0.1 + + globals@14.0.0: {} + + globals@16.2.0: {} + + globalthis@1.0.4: + dependencies: + define-properties: 1.2.1 + gopd: 1.2.0 + + google-auth-library@9.15.1: + dependencies: + base64-js: 1.5.1 + ecdsa-sig-formatter: 1.0.11 + gaxios: 6.7.1 + gcp-metadata: 6.1.1 + gtoken: 7.1.0 + jws: 4.0.0 + transitivePeerDependencies: + - encoding + - supports-color + + google-logging-utils@0.0.2: {} + + gopd@1.2.0: {} + + graphemer@1.4.0: {} + + gtoken@7.1.0: + dependencies: + gaxios: 6.7.1 + jws: 4.0.0 + transitivePeerDependencies: + - encoding + - supports-color + + has-bigints@1.1.0: {} + + has-flag@4.0.0: {} + + has-property-descriptors@1.0.2: + dependencies: + es-define-property: 1.0.1 + + has-proto@1.2.0: + dependencies: + dunder-proto: 1.0.1 + + has-symbols@1.1.0: {} + + has-tostringtag@1.0.2: + dependencies: + has-symbols: 1.1.0 + + hasown@2.0.2: + dependencies: + function-bind: 1.1.2 + + help-me@5.0.0: {} + + http-errors@2.0.0: + dependencies: + depd: 2.0.0 + inherits: 2.0.4 + setprototypeof: 1.2.0 + statuses: 2.0.1 + toidentifier: 1.0.1 + + https-proxy-agent@7.0.6: + dependencies: + agent-base: 7.1.3 + debug: 4.4.1 + transitivePeerDependencies: + - supports-color + + humanize-ms@1.2.1: + dependencies: + ms: 2.1.3 + + iconv-lite@0.6.3: + dependencies: + safer-buffer: 2.1.2 + + ignore@5.3.2: {} + + ignore@7.0.5: {} + + import-fresh@3.3.1: + dependencies: + parent-module: 1.0.1 + resolve-from: 4.0.0 + + imurmurhash@0.1.4: {} + + inflight@1.0.6: + dependencies: + once: 1.4.0 + wrappy: 1.0.2 + + inherits@2.0.4: {} + + internal-slot@1.1.0: + dependencies: + es-errors: 1.3.0 + hasown: 2.0.2 + side-channel: 1.1.0 + + interpret@1.4.0: {} + + ipaddr.js@1.9.1: {} + + is-array-buffer@3.0.5: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + get-intrinsic: 1.3.0 + + is-async-function@2.1.1: + dependencies: + async-function: 1.0.0 + call-bound: 1.0.4 + get-proto: 1.0.1 + has-tostringtag: 1.0.2 + safe-regex-test: 1.1.0 + + is-bigint@1.1.0: + dependencies: + has-bigints: 1.1.0 + + is-boolean-object@1.2.2: + dependencies: + call-bound: 1.0.4 + has-tostringtag: 1.0.2 + + is-callable@1.2.7: {} + + is-core-module@2.16.1: + dependencies: + hasown: 2.0.2 + + is-data-view@1.0.2: + dependencies: + call-bound: 1.0.4 + get-intrinsic: 1.3.0 + is-typed-array: 1.1.15 + + is-date-object@1.1.0: + dependencies: + call-bound: 1.0.4 + has-tostringtag: 1.0.2 + + is-extglob@2.1.1: {} + + is-finalizationregistry@1.1.1: + dependencies: + call-bound: 1.0.4 + + is-generator-function@1.1.0: + dependencies: + call-bound: 1.0.4 + get-proto: 1.0.1 + has-tostringtag: 1.0.2 + safe-regex-test: 1.1.0 + + is-glob@4.0.3: + dependencies: + is-extglob: 2.1.1 + + is-map@2.0.3: {} + + is-negative-zero@2.0.3: {} + + is-number-object@1.1.1: + dependencies: + call-bound: 1.0.4 + has-tostringtag: 1.0.2 + + is-number@7.0.0: {} + + is-promise@4.0.0: {} + + is-regex@1.2.1: + dependencies: + call-bound: 1.0.4 + gopd: 1.2.0 + has-tostringtag: 1.0.2 + hasown: 2.0.2 + + is-set@2.0.3: {} + + is-shared-array-buffer@1.0.4: + dependencies: + call-bound: 1.0.4 + + is-stream@2.0.1: {} + + is-string@1.1.1: + dependencies: + call-bound: 1.0.4 + has-tostringtag: 1.0.2 + + is-symbol@1.1.1: + dependencies: + call-bound: 1.0.4 + has-symbols: 1.1.0 + safe-regex-test: 1.1.0 + + is-typed-array@1.1.15: + dependencies: + which-typed-array: 1.1.19 + + is-weakmap@2.0.2: {} + + is-weakref@1.1.1: + dependencies: + call-bound: 1.0.4 + + is-weakset@2.0.4: + dependencies: + call-bound: 1.0.4 + get-intrinsic: 1.3.0 + + isarray@2.0.5: {} + + isexe@2.0.0: {} + + iterator.prototype@1.1.5: + dependencies: + define-data-property: 1.1.4 + es-object-atoms: 1.1.1 + get-intrinsic: 1.3.0 + get-proto: 1.0.1 + has-symbols: 1.1.0 + set-function-name: 2.0.2 + + joycon@3.1.1: {} + + js-tokens@4.0.0: {} + + js-yaml@4.1.0: + dependencies: + argparse: 2.0.1 + + json-bigint@1.0.0: + dependencies: + bignumber.js: 9.3.0 + + json-buffer@3.0.1: {} + + json-schema-traverse@0.4.1: {} + + json-schema@0.4.0: {} + + json-stable-stringify-without-jsonify@1.0.1: {} + + jsondiffpatch@0.6.0: + dependencies: + "@types/diff-match-patch": 1.0.36 + chalk: 5.4.1 + diff-match-patch: 1.0.5 + + jsx-ast-utils@3.3.5: + dependencies: + array-includes: 3.1.9 + array.prototype.flat: 1.3.3 + object.assign: 4.1.7 + object.values: 1.2.1 + + jwa@2.0.1: + dependencies: + buffer-equal-constant-time: 1.0.1 + ecdsa-sig-formatter: 1.0.11 + safe-buffer: 5.2.1 + + jws@4.0.0: + dependencies: + jwa: 2.0.1 + safe-buffer: 5.2.1 + + keyv@4.5.4: + dependencies: + json-buffer: 3.0.1 + + levn@0.4.1: + dependencies: + prelude-ls: 1.2.1 + type-check: 0.4.0 + + locate-path@6.0.0: + dependencies: + p-locate: 5.0.0 + + lodash.merge@4.6.2: {} + + loose-envify@1.4.0: + dependencies: + js-tokens: 4.0.0 + + math-intrinsics@1.1.0: {} + + media-typer@1.1.0: {} + + merge-descriptors@2.0.0: {} + + merge2@1.4.1: {} + + micromatch@4.0.8: + dependencies: + braces: 3.0.3 + picomatch: 2.3.1 + + mime-db@1.52.0: {} + + mime-db@1.54.0: {} + + mime-types@2.1.35: + dependencies: + mime-db: 1.52.0 + + mime-types@3.0.1: + dependencies: + mime-db: 1.54.0 + + minimatch@3.1.2: + dependencies: + brace-expansion: 1.1.12 + + minimatch@9.0.5: + dependencies: + brace-expansion: 2.0.2 + + minimist@1.2.8: {} + + ms@2.1.3: {} + + nanoid@3.3.11: {} + + natural-compare@1.4.0: {} + + negotiator@1.0.0: {} + + node-domexception@1.0.0: {} + + node-fetch@2.7.0: + dependencies: + whatwg-url: 5.0.0 + + object-assign@4.1.1: {} + + object-inspect@1.13.4: {} + + object-keys@1.1.1: {} + + object.assign@4.1.7: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-object-atoms: 1.1.1 + has-symbols: 1.1.0 + object-keys: 1.1.1 + + object.entries@1.1.9: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-object-atoms: 1.1.1 + + object.fromentries@2.0.8: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-object-atoms: 1.1.1 + + object.values@1.2.1: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-object-atoms: 1.1.1 + + ollama-ai-provider@1.2.0(zod@3.25.67): + dependencies: + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + partial-json: 0.1.7 + optionalDependencies: + zod: 3.25.67 + optional: true + + on-exit-leak-free@2.1.2: {} + + on-finished@2.4.1: + dependencies: + ee-first: 1.1.1 + + once@1.4.0: + dependencies: + wrappy: 1.0.2 + + openai@4.104.0(ws@8.18.2)(zod@3.25.67): + dependencies: + "@types/node": 18.19.112 + "@types/node-fetch": 2.6.12 + abort-controller: 3.0.0 + agentkeepalive: 4.6.0 + form-data-encoder: 1.7.2 + formdata-node: 4.4.1 + node-fetch: 2.7.0 + optionalDependencies: + ws: 8.18.2 + zod: 3.25.67 + transitivePeerDependencies: + - encoding + + optionator@0.9.4: + dependencies: + deep-is: 0.1.4 + fast-levenshtein: 2.0.6 + levn: 0.4.1 + prelude-ls: 1.2.1 + type-check: 0.4.0 + word-wrap: 1.2.5 + + own-keys@1.0.1: + dependencies: + get-intrinsic: 1.3.0 + object-keys: 1.1.1 + safe-push-apply: 1.0.0 + + p-limit@3.1.0: + dependencies: + yocto-queue: 0.1.0 + + p-locate@5.0.0: + dependencies: + p-limit: 3.1.0 + + parent-module@1.0.1: + dependencies: + callsites: 3.1.0 + + parseurl@1.3.3: {} + + partial-json@0.1.7: + optional: true + + path-exists@4.0.0: {} + + path-is-absolute@1.0.1: {} + + path-key@3.1.1: {} + + path-parse@1.0.7: {} + + path-to-regexp@8.2.0: {} + + picomatch@2.3.1: {} + + pino-abstract-transport@2.0.0: + dependencies: + split2: 4.2.0 + + pino-pretty@13.0.0: + dependencies: + colorette: 2.0.20 + dateformat: 4.6.3 + fast-copy: 3.0.2 + fast-safe-stringify: 2.1.1 + help-me: 5.0.0 + joycon: 3.1.1 + minimist: 1.2.8 + on-exit-leak-free: 2.1.2 + pino-abstract-transport: 2.0.0 + pump: 3.0.3 + secure-json-parse: 2.7.0 + sonic-boom: 4.2.0 + strip-json-comments: 3.1.1 + + pino-std-serializers@7.0.0: {} + + pino@9.7.0: + dependencies: + atomic-sleep: 1.0.0 + fast-redact: 3.5.0 + on-exit-leak-free: 2.1.2 + pino-abstract-transport: 2.0.0 + pino-std-serializers: 7.0.0 + process-warning: 5.0.0 + quick-format-unescaped: 4.0.4 + real-require: 0.2.0 + safe-stable-stringify: 2.5.0 + sonic-boom: 4.2.0 + thread-stream: 3.1.0 + + pkce-challenge@5.0.0: {} + + playwright-core@1.53.1: {} + + playwright@1.53.1: + dependencies: + playwright-core: 1.53.1 + optionalDependencies: + fsevents: 2.3.2 + + possible-typed-array-names@1.1.0: {} + + prelude-ls@1.2.1: {} + + prettier@3.6.1: {} + + process-warning@5.0.0: {} + + prop-types@15.8.1: + dependencies: + loose-envify: 1.4.0 + object-assign: 4.1.1 + react-is: 16.13.1 + + proxy-addr@2.0.7: + dependencies: + forwarded: 0.2.0 + ipaddr.js: 1.9.1 + + pump@3.0.3: + dependencies: + end-of-stream: 1.4.5 + once: 1.4.0 + + punycode@2.3.1: {} + + qs@6.14.0: + dependencies: + side-channel: 1.1.0 + + queue-microtask@1.2.3: {} + + quick-format-unescaped@4.0.4: {} + + range-parser@1.2.1: {} + + raw-body@3.0.0: + dependencies: + bytes: 3.1.2 + http-errors: 2.0.0 + iconv-lite: 0.6.3 + unpipe: 1.0.0 + + react-is@16.13.1: {} + + react@19.1.0: {} + + real-require@0.2.0: {} + + rechoir@0.6.2: + dependencies: + resolve: 1.22.10 + + reflect.getprototypeof@1.0.10: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-errors: 1.3.0 + es-object-atoms: 1.1.1 + get-intrinsic: 1.3.0 + get-proto: 1.0.1 + which-builtin-type: 1.2.1 + + regexp.prototype.flags@1.5.4: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-errors: 1.3.0 + get-proto: 1.0.1 + gopd: 1.2.0 + set-function-name: 2.0.2 + + resolve-from@4.0.0: {} + + resolve@1.22.10: + dependencies: + is-core-module: 2.16.1 + path-parse: 1.0.7 + supports-preserve-symlinks-flag: 1.0.0 + + resolve@2.0.0-next.5: + dependencies: + is-core-module: 2.16.1 + path-parse: 1.0.7 + supports-preserve-symlinks-flag: 1.0.0 + + reusify@1.1.0: {} + + router@2.2.0: + dependencies: + debug: 4.4.1 + depd: 2.0.0 + is-promise: 4.0.0 + parseurl: 1.3.3 + path-to-regexp: 8.2.0 + transitivePeerDependencies: + - supports-color + + run-parallel@1.2.0: + dependencies: + queue-microtask: 1.2.3 + + safe-array-concat@1.1.3: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + get-intrinsic: 1.3.0 + has-symbols: 1.1.0 + isarray: 2.0.5 + + safe-buffer@5.2.1: {} + + safe-push-apply@1.0.0: + dependencies: + es-errors: 1.3.0 + isarray: 2.0.5 + + safe-regex-test@1.1.0: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + is-regex: 1.2.1 + + safe-stable-stringify@2.5.0: {} + + safer-buffer@2.1.2: {} + + secure-json-parse@2.7.0: {} + + semver@6.3.1: {} + + semver@7.7.2: {} + + send@1.2.0: + dependencies: + debug: 4.4.1 + encodeurl: 2.0.0 + escape-html: 1.0.3 + etag: 1.8.1 + fresh: 2.0.0 + http-errors: 2.0.0 + mime-types: 3.0.1 + ms: 2.1.3 + on-finished: 2.4.1 + range-parser: 1.2.1 + statuses: 2.0.2 + transitivePeerDependencies: + - supports-color + + serve-static@2.2.0: + dependencies: + encodeurl: 2.0.0 + escape-html: 1.0.3 + parseurl: 1.3.3 + send: 1.2.0 + transitivePeerDependencies: + - supports-color + + set-cookie-parser@2.7.1: {} + + set-function-length@1.2.2: + dependencies: + define-data-property: 1.1.4 + es-errors: 1.3.0 + function-bind: 1.1.2 + get-intrinsic: 1.3.0 + gopd: 1.2.0 + has-property-descriptors: 1.0.2 + + set-function-name@2.0.2: + dependencies: + define-data-property: 1.1.4 + es-errors: 1.3.0 + functions-have-names: 1.2.3 + has-property-descriptors: 1.0.2 + + set-proto@1.0.0: + dependencies: + dunder-proto: 1.0.1 + es-errors: 1.3.0 + es-object-atoms: 1.1.1 + + setprototypeof@1.2.0: {} + + shebang-command@2.0.0: + dependencies: + shebang-regex: 3.0.0 + + shebang-regex@3.0.0: {} + + shelljs@0.8.5: + dependencies: + glob: 7.2.3 + interpret: 1.4.0 + rechoir: 0.6.2 + + shx@0.3.4: + dependencies: + minimist: 1.2.8 + shelljs: 0.8.5 + + side-channel-list@1.0.0: + dependencies: + es-errors: 1.3.0 + object-inspect: 1.13.4 + + side-channel-map@1.0.1: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + get-intrinsic: 1.3.0 + object-inspect: 1.13.4 + + side-channel-weakmap@1.0.2: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + get-intrinsic: 1.3.0 + object-inspect: 1.13.4 + side-channel-map: 1.0.1 + + side-channel@1.1.0: + dependencies: + es-errors: 1.3.0 + object-inspect: 1.13.4 + side-channel-list: 1.0.0 + side-channel-map: 1.0.1 + side-channel-weakmap: 1.0.2 + + sonic-boom@4.2.0: + dependencies: + atomic-sleep: 1.0.0 + + split2@4.2.0: {} + + statuses@2.0.1: {} + + statuses@2.0.2: {} + + stop-iteration-iterator@1.1.0: + dependencies: + es-errors: 1.3.0 + internal-slot: 1.1.0 + + string.prototype.matchall@4.0.12: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-errors: 1.3.0 + es-object-atoms: 1.1.1 + get-intrinsic: 1.3.0 + gopd: 1.2.0 + has-symbols: 1.1.0 + internal-slot: 1.1.0 + regexp.prototype.flags: 1.5.4 + set-function-name: 2.0.2 + side-channel: 1.1.0 + + string.prototype.repeat@1.0.0: + dependencies: + define-properties: 1.2.1 + es-abstract: 1.24.0 + + string.prototype.trim@1.2.10: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-data-property: 1.1.4 + define-properties: 1.2.1 + es-abstract: 1.24.0 + es-object-atoms: 1.1.1 + has-property-descriptors: 1.0.2 + + string.prototype.trimend@1.0.9: + dependencies: + call-bind: 1.0.8 + call-bound: 1.0.4 + define-properties: 1.2.1 + es-object-atoms: 1.1.1 + + string.prototype.trimstart@1.0.8: + dependencies: + call-bind: 1.0.8 + define-properties: 1.2.1 + es-object-atoms: 1.1.1 + + strip-json-comments@3.1.1: {} + + supports-color@7.2.0: + dependencies: + has-flag: 4.0.0 + + supports-preserve-symlinks-flag@1.0.0: {} + + swr@2.3.3(react@19.1.0): + dependencies: + dequal: 2.0.3 + react: 19.1.0 + use-sync-external-store: 1.5.0(react@19.1.0) + + thread-stream@3.1.0: + dependencies: + real-require: 0.2.0 + + throttleit@2.1.0: {} + + tldts-core@6.1.86: {} + + tldts@6.1.86: + dependencies: + tldts-core: 6.1.86 + + to-regex-range@5.0.1: + dependencies: + is-number: 7.0.0 + + toidentifier@1.0.1: {} + + tough-cookie@5.1.2: + dependencies: + tldts: 6.1.86 + + tr46@0.0.3: {} + + ts-api-utils@2.1.0(typescript@5.8.3): + dependencies: + typescript: 5.8.3 + + type-check@0.4.0: + dependencies: + prelude-ls: 1.2.1 + + type-is@2.0.1: + dependencies: + content-type: 1.0.5 + media-typer: 1.1.0 + mime-types: 3.0.1 + + typed-array-buffer@1.0.3: + dependencies: + call-bound: 1.0.4 + es-errors: 1.3.0 + is-typed-array: 1.1.15 + + typed-array-byte-length@1.0.3: + dependencies: + call-bind: 1.0.8 + for-each: 0.3.5 + gopd: 1.2.0 + has-proto: 1.2.0 + is-typed-array: 1.1.15 + + typed-array-byte-offset@1.0.4: + dependencies: + available-typed-arrays: 1.0.7 + call-bind: 1.0.8 + for-each: 0.3.5 + gopd: 1.2.0 + has-proto: 1.2.0 + is-typed-array: 1.1.15 + reflect.getprototypeof: 1.0.10 + + typed-array-length@1.0.7: + dependencies: + call-bind: 1.0.8 + for-each: 0.3.5 + gopd: 1.2.0 + is-typed-array: 1.1.15 + possible-typed-array-names: 1.1.0 + reflect.getprototypeof: 1.0.10 + + typescript-eslint@8.35.0(eslint@9.29.0)(typescript@5.8.3): + dependencies: + "@typescript-eslint/eslint-plugin": 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + eslint: 9.29.0 + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + + typescript@5.8.3: {} + + unbox-primitive@1.1.0: + dependencies: + call-bound: 1.0.4 + has-bigints: 1.1.0 + has-symbols: 1.1.0 + which-boxed-primitive: 1.1.1 + + undici-types@5.26.5: {} + + unpipe@1.0.0: {} + + uri-js@4.4.1: + dependencies: + punycode: 2.3.1 + + use-sync-external-store@1.5.0(react@19.1.0): + dependencies: + react: 19.1.0 + + uuid@9.0.1: {} + + vary@1.1.2: {} + + web-streams-polyfill@4.0.0-beta.3: {} + + webidl-conversions@3.0.1: {} + + whatwg-url@5.0.0: + dependencies: + tr46: 0.0.3 + webidl-conversions: 3.0.1 + + which-boxed-primitive@1.1.1: + dependencies: + is-bigint: 1.1.0 + is-boolean-object: 1.2.2 + is-number-object: 1.1.1 + is-string: 1.1.1 + is-symbol: 1.1.1 + + which-builtin-type@1.2.1: + dependencies: + call-bound: 1.0.4 + function.prototype.name: 1.1.8 + has-tostringtag: 1.0.2 + is-async-function: 2.1.1 + is-date-object: 1.1.0 + is-finalizationregistry: 1.1.1 + is-generator-function: 1.1.0 + is-regex: 1.2.1 + is-weakref: 1.1.1 + isarray: 2.0.5 + which-boxed-primitive: 1.1.1 + which-collection: 1.0.2 + which-typed-array: 1.1.19 + + which-collection@1.0.2: + dependencies: + is-map: 2.0.3 + is-set: 2.0.3 + is-weakmap: 2.0.2 + is-weakset: 2.0.4 + + which-typed-array@1.1.19: + dependencies: + available-typed-arrays: 1.0.7 + call-bind: 1.0.8 + call-bound: 1.0.4 + for-each: 0.3.5 + get-proto: 1.0.1 + gopd: 1.2.0 + has-tostringtag: 1.0.2 + + which@2.0.2: + dependencies: + isexe: 2.0.0 + + word-wrap@1.2.5: {} + + wrappy@1.0.2: {} + + ws@8.18.2: {} + + yocto-queue@0.1.0: {} + + zod-to-json-schema@3.24.6(zod@3.25.67): + dependencies: + zod: 3.25.67 + + zod@3.25.67: {} diff --git a/smithery.config.js b/smithery.config.js index e2dfe2e..c082c3c 100644 --- a/smithery.config.js +++ b/smithery.config.js @@ -6,5 +6,5 @@ export default { // Mark playwright-core as external to prevent bundling // This avoids the relative path resolution issue in Docker external: ["playwright-core"], - } -} + }, +}; diff --git a/smithery.yaml b/smithery.yaml index 8fa57d3..322550e 100644 --- a/smithery.yaml +++ b/smithery.yaml @@ -1 +1 @@ -runtime: "typescript" \ No newline at end of file +runtime: "typescript" diff --git a/src/config.ts b/src/config.ts index ecd65a7..ce2151b 100644 --- a/src/config.ts +++ b/src/config.ts @@ -1,12 +1,12 @@ -import os from 'os'; -import fs from 'fs'; -import path from 'path'; -import { sanitizeForFilePath } from './utils.js'; +import os from "os"; +import fs from "fs"; +import path from "path"; +import { sanitizeForFilePath } from "./utils.js"; import type { Cookie } from "playwright-core"; -import type { Config } from '../config.js'; -import { AvailableModelSchema } from '@browserbasehq/stagehand'; +import type { Config } from "../config.js"; +import { AvailableModelSchema } from "@browserbasehq/stagehand"; -export type ToolCapability = 'core' | string; +export type ToolCapability = "core" | string; // Define Command Line Options Structure export type CLIOptions = { @@ -61,15 +61,19 @@ export async function resolveConfig(cliOptions: CLIOptions): Promise { console.warn("Warning: BROWSERBASE_API_KEY environment variable not set."); } if (!mergedConfig.browserbaseProjectId) { - console.warn("Warning: BROWSERBASE_PROJECT_ID environment variable not set."); + console.warn( + "Warning: BROWSERBASE_PROJECT_ID environment variable not set.", + ); } return mergedConfig; } // Create Config structure based on CLI options -export async function configFromCLIOptions(cliOptions: CLIOptions): Promise { - return { +export async function configFromCLIOptions( + cliOptions: CLIOptions, +): Promise { + return { browserbaseApiKey: cliOptions.browserbaseApiKey, browserbaseProjectId: cliOptions.browserbaseProjectId, server: { @@ -87,12 +91,15 @@ export async function configFromCLIOptions(cliOptions: CLIOptions): Promise { +export async function outputFile( + config: Config, + name: string, +): Promise { const outputDir = os.tmpdir(); await fs.promises.mkdir(outputDir, { recursive: true }); const sanitizedName = sanitizeForFilePath(name); @@ -103,7 +110,7 @@ export async function outputFile(config: Config, name: string): Promise function pickDefined(obj: T | undefined): Partial { if (!obj) return {}; return Object.fromEntries( - Object.entries(obj).filter(([_, v]) => v !== undefined) + Object.entries(obj).filter(([, v]) => v !== undefined), ) as Partial; } @@ -111,35 +118,35 @@ function pickDefined(obj: T | undefined): Partial { function mergeConfig(base: Config, overrides: Config): Config { const baseFiltered = pickDefined(base); const overridesFiltered = pickDefined(overrides); - + // Create the result object const result = { ...baseFiltered } as Config; - + // For each property in overrides for (const [key, value] of Object.entries(overridesFiltered)) { - if (key === 'context' && value && result.context) { + if (key === "context" && value && result.context) { // Special handling for context object to ensure deep merge result.context = { ...result.context, - ...(value as Config['context']) + ...(value as Config["context"]), }; } else if ( - value && - typeof value === 'object' && - !Array.isArray(value) && - result[key as keyof Config] && - typeof result[key as keyof Config] === 'object' + value && + typeof value === "object" && + !Array.isArray(value) && + result[key as keyof Config] && + typeof result[key as keyof Config] === "object" ) { // Deep merge for other nested objects result[key as keyof Config] = { ...(result[key as keyof Config] as object), - ...value - } as any; + ...value, + } as unknown; } else { // Simple override for primitives, arrays, etc. - result[key as keyof Config] = value as any; + result[key as keyof Config] = value as unknown; } } - + return result; -} \ No newline at end of file +} diff --git a/src/context.ts b/src/context.ts index 011eb68..49127a5 100644 --- a/src/context.ts +++ b/src/context.ts @@ -1,12 +1,16 @@ import type { Stagehand } from "@browserbasehq/stagehand"; import { Server } from "@modelcontextprotocol/sdk/server/index.js"; import type { Config } from "../config.js"; -import { CallToolResult, TextContent, ImageContent } from "@modelcontextprotocol/sdk/types.js"; +import { + CallToolResult, + TextContent, + ImageContent, +} from "@modelcontextprotocol/sdk/types.js"; import { listResources, readResource } from "./resources.js"; -import { - getSession, - defaultSessionId, - type BrowserSession +import { + getSession, + defaultSessionId, + type BrowserSession, } from "./sessionManager.js"; export type ToolActionResult = @@ -31,7 +35,9 @@ export class Context { /** * Gets the Stagehand instance for the current session from SessionManager */ - public async getStagehand(sessionId: string = this.currentSessionId): Promise { + public async getStagehand( + sessionId: string = this.currentSessionId, + ): Promise { const session = await getSession(sessionId, this.config); if (!session) { throw new Error(`No session found for ID: ${sessionId}`); @@ -45,12 +51,18 @@ export class Context { if (session && session.page && !session.page.isClosed()) { return session.page; } - + return null; } - public async getActiveBrowser(createIfMissing: boolean = true): Promise { - const session = await getSession(this.currentSessionId, this.config, createIfMissing); + public async getActiveBrowser( + createIfMissing: boolean = true, + ): Promise { + const session = await getSession( + this.currentSessionId, + this.config, + createIfMissing, + ); if (!session || !session.browser || !session.browser.isConnected()) { return null; } @@ -59,33 +71,47 @@ export class Context { async run(tool: any, args: any): Promise { try { - console.error(`Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`); - + console.error( + `Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`, + ); + // Check if this tool has a handle method (new tool system) if ("handle" in tool && typeof tool.handle === "function") { const toolResult = await tool.handle(this as any, args); - + if (toolResult?.action) { const actionResult = await toolResult.action(); const content = actionResult?.content || []; - + return { - content: Array.isArray(content) ? content : [{ type: "text", text: "Action completed successfully." }], + content: Array.isArray(content) + ? content + : [{ type: "text", text: "Action completed successfully." }], isError: false, }; } else { return { - content: [{ type: "text", text: `${tool.schema.name} completed successfully.` }], + content: [ + { + type: "text", + text: `${tool.schema.name} completed successfully.`, + }, + ], isError: false, }; } } else { // Fallback for any legacy tools without handle method - throw new Error(`Tool ${tool.schema.name} does not have a handle method`); + throw new Error( + `Tool ${tool.schema.name} does not have a handle method`, + ); } } catch (error) { - const errorMessage = error instanceof Error ? error.message : String(error); - console.error(`Tool ${tool.schema?.name || 'unknown'} failed: ${errorMessage}`); + const errorMessage = + error instanceof Error ? error.message : String(error); + console.error( + `Tool ${tool.schema?.name || "unknown"} failed: ${errorMessage}`, + ); return { content: [{ type: "text", text: `Error: ${errorMessage}` }], isError: true, @@ -101,8 +127,11 @@ export class Context { return listResources(); } + /** + * Read a resource by URI + * Documentation: https://modelcontextprotocol.io/docs/concepts/resources + */ readResource(uri: string) { return readResource(uri); } - -} \ No newline at end of file +} diff --git a/src/index.ts b/src/index.ts index b7233df..5010632 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,63 +1,113 @@ import dotenv from "dotenv"; dotenv.config(); -import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js'; -import { z } from 'zod'; -import type { Tool } from "./tools/tool.js"; +import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js"; +import { z } from "zod"; +import type { Tool, InputType } from "./tools/tool.js"; import { Context } from "./context.js"; import type { Config } from "../config.js"; import { TOOLS } from "./tools/index.js"; import { AvailableModelSchema } from "@browserbasehq/stagehand"; +import { PROMPTS, getPrompt } from "./prompts.js"; +import { + ListResourcesRequestSchema, + ReadResourceRequestSchema, + ListResourceTemplatesRequestSchema, + ListPromptsRequestSchema, + GetPromptRequestSchema, +} from "@modelcontextprotocol/sdk/types.js"; + +const cookieSchema = z.object({ + name: z.string(), + value: z.string(), + domain: z.string(), + path: z.string().optional(), + expires: z.number().optional(), + httpOnly: z.boolean().optional(), + secure: z.boolean().optional(), + sameSite: z.enum(["Strict", "Lax", "None"]).optional(), +}); // Configuration schema for Smithery - matches existing Config interface +// @ts-expect-error Type instantiation is excessively deep and possibly infinite with complex Zod schemas export const configSchema = z.object({ browserbaseApiKey: z.string().describe("The Browserbase API Key to use"), - browserbaseProjectId: z.string().describe("The Browserbase Project ID to use"), - proxies: z.boolean().optional().describe("Whether or not to use Browserbase proxies"), - advancedStealth: z.boolean().optional().describe("Use advanced stealth mode. Only available to Browserbase Scale Plan users"), - context: z.object({ - contextId: z.string().optional().describe("The ID of the context to use"), - persist: z.boolean().optional().describe("Whether or not to persist the context") - }).optional(), - viewPort: z.object({ - browserWidth: z.number().optional().describe("The width of the browser"), - browserHeight: z.number().optional().describe("The height of the browser") - }).optional(), - cookies: z.array(z.object({ // Playwright Cookies Type in Zod format - name: z.string(), - value: z.string(), - domain: z.string(), - path: z.string().optional(), - expires: z.number().optional(), - httpOnly: z.boolean().optional(), - secure: z.boolean().optional(), - sameSite: z.enum(['Strict', 'Lax', 'None']).optional() - })).optional().describe("Cookies to inject into the Browserbase context"), - server: z.object({ - port: z.number().optional().describe("The port to listen on for SSE or MCP transport"), - host: z.string().optional().describe("The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces") - }).optional(), + browserbaseProjectId: z + .string() + .describe("The Browserbase Project ID to use"), + proxies: z + .boolean() + .optional() + .describe("Whether or not to use Browserbase proxies"), + advancedStealth: z + .boolean() + .optional() + .describe( + "Use advanced stealth mode. Only available to Browserbase Scale Plan users", + ), + context: z + .object({ + contextId: z.string().optional().describe("The ID of the context to use"), + persist: z + .boolean() + .optional() + .describe("Whether or not to persist the context"), + }) + .optional(), + viewPort: z + .object({ + browserWidth: z.number().optional().describe("The width of the browser"), + browserHeight: z + .number() + .optional() + .describe("The height of the browser"), + }) + .optional(), + cookies: z + .array(cookieSchema) + .optional() + .describe("Cookies to inject into the Browserbase context"), + server: z + .object({ + port: z + .number() + .optional() + .describe("The port to listen on for SSE or MCP transport"), + host: z + .string() + .optional() + .describe( + "The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces", + ), + }) + .optional(), modelName: AvailableModelSchema.optional().describe( - "The model to use for Stagehand (default: google/gemini-2.0-flash)" - ), + "The model to use for Stagehand (default: google/gemini-2.0-flash)", + ), // Already an existing Zod Enum }); // Default function for Smithery export default function ({ config }: { config: z.infer }) { if (!config.browserbaseApiKey) { - throw new Error('browserbaseApiKey is required'); + throw new Error("browserbaseApiKey is required"); } if (!config.browserbaseProjectId) { - throw new Error('browserbaseProjectId is required'); + throw new Error("browserbaseProjectId is required"); } const server = new McpServer({ - name: 'Browserbase MCP Server', - version: '1.0.6', + name: "Browserbase MCP Server", + version: "2.0.0", capabilities: { - logging: {} - } + resources: { + subscribe: true, + listChanged: true, + }, + prompts: { + listChanged: true, + }, + }, }); const internalConfig: Config = config as Config; @@ -65,12 +115,49 @@ export default function ({ config }: { config: z.infer }) { // Create the context, passing server instance and config const context = new Context(server.server, internalConfig); - const tools: Tool[] = [ - ...TOOLS, - ]; + server.server.registerCapabilities({ + resources: { + subscribe: true, + listChanged: true, + }, + prompts: { + listChanged: true, + }, + }); + + // Add resource handlers + server.server.setRequestHandler(ListResourcesRequestSchema, async () => { + return context.listResources(); + }); + + server.server.setRequestHandler( + ReadResourceRequestSchema, + async (request) => { + return context.readResource(request.params.uri); + }, + ); + + server.server.setRequestHandler( + ListResourceTemplatesRequestSchema, + async () => { + return { resourceTemplates: [] }; + }, + ); + + // Add prompt handlers + server.server.setRequestHandler(ListPromptsRequestSchema, async () => { + return { prompts: PROMPTS }; + }); + + server.server.setRequestHandler(GetPromptRequestSchema, async (request) => { + const prompt = getPrompt(request.params.name); + return prompt; + }); + + const tools: Tool[] = [...TOOLS]; // Register each tool with the Smithery server - tools.forEach(tool => { + tools.forEach((tool) => { if (tool.schema.inputSchema instanceof z.ZodObject) { server.tool( tool.schema.name, @@ -81,18 +168,23 @@ export default function ({ config }: { config: z.infer }) { const result = await context.run(tool, params); return result; } catch (error) { - const errorMessage = error instanceof Error ? error.message : String(error); - process.stderr.write(`[Smithery Error] ${new Date().toISOString()} Error running tool ${tool.schema.name}: ${errorMessage}\n`); - throw new Error(`Failed to run tool '${tool.schema.name}': ${errorMessage}`); + const errorMessage = + error instanceof Error ? error.message : String(error); + process.stderr.write( + `[Smithery Error] ${new Date().toISOString()} Error running tool ${tool.schema.name}: ${errorMessage}\n`, + ); + throw new Error( + `Failed to run tool '${tool.schema.name}': ${errorMessage}`, + ); } - } + }, ); } else { console.warn( - `Tool "${tool.schema.name}" has an input schema that is not a ZodObject. Schema type: ${tool.schema.inputSchema.constructor.name}` + `Tool "${tool.schema.name}" has an input schema that is not a ZodObject. Schema type: ${tool.schema.inputSchema.constructor.name}`, ); } }); return server.server; -} \ No newline at end of file +} diff --git a/src/program.ts b/src/program.ts index c1ac1ec..1cc53eb 100644 --- a/src/program.ts +++ b/src/program.ts @@ -1,13 +1,13 @@ -import { program } from 'commander'; -import * as fs from 'fs'; -import * as path from 'path'; -import { fileURLToPath } from 'url'; +import { program } from "commander"; +import * as fs from "fs"; +import * as path from "path"; +import { fileURLToPath } from "url"; -import createServerFunction from './index.js'; -import { ServerList } from './server.js'; -import { startHttpTransport, startStdioTransport } from './transport.js'; +import createServerFunction from "./index.js"; +import { ServerList } from "./server.js"; +import { startHttpTransport, startStdioTransport } from "./transport.js"; -import { resolveConfig } from './config.js'; +import { resolveConfig } from "./config.js"; let __filename: string; let __dirname: string; @@ -18,42 +18,63 @@ try { __dirname = path.dirname(__filename); } catch { // Fallback for CommonJS or when import.meta is not available - __filename = (globalThis as any).__filename || process.cwd() + '/dist/program.js'; + __filename = + (globalThis as any).__filename || process.cwd() + "/dist/program.js"; __dirname = path.dirname(__filename); } // Load package.json using fs -const packageJSONPath = path.resolve(__dirname, '../package.json'); +const packageJSONPath = path.resolve(__dirname, "../package.json"); const packageJSONBuffer = fs.readFileSync(packageJSONPath); const packageJSON = JSON.parse(packageJSONBuffer.toString()); program - .version('Version ' + packageJSON.version) - .name(packageJSON.name) - .option('--browserbaseApiKey ', 'The Browserbase API Key to use') - .option('--browserbaseProjectId ', 'The Browserbase Project ID to use') - .option('--proxies', 'Use Browserbase proxies.') - .option('--advancedStealth', 'Use advanced stealth mode. Only available to Browserbase Scale Plan users.') - .option('--contextId ', 'Browserbase Context ID to use.') - .option('--persist [boolean]', 'Whether to persist the Browserbase context', true) - .option('--port ', 'Port to listen on for SSE transport.') - .option('--host ', 'Host to bind server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces.') - .option('--cookies [json]', 'JSON array of cookies to inject into the browser. Format: [{"name":"cookie1","value":"val1","domain":"example.com"}, ...]') - .option('--browserWidth ', 'Browser width to use for the browser.') - .option('--browserHeight ', 'Browser height to use for the browser.') - .option('--modelName ', 'The model to use for Stagehand (default: google/gemini-2.0-flash)') - .action(async options => { - const config = await resolveConfig(options); - const serverList = new ServerList(async() => createServerFunction( - { config: config as Required> & typeof config } - )); - setupExitWatchdog(serverList); + .version("Version " + packageJSON.version) + .name(packageJSON.name) + .option("--browserbaseApiKey ", "The Browserbase API Key to use") + .option("--browserbaseProjectId ", "The Browserbase Project ID to use") + .option("--proxies", "Use Browserbase proxies.") + .option( + "--advancedStealth", + "Use advanced stealth mode. Only available to Browserbase Scale Plan users.", + ) + .option("--contextId ", "Browserbase Context ID to use.") + .option( + "--persist [boolean]", + "Whether to persist the Browserbase context", + true, + ) + .option("--port ", "Port to listen on for SSE transport.") + .option( + "--host ", + "Host to bind server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces.", + ) + .option( + "--cookies [json]", + 'JSON array of cookies to inject into the browser. Format: [{"name":"cookie1","value":"val1","domain":"example.com"}, ...]', + ) + .option("--browserWidth ", "Browser width to use for the browser.") + .option("--browserHeight ", "Browser height to use for the browser.") + .option( + "--modelName ", + "The model to use for Stagehand (default: google/gemini-2.0-flash)", + ) + .action(async (options) => { + const config = await resolveConfig(options); + const serverList = new ServerList(async () => + createServerFunction({ + config: config as Required< + Pick + > & + typeof config, + }), + ); + setupExitWatchdog(serverList); - if (options.port) - startHttpTransport(+options.port, options.host, serverList); - else - await startStdioTransport(serverList); - }); + if (options.port) + startHttpTransport(+options.port, options.host, serverList); + else await startStdioTransport(serverList); + }); function setupExitWatchdog(serverList: ServerList) { const handleExit = async () => { @@ -62,9 +83,9 @@ function setupExitWatchdog(serverList: ServerList) { process.exit(0); }; - process.stdin.on('close', handleExit); - process.on('SIGINT', handleExit); - process.on('SIGTERM', handleExit); + process.stdin.on("close", handleExit); + process.on("SIGINT", handleExit); + process.on("SIGTERM", handleExit); } -program.parse(process.argv); \ No newline at end of file +program.parse(process.argv); diff --git a/src/prompts.ts b/src/prompts.ts index 83b6cc9..ff62aea 100644 --- a/src/prompts.ts +++ b/src/prompts.ts @@ -9,8 +9,8 @@ export const PROMPTS = [ { name: "click_search_button", description: "A prompt template for clicking on a search button", - arguments: [] // No arguments required for this specific prompt - } + arguments: [], // No arguments required for this specific prompt + }, ]; /** @@ -21,18 +21,19 @@ export const PROMPTS = [ export function getPrompt(name: string) { if (name === "click_search_button") { return { - description: "This prompt provides instructions for clicking on a search button", + description: + "This prompt provides instructions for clicking on a search button", messages: [ { role: "user", content: { type: "text", - text: "Please click on the search button" - } - } - ] + text: "Please click on the search button", + }, + }, + ], }; } - + throw new Error(`Invalid prompt name: ${name}`); -} \ No newline at end of file +} diff --git a/src/resources.ts b/src/resources.ts index 7250966..f5a6c69 100644 --- a/src/resources.ts +++ b/src/resources.ts @@ -1,6 +1,7 @@ /** * Resources module for the Stagehand MCP server * Contains resources definitions and handlers for resource-related requests + * Docs: https://modelcontextprotocol.io/docs/concepts/resources */ // Define the resources @@ -17,14 +18,14 @@ export const screenshots = new Map(); * @returns A list of available resources including screenshots */ export function listResources() { - return { + return { resources: [ ...Array.from(screenshots.keys()).map((name) => ({ uri: `screenshot://${name}`, mimeType: "image/png", name: `Screenshot: ${name}`, })), - ] + ], }; } @@ -59,4 +60,4 @@ export function readResource(uri: string) { } throw new Error(`Resource not found: ${uri}`); -} \ No newline at end of file +} diff --git a/src/server.ts b/src/server.ts index de86541..1c5b833 100644 --- a/src/server.ts +++ b/src/server.ts @@ -17,11 +17,10 @@ export class ServerList { async close(server: Server) { await server.close(); const index = this._servers.indexOf(server); - if (index !== -1) - this._servers.splice(index, 1); + if (index !== -1) this._servers.splice(index, 1); } async closeAll() { - await Promise.all(this._servers.map(server => server.close())); + await Promise.all(this._servers.map((server) => server.close())); } } diff --git a/src/sessionManager.ts b/src/sessionManager.ts index 9c1bc70..4b6ff15 100644 --- a/src/sessionManager.ts +++ b/src/sessionManager.ts @@ -1,9 +1,6 @@ -import { - Browser, - Page, -} from "playwright-core"; +import { Browser, Page } from "playwright-core"; import { AvailableModel, Stagehand } from "@browserbasehq/stagehand"; -import type { Config } from "../config.js"; +import type { Config } from "../config.js"; import type { Cookie } from "playwright-core"; export type BrowserSession = { @@ -34,7 +31,7 @@ export function setActiveSessionId(id: string): void { activeSessionId = id; } else { process.stderr.write( - `[SessionManager] WARN - Set active session failed for non-existent ID: ${id}\n` + `[SessionManager] WARN - Set active session failed for non-existent ID: ${id}\n`, ); } } @@ -52,20 +49,27 @@ export function getActiveSessionId(): string { * @param context Playwright browser context * @param cookies Array of cookies to add */ -export async function addCookiesToContext(context: any, cookies: Cookie[]): Promise { +export async function addCookiesToContext( + context: any, + cookies: Cookie[], +): Promise { if (!cookies || cookies.length === 0) { return; } - + try { - process.stderr.write(`[SessionManager] Adding ${cookies.length} cookies to browser context\n`); + process.stderr.write( + `[SessionManager] Adding ${cookies.length} cookies to browser context\n`, + ); await context.addCookies(cookies); - process.stderr.write(`[SessionManager] Successfully added cookies to browser context\n`); + process.stderr.write( + `[SessionManager] Successfully added cookies to browser context\n`, + ); } catch (error) { process.stderr.write( `[SessionManager] Error adding cookies to browser context: ${ error instanceof Error ? error.message : String(error) - }\n` + }\n`, ); } } @@ -74,7 +78,7 @@ export async function addCookiesToContext(context: any, cookies: Cookie[]): Prom export async function createNewBrowserSession( newSessionId: string, config: Config, - resumeSessionId?: string + resumeSessionId?: string, ): Promise { if (!config.browserbaseApiKey) { throw new Error("Browserbase API Key is missing in the configuration."); @@ -85,18 +89,19 @@ export async function createNewBrowserSession( try { process.stderr.write( - `[SessionManager] ${resumeSessionId ? 'Resuming' : 'Creating'} Stagehand session ${newSessionId}...\n` + `[SessionManager] ${resumeSessionId ? "Resuming" : "Creating"} Stagehand session ${newSessionId}...\n`, ); - + // Create and initialize Stagehand instance const stagehand = new Stagehand({ env: "BROWSERBASE", apiKey: config.browserbaseApiKey, projectId: config.browserbaseProjectId, - modelName: (config.modelName || "google/gemini-2.0-flash") as AvailableModel, + modelName: (config.modelName || + "google/gemini-2.0-flash") as AvailableModel, modelClientOptions: { apiKey: process.env.GEMINI_API_KEY, // TODO: change this in prod to just use our key - }, + }, ...(resumeSessionId && { browserbaseSessionID: resumeSessionId }), browserbaseSessionCreateParams: { projectId: config.browserbaseProjectId!, @@ -106,10 +111,12 @@ export async function createNewBrowserSession( width: config.viewPort?.browserWidth ?? 1024, height: config.viewPort?.browserHeight ?? 768, }, - context: config.context?.contextId ? { - id: config.context?.contextId, - persist: config.context?.persist ?? true, - } : undefined, + context: config.context?.contextId + ? { + id: config.context?.contextId, + persist: config.context?.persist ?? true, + } + : undefined, advancedStealth: config.advancedStealth ?? undefined, }, }, @@ -117,24 +124,24 @@ export async function createNewBrowserSession( console.error(`Stagehand[${newSessionId}]: ${logLine.message}`); }, }); - + await stagehand.init(); - + // Get the page and browser from Stagehand const page = stagehand.page as unknown as Page; const browser = page.context().browser(); - + if (!browser) { throw new Error("Failed to get browser from Stagehand page context"); } - + const browserbaseSessionId = stagehand.browserbaseSessionID; - + process.stderr.write( - `[SessionManager] Stagehand initialized with Browserbase session: ${browserbaseSessionId}\n` + `[SessionManager] Stagehand initialized with Browserbase session: ${browserbaseSessionId}\n`, ); process.stderr.write( - `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${browserbaseSessionId}\n` + `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${browserbaseSessionId}\n`, ); // Set up disconnect handler @@ -143,7 +150,7 @@ export async function createNewBrowserSession( browsers.delete(newSessionId); if (defaultBrowserSession && defaultBrowserSession.browser === browser) { process.stderr.write( - `[SessionManager] Disconnected (default): ${newSessionId}\n` + `[SessionManager] Disconnected (default): ${newSessionId}\n`, ); defaultBrowserSession = null; } @@ -152,21 +159,25 @@ export async function createNewBrowserSession( newSessionId !== defaultSessionId ) { process.stderr.write( - `[SessionManager] WARN - Active session disconnected, resetting to default: ${newSessionId}\n` + `[SessionManager] WARN - Active session disconnected, resetting to default: ${newSessionId}\n`, ); setActiveSessionId(defaultSessionId); } }); - + // Add cookies to the context if they are provided in the config - if (config.cookies && Array.isArray(config.cookies) && config.cookies.length > 0) { + if ( + config.cookies && + Array.isArray(config.cookies) && + config.cookies.length > 0 + ) { await addCookiesToContext(page.context(), config.cookies); } const sessionObj: BrowserSession = { browser, page, - sessionId: browserbaseSessionId!, + sessionId: browserbaseSessionId!, stagehand, }; @@ -178,7 +189,7 @@ export async function createNewBrowserSession( setActiveSessionId(newSessionId); process.stderr.write( - `[SessionManager] Session created and active: ${newSessionId}\n` + `[SessionManager] Session created and active: ${newSessionId}\n`, ); return sessionObj; @@ -188,33 +199,33 @@ export async function createNewBrowserSession( ? creationError.message : String(creationError); process.stderr.write( - `[SessionManager] Creating session ${newSessionId} failed: ${errorMessage}\n` - ); + `[SessionManager] Creating session ${newSessionId} failed: ${errorMessage}\n`, + ); throw new Error( - `Failed to create/connect session ${newSessionId}: ${errorMessage}` + `Failed to create/connect session ${newSessionId}: ${errorMessage}`, ); } } async function closeBrowserGracefully( session: BrowserSession | undefined | null, - sessionIdToLog: string + sessionIdToLog: string, ): Promise { // Close Stagehand instance which handles browser cleanup if (session?.stagehand) { try { process.stderr.write( - `[SessionManager] Closing Stagehand for session: ${sessionIdToLog}\n` + `[SessionManager] Closing Stagehand for session: ${sessionIdToLog}\n`, ); await session.stagehand.close(); process.stderr.write( - `[SessionManager] Successfully closed Stagehand and browser for session: ${sessionIdToLog}\n` + `[SessionManager] Successfully closed Stagehand and browser for session: ${sessionIdToLog}\n`, ); } catch (closeError) { process.stderr.write( `[SessionManager] WARN - Error closing Stagehand for session ${sessionIdToLog}: ${ closeError instanceof Error ? closeError.message : String(closeError) - }\n` + }\n`, ); } } @@ -222,7 +233,7 @@ async function closeBrowserGracefully( // Internal function to ensure default session export async function ensureDefaultSessionInternal( - config: Config + config: Config, ): Promise { const sessionId = defaultSessionId; let needsRecreation = false; @@ -230,7 +241,7 @@ export async function ensureDefaultSessionInternal( if (!defaultBrowserSession) { needsRecreation = true; process.stderr.write( - `[SessionManager] Default session ${sessionId} not found, creating.\n` + `[SessionManager] Default session ${sessionId} not found, creating.\n`, ); } else if ( !defaultBrowserSession.browser.isConnected() || @@ -238,7 +249,7 @@ export async function ensureDefaultSessionInternal( ) { needsRecreation = true; process.stderr.write( - `[SessionManager] Default session ${sessionId} is stale, recreating.\n` + `[SessionManager] Default session ${sessionId} is stale, recreating.\n`, ); await closeBrowserGracefully(defaultBrowserSession, sessionId); defaultBrowserSession = null; @@ -249,30 +260,33 @@ export async function ensureDefaultSessionInternal( try { defaultBrowserSession = await createNewBrowserSession(sessionId, config); return defaultBrowserSession; - } catch (error) { + } catch (creationError) { // Error during initial creation or recreation process.stderr.write( `[SessionManager] Initial/Recreation attempt for default session ${sessionId} failed. Error: ${ - error instanceof Error ? error.message : String(error) - }\n` + creationError instanceof Error + ? creationError.message + : String(creationError) + }\n`, ); // Attempt one more time after a failure process.stderr.write( - `[SessionManager] Retrying creation of default session ${sessionId} after error...\n` + `[SessionManager] Retrying creation of default session ${sessionId} after error...\n`, ); try { - defaultBrowserSession = await createNewBrowserSession(sessionId, config); + defaultBrowserSession = await createNewBrowserSession( + sessionId, + config, + ); return defaultBrowserSession; } catch (retryError) { const finalErrorMessage = - retryError instanceof Error - ? retryError.message - : String(retryError); + retryError instanceof Error ? retryError.message : String(retryError); process.stderr.write( - `[SessionManager] Failed to recreate default session ${sessionId} after retry: ${finalErrorMessage}\n` + `[SessionManager] Failed to recreate default session ${sessionId} after retry: ${finalErrorMessage}\n`, ); throw new Error( - `Failed to ensure default session ${sessionId} after initial error and retry: ${finalErrorMessage}` + `Failed to ensure default session ${sessionId} after initial error and retry: ${finalErrorMessage}`, ); } } @@ -287,14 +301,14 @@ export async function ensureDefaultSessionInternal( export async function getSession( sessionId: string, config: Config, - createIfMissing: boolean = true + createIfMissing: boolean = true, ): Promise { if (sessionId === defaultSessionId && createIfMissing) { try { return await ensureDefaultSessionInternal(config); } catch (error) { process.stderr.write( - `[SessionManager] Failed to get default session due to error in ensureDefaultSessionInternal for ${sessionId}. See previous messages for details.\n` + `[SessionManager] Failed to get default session due to error in ensureDefaultSessionInternal for ${sessionId}. See previous messages for details.\n`, ); return null; // Or rethrow if getSession failing for default is critical } @@ -302,11 +316,11 @@ export async function getSession( // For non-default sessions process.stderr.write(`[SessionManager] Getting session: ${sessionId}\n`); - let sessionObj = browsers.get(sessionId); + const sessionObj = browsers.get(sessionId); if (!sessionObj) { process.stderr.write( - `[SessionManager] WARN - Session not found in map: ${sessionId}\n` + `[SessionManager] WARN - Session not found in map: ${sessionId}\n`, ); return null; } @@ -314,13 +328,13 @@ export async function getSession( // Validate the found session if (!sessionObj.browser.isConnected() || sessionObj.page.isClosed()) { process.stderr.write( - `[SessionManager] WARN - Found session ${sessionId} is stale, removing.\n` + `[SessionManager] WARN - Found session ${sessionId} is stale, removing.\n`, ); await closeBrowserGracefully(sessionObj, sessionId); browsers.delete(sessionId); if (activeSessionId === sessionId) { process.stderr.write( - `[SessionManager] WARN - Invalidated active session ${sessionId}, resetting to default.\n` + `[SessionManager] WARN - Invalidated active session ${sessionId}, resetting to default.\n`, ); setActiveSessionId(defaultSessionId); } @@ -339,22 +353,20 @@ export async function getSession( * @param sessionId The session ID to clean up */ export function cleanupSession(sessionId: string): void { - process.stderr.write( - `[SessionManager] Cleaning up session: ${sessionId}\n` - ); - + process.stderr.write(`[SessionManager] Cleaning up session: ${sessionId}\n`); + // Remove from browsers map browsers.delete(sessionId); - + // Clear default session reference if this was the default if (sessionId === defaultSessionId && defaultBrowserSession) { defaultBrowserSession = null; } - + // Reset active session to default if this was the active one if (activeSessionId === sessionId) { process.stderr.write( - `[SessionManager] Cleaned up active session ${sessionId}, resetting to default.\n` + `[SessionManager] Cleaned up active session ${sessionId}, resetting to default.\n`, ); setActiveSessionId(defaultSessionId); } @@ -368,15 +380,15 @@ export async function closeAllSessions(): Promise { process.stderr.write(`[SessionManager] Closing session: ${id}\n`); closePromises.push( // Use the helper for consistent logging/error handling - closeBrowserGracefully(session, id) + closeBrowserGracefully(session, id), ); } try { await Promise.all(closePromises); - } catch(e) { + } catch (_e) { // Individual errors are caught and logged by closeBrowserGracefully process.stderr.write( - `[SessionManager] WARN - Some errors occurred during batch session closing. See individual messages.\n` + `[SessionManager] WARN - Some errors occurred during batch session closing. See individual messages.\n`, ); } diff --git a/src/tools/act.ts b/src/tools/act.ts index 66cb399..ead9868 100644 --- a/src/tools/act.ts +++ b/src/tools/act.ts @@ -4,35 +4,40 @@ import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; const ActInputSchema = z.object({ - action: z.string().describe( - "The action to perform. Should be as atomic and specific as possible, " + - "i.e. 'Click the sign in button' or 'Type 'hello' into the search input'. AVOID actions that are more than one " + - "step, i.e. 'Order me pizza' or 'Send an email to Paul asking him to call me'. The instruction should be just as specific as possible, " + - "and have a strong correlation to the text on the page. If unsure, use observe before using act." - ), - variables: z.object({}).optional().describe( - "Variables used in the action template. ONLY use variables if you're dealing " + - "with sensitive data or dynamic content. For example, if you're logging in to a website, " + - "you can use a variable for the password. When using variables, you MUST have the variable " + - "key in the action template. For example: {\"action\": \"Fill in the password\", \"variables\": {\"password\": \"123456\"}}" - ), + action: z + .string() + .describe( + "The action to perform. Should be as atomic and specific as possible, " + + "i.e. 'Click the sign in button' or 'Type 'hello' into the search input'. AVOID actions that are more than one " + + "step, i.e. 'Order me pizza' or 'Send an email to Paul asking him to call me'. The instruction should be just as specific as possible, " + + "and have a strong correlation to the text on the page. If unsure, use observe before using act.", + ), + variables: z + .object({}) + .optional() + .describe( + "Variables used in the action template. ONLY use variables if you're dealing " + + "with sensitive data or dynamic content. For example, if you're logging in to a website, " + + "you can use a variable for the password. When using variables, you MUST have the variable " + + 'key in the action template. For example: {"action": "Fill in the password", "variables": {"password": "123456"}}', + ), }); type ActInput = z.infer; const actSchema: ToolSchema = { - name: "stagehand_act", - description: + name: "browserbase_stagehand_act", + description: "Performs an action on a web page element. Act actions should be as atomic and " + - "specific as possible, i.e. \"Click the sign in button\" or \"Type 'hello' into the search input\". " + - "AVOID actions that are more than one step, i.e. \"Order me pizza\" or \"Send an email to Paul " + - "asking him to call me\".", + 'specific as possible, i.e. "Click the sign in button" or "Type \'hello\' into the search input". ' + + 'AVOID actions that are more than one step, i.e. "Order me pizza" or "Send an email to Paul ' + + 'asking him to call me".', inputSchema: ActInputSchema, }; async function handleAct( context: Context, - params: ActInput + params: ActInput, ): Promise { const action = async (): Promise => { try { @@ -42,7 +47,7 @@ async function handleAct( action: params.action, variables: params.variables, }); - + return { content: [ { @@ -69,4 +74,4 @@ const actTool: Tool = { handle: handleAct, }; -export default actTool; \ No newline at end of file +export default actTool; diff --git a/src/tools/extract.ts b/src/tools/extract.ts index 17d58f2..eec032e 100644 --- a/src/tools/extract.ts +++ b/src/tools/extract.ts @@ -4,30 +4,23 @@ import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; const ExtractInputSchema = z.object({ - instruction: z.string().describe( - "The specific instruction for what information to extract from the current page. " + - "Be as detailed and specific as possible about what you want to extract. For example: " + - "'Extract all product names and prices from the listing page' or 'Get the article title, " + - "author, and publication date from this blog post'. The more specific your instruction, " + - "the better the extraction results will be. Avoid vague instructions like 'get everything' " + - "or 'extract the data'. Instead, be explicit about the exact elements, text, or information you need." - ), - schema: z.string().describe( - "A JSON schema string that defines the exact structure and format of the data you want to extract. " + - "This schema should be a valid JSON string that describes the expected output format. For example: " + - "'{\"type\": \"object\", \"properties\": {\"title\": {\"type\": \"string\"}, \"price\": {\"type\": \"number\"}}}' " + - "or '{\"type\": \"array\", \"items\": {\"type\": \"object\", \"properties\": {\"name\": {\"type\": \"string\"}, " + - "\"description\": {\"type\": \"string\"}}}}'. The schema helps ensure the extracted data is properly " + - "formatted and structured. If the schema is invalid JSON, extraction will proceed without schema validation. " + - "Use this to specify exactly how you want the extracted information organized and typed." - ), + instruction: z + .string() + .describe( + "The specific instruction for what information to extract from the current page. " + + "Be as detailed and specific as possible about what you want to extract. For example: " + + "'Extract all product names and prices from the listing page' or 'Get the article title, " + + "author, and publication date from this blog post'. The more specific your instruction, " + + "the better the extraction results will be. Avoid vague instructions like 'get everything' " + + "or 'extract the data'. Instead, be explicit about the exact elements, text, or information you need.", + ), }); type ExtractInput = z.infer; const extractSchema: ToolSchema = { - name: "stagehand_extract", - description: + name: "browserbase_stagehand_extract", + description: "Extracts structured information and text content from the current web page based on specific instructions " + "and a defined schema. This tool is ideal for scraping data, gathering information, or pulling specific " + "content from web pages. Use this tool when you need to get text content, data, or information from a page " + @@ -40,29 +33,19 @@ const extractSchema: ToolSchema = { async function handleExtract( context: Context, - params: ExtractInput + params: ExtractInput, ): Promise { const action = async (): Promise => { try { const stagehand = await context.getStagehand(); - - let parsedSchema = null; - try { - parsedSchema = JSON.parse(params.schema); - } catch (error) { - throw new Error(`Invalid schema format: ${error instanceof Error ? error.message : 'Unknown error'}`); - } - const extraction = await stagehand.page.extract({ - instruction: params.instruction, - schema: parsedSchema // If schema not properly formatted, will just extract without given schema - }); + const extraction = await stagehand.page.extract(params.instruction); return { content: [ { type: "text", - text: `Extracted content:\n${extraction.join("\n")}`, + text: `Extracted content:\n${JSON.stringify(extraction, null, 2)}`, }, ], }; @@ -84,4 +67,4 @@ const extractTool: Tool = { handle: handleExtract, }; -export default extractTool; \ No newline at end of file +export default extractTool; diff --git a/src/tools/index.ts b/src/tools/index.ts index c1d911f..16711f0 100644 --- a/src/tools/index.ts +++ b/src/tools/index.ts @@ -24,4 +24,4 @@ export const TOOLS = [ screenshotTool, ]; -export const sessionManagementTools = sessionTools; \ No newline at end of file +export const sessionManagementTools = sessionTools; diff --git a/src/tools/navigate.ts b/src/tools/navigate.ts index fa97c02..acac0b2 100644 --- a/src/tools/navigate.ts +++ b/src/tools/navigate.ts @@ -10,7 +10,7 @@ const NavigateInputSchema = z.object({ type NavigateInput = z.infer; const navigateSchema: ToolSchema = { - name: "stagehand_navigate", + name: "browserbase_stagehand_navigate", description: "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otheriwse use https://google.com as the starting point", inputSchema: NavigateInputSchema, @@ -18,7 +18,7 @@ const navigateSchema: ToolSchema = { async function handleNavigate( context: Context, - params: NavigateInput + params: NavigateInput, ): Promise { const action = async (): Promise => { try { @@ -27,7 +27,7 @@ async function handleNavigate( throw new Error("No active page available"); } await page.goto(params.url, { waitUntil: "domcontentloaded" }); - + return { content: [ { @@ -58,4 +58,4 @@ const navigateTool: Tool = { handle: handleNavigate, }; -export default navigateTool; \ No newline at end of file +export default navigateTool; diff --git a/src/tools/observe.ts b/src/tools/observe.ts index 064e1cc..ec44889 100644 --- a/src/tools/observe.ts +++ b/src/tools/observe.ts @@ -4,26 +4,31 @@ import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; const ObserveInputSchema = z.object({ - instruction: z.string().describe( - "Detailed instruction for what specific elements or components to observe on the web page. " + - "This instruction must be extremely specific and descriptive. For example: 'Find the red login button " + - "in the top right corner', 'Locate the search input field with placeholder text', or 'Identify all " + - "clickable product cards on the page'. The more specific and detailed your instruction, the better " + - "the observation results will be. Avoid generic instructions like 'find buttons' or 'see elements'. " + - "Instead, describe the visual characteristics, location, text content, or functionality of the elements " + - "you want to observe. This tool is designed to help you identify interactive elements that you can " + - "later use with the act tool for performing actions like clicking, typing, or form submission." - ), - returnAction: z.boolean().optional().describe( - "Whether to return the action to perform on the element. If true, the action will be returned as a string. " + - "If false, the action will not be returned." - ), + instruction: z + .string() + .describe( + "Detailed instruction for what specific elements or components to observe on the web page. " + + "This instruction must be extremely specific and descriptive. For example: 'Find the red login button " + + "in the top right corner', 'Locate the search input field with placeholder text', or 'Identify all " + + "clickable product cards on the page'. The more specific and detailed your instruction, the better " + + "the observation results will be. Avoid generic instructions like 'find buttons' or 'see elements'. " + + "Instead, describe the visual characteristics, location, text content, or functionality of the elements " + + "you want to observe. This tool is designed to help you identify interactive elements that you can " + + "later use with the act tool for performing actions like clicking, typing, or form submission.", + ), + returnAction: z + .boolean() + .optional() + .describe( + "Whether to return the action to perform on the element. If true, the action will be returned as a string. " + + "If false, the action will not be returned.", + ), }); type ObserveInput = z.infer; const observeSchema: ToolSchema = { - name: "stagehand_observe", + name: "browserbase_stagehand_observe", description: "Observes and identifies specific interactive elements on the current web page that can be used for subsequent actions. " + "This tool is specifically designed for finding actionable (interactable) elements such as buttons, links, form fields, " + @@ -38,7 +43,7 @@ const observeSchema: ToolSchema = { async function handleObserve( context: Context, - params: ObserveInput + params: ObserveInput, ): Promise { const action = async (): Promise => { try { @@ -75,4 +80,4 @@ const observeTool: Tool = { handle: handleObserve, }; -export default observeTool; \ No newline at end of file +export default observeTool; diff --git a/src/tools/screenshot.ts b/src/tools/screenshot.ts index 0c0b2a6..ea7ee9f 100644 --- a/src/tools/screenshot.ts +++ b/src/tools/screenshot.ts @@ -11,7 +11,7 @@ const ScreenshotInputSchema = z.object({ type ScreenshotInput = z.infer; const screenshotSchema: ToolSchema = { - name: "screenshot", + name: "browserbase_screenshot", description: "Takes a screenshot of the current page. Use this tool to learn where you are on the page when controlling the browser with Stagehand. Only use this tool when the other tools are not sufficient to get the information you need.", inputSchema: ScreenshotInputSchema, @@ -19,7 +19,7 @@ const screenshotSchema: ToolSchema = { async function handleScreenshot( context: Context, - params: ScreenshotInput + params: ScreenshotInput, ): Promise { const action = async (): Promise => { try { @@ -34,13 +34,11 @@ async function handleScreenshot( // Convert buffer to base64 string and store in memory const screenshotBase64 = screenshotBuffer.toString("base64"); - const name = - `screenshot-${params.name}-${new Date() - .toISOString() - .replace(/:/g, "-")}` || - `screenshot-${new Date() - .toISOString() - .replace(/:/g, "-")}`; + const name = params.name + ? `screenshot-${params.name}-${new Date() + .toISOString() + .replace(/:/g, "-")}` + : `screenshot-${new Date().toISOString().replace(/:/g, "-")}`; screenshots.set(name, screenshotBase64); // Notify the client that the resources changed @@ -83,4 +81,4 @@ const screenshotTool: Tool = { handle: handleScreenshot, }; -export default screenshotTool; \ No newline at end of file +export default screenshotTool; diff --git a/src/tools/session.ts b/src/tools/session.ts index aa0fb70..6024b75 100644 --- a/src/tools/session.ts +++ b/src/tools/session.ts @@ -1,7 +1,7 @@ import { z } from "zod"; -import type { Tool, ToolSchema, ToolResult } from "./tool.js"; -import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { Tool, ToolSchema, ToolResult } from "./tool.js"; +import type { Context } from "../context.js"; +import type { ToolActionResult } from "../context.js"; // Import SessionManager functions import { @@ -20,23 +20,22 @@ const CreateSessionInputSchema = z.object({ .string() .optional() .describe( - "Optional session ID to use/reuse. If not provided or invalid, a new session is created." + "Optional session ID to use/reuse. If not provided or invalid, a new session is created.", ), }); type CreateSessionInput = z.infer; const createSessionSchema: ToolSchema = { - name: "browserbase_session_create", + name: "browserbase_session_create", description: - "Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand. This creates the browser session with all configuration flags (proxies, stealth, viewport, cookies, etc.) and initializes Stagehand to work with that session. Updates the active session.", + "Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand. This creates the browser session with all configuration flags (proxies, stealth, viewport, cookies, etc.) and initializes Stagehand to work with that session. Updates the active session.", inputSchema: CreateSessionInputSchema, }; - // Handle function for CreateSession using SessionManager async function handleCreateSession( context: Context, - params: CreateSessionInput + params: CreateSessionInput, ): Promise { const action = async (): Promise => { try { @@ -44,10 +43,10 @@ async function handleCreateSession( let targetSessionId: string; if (params.sessionId) { - const projectId = config.browserbaseProjectId || ''; + const projectId = config.browserbaseProjectId || ""; targetSessionId = `${params.sessionId}_${projectId}`; process.stderr.write( - `[tool.createSession] Attempting to create/assign session with specified ID: ${targetSessionId}` + `[tool.createSession] Attempting to create/assign session with specified ID: ${targetSessionId}`, ); } else { targetSessionId = defaultSessionId; @@ -58,21 +57,27 @@ async function handleCreateSession( session = await ensureDefaultSessionInternal(config); } else { // When user provides a sessionId, we want to resume that Browserbase session - session = await createNewBrowserSession(targetSessionId, config, params.sessionId); + session = await createNewBrowserSession( + targetSessionId, + config, + params.sessionId, + ); } if (!session || !session.browser || !session.page || !session.sessionId) { throw new Error( - `SessionManager failed to return a valid session object with actualSessionId for ID: ${targetSessionId}` + `SessionManager failed to return a valid session object with actualSessionId for ID: ${targetSessionId}`, ); } context.currentSessionId = targetSessionId; process.stderr.write( - `[tool.connected] Successfully connected to Browserbase session. Internal ID: ${targetSessionId}, Actual ID: ${session.sessionId}` + `[tool.connected] Successfully connected to Browserbase session. Internal ID: ${targetSessionId}, Actual ID: ${session.sessionId}`, ); - process.stderr.write(`[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.sessionId}`); + process.stderr.write( + `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.sessionId}`, + ); return { content: [ @@ -82,25 +87,21 @@ async function handleCreateSession( }, ], }; - } catch (error: any) { + } catch (error: unknown) { + const errorMessage = + error instanceof Error ? error.message : String(error); process.stderr.write( - `[tool.createSession] Action failed: ${ - error.message || String(error) - }` + `[tool.createSession] Action failed: ${errorMessage}`, ); // Re-throw to be caught by Context.run's error handling for actions - throw new Error( - `Failed to create Browserbase session: ${ - error.message || String(error) - }` - ); + throw new Error(`Failed to create Browserbase session: ${errorMessage}`); } }; // Return the ToolResult structure expected by Context.run return { - action: action, - waitForNetwork: false, + action: action, + waitForNetwork: false, }; } @@ -129,7 +130,7 @@ const closeSessionSchema: ToolSchema = { async function handleCloseSession( context: Context, - _params: CloseSessionInput + _params: CloseSessionInput, ): Promise { const action = async (): Promise => { // Store the current session ID before it's potentially changed. @@ -140,22 +141,26 @@ async function handleCloseSession( // Step 1: Attempt to get the session and close Stagehand let browserbaseSessionId: string | undefined; try { - const session = await getSession(previousSessionId, context.config, false); - + const session = await getSession( + previousSessionId, + context.config, + false, + ); + if (session && session.stagehand) { // Store the actual Browserbase session ID for the replay URL browserbaseSessionId = session.sessionId; - + process.stderr.write( - `[tool.closeSession] Attempting to close Stagehand for session: ${previousSessionId || 'default'} (Browserbase ID: ${browserbaseSessionId})` + `[tool.closeSession] Attempting to close Stagehand for session: ${previousSessionId || "default"} (Browserbase ID: ${browserbaseSessionId})`, ); - + // Use Stagehand's close method which handles browser cleanup properly await session.stagehand.close(); stagehandClosedSuccessfully = true; - + process.stderr.write( - `[tool.closeSession] Stagehand and browser connection for session (${previousSessionId}) closed successfully.` + `[tool.closeSession] Stagehand and browser connection for session (${previousSessionId}) closed successfully.`, ); // Clean up the session from tracking @@ -163,19 +168,19 @@ async function handleCloseSession( if (browserbaseSessionId) { process.stderr.write( - `[tool.closeSession] View session replay at https://www.browserbase.com/sessions/${browserbaseSessionId}` + `[tool.closeSession] View session replay at https://www.browserbase.com/sessions/${browserbaseSessionId}`, ); } - } else { process.stderr.write( - `[tool.closeSession] No Stagehand instance found for session: ${previousSessionId || 'default/unknown'}` + `[tool.closeSession] No Stagehand instance found for session: ${previousSessionId || "default/unknown"}`, ); } - } catch (error: any) { - stagehandCloseErrorMessage = error.message || String(error); + } catch (error: unknown) { + stagehandCloseErrorMessage = + error instanceof Error ? error.message : String(error); process.stderr.write( - `[tool.closeSession] Error retrieving or closing Stagehand (session ID was ${previousSessionId || 'default/unknown'}): ${stagehandCloseErrorMessage}` + `[tool.closeSession] Error retrieving or closing Stagehand (session ID was ${previousSessionId || "default/unknown"}): ${stagehandCloseErrorMessage}`, ); } @@ -183,18 +188,18 @@ async function handleCloseSession( const oldContextSessionId = context.currentSessionId; context.currentSessionId = defaultSessionId; process.stderr.write( - `[tool.closeSession] Session context reset to default. Previous context session ID was ${oldContextSessionId || 'default/unknown'}.` + `[tool.closeSession] Session context reset to default. Previous context session ID was ${oldContextSessionId || "default/unknown"}.`, ); // Step 3: Determine the result message if (stagehandCloseErrorMessage && !stagehandClosedSuccessfully) { throw new Error( - `Failed to close the Stagehand session (session ID in context was ${previousSessionId || 'default/unknown'}). Error: ${stagehandCloseErrorMessage}. Session context has been reset to default.` + `Failed to close the Stagehand session (session ID in context was ${previousSessionId || "default/unknown"}). Error: ${stagehandCloseErrorMessage}. Session context has been reset to default.`, ); } if (stagehandClosedSuccessfully) { - let successMessage = `Browserbase session (${previousSessionId || 'default'}) closed successfully via Stagehand. Context reset to default.`; + let successMessage = `Browserbase session (${previousSessionId || "default"}) closed successfully via Stagehand. Context reset to default.`; if (browserbaseSessionId && previousSessionId !== defaultSessionId) { successMessage += ` View replay at https://browserbase.com/sessions/${browserbaseSessionId}`; } @@ -202,9 +207,10 @@ async function handleCloseSession( } // No Stagehand instance was found - let infoMessage = "No active Stagehand session found to close. Session context has been reset to default."; + let infoMessage = + "No active Stagehand session found to close. Session context has been reset to default."; if (previousSessionId && previousSessionId !== defaultSessionId) { - infoMessage = `No active Stagehand session found for session ID '${previousSessionId}'. The context has been reset to default.`; + infoMessage = `No active Stagehand session found for session ID '${previousSessionId}'. The context has been reset to default.`; } return { content: [{ type: "text", text: infoMessage }] }; }; @@ -221,4 +227,4 @@ const closeSessionTool: Tool = { handle: handleCloseSession, }; -export default [createSessionTool, closeSessionTool]; \ No newline at end of file +export default [createSessionTool, closeSessionTool]; diff --git a/src/tools/tool.ts b/src/tools/tool.ts index a78f231..e7622d5 100644 --- a/src/tools/tool.ts +++ b/src/tools/tool.ts @@ -1,9 +1,9 @@ -import type { ImageContent, TextContent } from '@modelcontextprotocol/sdk/types.js'; -import type { z } from 'zod'; -import type { Context } from '../context.js'; -import type { BrowserSession } from '../sessionManager.js'; -import type { Server } from '@modelcontextprotocol/sdk/server/index.js'; -import type { Config } from '../../config.js'; +import type { + ImageContent, + TextContent, +} from "@modelcontextprotocol/sdk/types.js"; +import type { z } from "zod"; +import type { Context } from "../context.js"; export type ToolSchema = { name: string; @@ -14,7 +14,10 @@ export type ToolSchema = { // Export InputType export type InputType = z.Schema; -export type ToolActionResult = { content?: (ImageContent | TextContent)[] } | undefined | void; +export type ToolActionResult = + | { content?: (ImageContent | TextContent)[] } + | undefined + | void; export type ToolResult = { action?: () => Promise; @@ -27,18 +30,10 @@ export type Tool = { handle: (context: Context, params: z.output) => Promise; }; -export function defineTool(tool: Tool): Tool { +export function defineTool( + tool: Tool, +): Tool { return tool; } -export {}; // Ensure this is treated as a module - -// Represents the execution context for a tool -export interface ToolContext { - page: BrowserSession['page']; - browser: BrowserSession['browser']; - server: Server; - sessionId: string; - config: Config; - context: Context; // The main context instance -} \ No newline at end of file +export {}; // Ensure this is treated as a module diff --git a/src/transport.ts b/src/transport.ts index a69177c..0a266ad 100644 --- a/src/transport.ts +++ b/src/transport.ts @@ -1,39 +1,45 @@ -import http from 'node:http'; -import assert from 'node:assert'; -import crypto from 'node:crypto'; +import http from "node:http"; +import assert from "node:assert"; +import crypto from "node:crypto"; -import { ServerList } from './server.js'; -import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js'; -import { SSEServerTransport } from '@modelcontextprotocol/sdk/server/sse.js'; -import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js'; +import { ServerList } from "./server.js"; +import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js"; +import { SSEServerTransport } from "@modelcontextprotocol/sdk/server/sse.js"; +import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js"; export async function startStdioTransport(serverList: ServerList) { const server = await serverList.create(); await server.connect(new StdioServerTransport()); } -async function handleSSE(req: http.IncomingMessage, res: http.ServerResponse, url: URL, serverList: ServerList, sessions: Map) { - if (req.method === 'POST') { - const sessionId = url.searchParams.get('sessionId'); +async function handleSSE( + req: http.IncomingMessage, + res: http.ServerResponse, + url: URL, + serverList: ServerList, + sessions: Map, +) { + if (req.method === "POST") { + const sessionId = url.searchParams.get("sessionId"); if (!sessionId) { res.statusCode = 400; - return res.end('Missing sessionId'); + return res.end("Missing sessionId"); } const transport = sessions.get(sessionId); if (!transport) { res.statusCode = 404; - return res.end('Session not found'); + return res.end("Session not found"); } return await transport.handlePostMessage(req, res); - } else if (req.method === 'GET') { - const transport = new SSEServerTransport('/sse', res); + } else if (req.method === "GET") { + const transport = new SSEServerTransport("/sse", res); sessions.set(transport.sessionId, transport); const server = await serverList.create(); - res.on('close', () => { + res.on("close", () => { sessions.delete(transport.sessionId); - serverList.close(server).catch(e => { + serverList.close(server).catch((e) => { console.error(e); }); }); @@ -41,31 +47,35 @@ async function handleSSE(req: http.IncomingMessage, res: http.ServerResponse, ur } res.statusCode = 405; - res.end('Method not allowed'); + res.end("Method not allowed"); } -async function handleStreamable(req: http.IncomingMessage, res: http.ServerResponse, serverList: ServerList, sessions: Map) { - const sessionId = req.headers['mcp-session-id'] as string | undefined; +async function handleStreamable( + req: http.IncomingMessage, + res: http.ServerResponse, + serverList: ServerList, + sessions: Map, +) { + const sessionId = req.headers["mcp-session-id"] as string | undefined; if (sessionId) { const transport = sessions.get(sessionId); if (!transport) { res.statusCode = 404; - res.end('Session not found'); + res.end("Session not found"); return; } return await transport.handleRequest(req, res); } - if (req.method === 'POST') { + if (req.method === "POST") { const transport = new StreamableHTTPServerTransport({ sessionIdGenerator: () => crypto.randomUUID(), - onsessioninitialized: sessionId => { + onsessioninitialized: (sessionId) => { sessions.set(sessionId, transport); - } + }, }); transport.onclose = () => { - if (transport.sessionId) - sessions.delete(transport.sessionId); + if (transport.sessionId) sessions.delete(transport.sessionId); }; const server = await serverList.create(); await server.connect(transport); @@ -73,45 +83,52 @@ async function handleStreamable(req: http.IncomingMessage, res: http.ServerRespo } res.statusCode = 400; - res.end('Invalid request'); + res.end("Invalid request"); } -export function startHttpTransport(port: number, hostname: string | undefined, serverList: ServerList) { +export function startHttpTransport( + port: number, + hostname: string | undefined, + serverList: ServerList, +) { const sseSessions = new Map(); const streamableSessions = new Map(); const httpServer = http.createServer(async (req, res) => { const url = new URL(`http://localhost${req.url}`); - if (url.pathname.startsWith('/mcp')) + if (url.pathname.startsWith("/mcp")) await handleStreamable(req, res, serverList, streamableSessions); - else - await handleSSE(req, res, url, serverList, sseSessions); + else await handleSSE(req, res, url, serverList, sseSessions); }); httpServer.listen(port, hostname, () => { const address = httpServer.address(); - assert(address, 'Could not bind server socket'); + assert(address, "Could not bind server socket"); let url: string; - if (typeof address === 'string') { + if (typeof address === "string") { url = address; } else { const resolvedPort = address.port; - let resolvedHost = address.family === 'IPv4' ? address.address : `[${address.address}]`; - if (resolvedHost === '0.0.0.0' || resolvedHost === '[::]') - resolvedHost = 'localhost'; + let resolvedHost = + address.family === "IPv4" ? address.address : `[${address.address}]`; + if (resolvedHost === "0.0.0.0" || resolvedHost === "[::]") + resolvedHost = "localhost"; url = `http://${resolvedHost}:${resolvedPort}`; } const message = [ `Listening on ${url}`, - 'Put this in your client config:', - JSON.stringify({ - 'mcpServers': { - 'browserbase': { - 'url': `${url}/sse` - } - } - }, undefined, 2), - 'If your client supports streamable HTTP, you can use the /mcp endpoint instead.', - ].join('\n'); - // eslint-disable-next-line no-console + "Put this in your client config:", + JSON.stringify( + { + mcpServers: { + browserbase: { + url: `${url}/sse`, + }, + }, + }, + undefined, + 2, + ), + "If your client supports streamable HTTP, you can use the /mcp endpoint instead.", + ].join("\n"); console.log(message); }); -} \ No newline at end of file +} diff --git a/src/utils.ts b/src/utils.ts index e35e30e..be464d4 100644 --- a/src/utils.ts +++ b/src/utils.ts @@ -3,26 +3,26 @@ * @param message The message to sanitize * @returns A sanitized JSON string */ -export function sanitizeMessage(message: any): string { +export function sanitizeMessage(message: unknown): string { try { // Ensure the message is properly stringified JSON - if (typeof message === 'string') { + if (typeof message === "string") { JSON.parse(message); // Validate JSON structure return message; } return JSON.stringify(message); - } catch (error) { + } catch { return JSON.stringify({ - jsonrpc: '2.0', + jsonrpc: "2.0", error: { code: -32700, - message: 'Parse error', + message: "Parse error", }, id: null, }); } -} +} export function sanitizeForFilePath(s: string) { - return s.replace(/[^a-zA-Z0-9_.-]/g, '_'); // More robust sanitization -} \ No newline at end of file + return s.replace(/[^a-zA-Z0-9_.-]/g, "_"); // More robust sanitization +} diff --git a/tsconfig.json b/tsconfig.json index 316a446..7177886 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -9,7 +9,8 @@ "forceConsistentCasingInFileNames": true, "resolveJsonModule": true, "outDir": "dist", - "rootDir": "src" + "rootDir": "src", + "noErrorTruncation": false }, "include": ["src/**/*.ts"], "exclude": ["node_modules"] From f32fd05b6514ef8de610e6d5370666e06b795ba3 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 26 Jun 2025 00:00:37 -0700 Subject: [PATCH 10/32] v0 multi-session tools --- README.md | 80 ++++++++++++++- src/program.ts | 2 + src/stagehandStore.ts | 153 +++++++++++++++++++++++++++ src/tools/index.ts | 22 +++- src/tools/multiSession.ts | 211 ++++++++++++++++++++++++++++++++++++++ src/types/types.ts | 20 ++++ tsconfig.json | 2 +- 7 files changed, 487 insertions(+), 3 deletions(-) create mode 100644 src/stagehandStore.ts create mode 100644 src/tools/multiSession.ts create mode 100644 src/types/types.ts diff --git a/README.md b/README.md index 5fbaa24..314cfe5 100644 --- a/README.md +++ b/README.md @@ -19,6 +19,7 @@ This server provides cloud browser automation capabilities using [Browserbase](h | Model Flexibility | Supports multiple models (OpenAI, Claude, Gemini, and more) | | Vision Support | Use annotated screenshots for complex DOMs | | Session Management | Create, manage, and close browser sessions | +| Multi-Session | Run multiple browser sessions in parallel | ### Alternative Installation Methods @@ -332,6 +333,82 @@ The Browserbase MCP server provides the following tools for browser automation: - Output: - Confirmation message and session replay URL +### Multi-Session Management Tools + +The server now supports managing multiple browser sessions in parallel, allowing you to control multiple browsers simultaneously: + +- **stagehand_session_create_multi** + - Create a new independent Stagehand browser session + - Inputs: + - `name` (string, optional): Optional name for the session + - `browserbaseSessionID` (string, optional): Resume an existing Browserbase session + - `browserbaseSessionCreateParams` (object, optional): Custom Browserbase session parameters + - Output: + - Session ID and Browserbase session ID + +- **stagehand_session_list** + - List all active Stagehand browser sessions + - No inputs required + - Output: + - List of active sessions with IDs, names, and metadata + +- **stagehand_session_close_multi** + - Close a specific Stagehand browser session + - Input: + - `sessionId` (string): The session ID to close + - Output: + - Confirmation message + +- **stagehand_navigate_session** + - Navigate to a URL in a specific browser session + - Inputs: + - `sessionId` (string): The session ID to use + - `url` (string): The URL to navigate to + +- **stagehand_act_session** + - Perform an action in a specific browser session + - Inputs: + - `sessionId` (string): The session ID to use + - `action` (string): The action to perform + - `variables` (object, optional): Variables for the action + +- **stagehand_extract_session** + - Extract information from a specific browser session + - Inputs: + - `sessionId` (string): The session ID to use + - `instruction` (string): What to extract + +- **stagehand_observe_session** + - Observe elements in a specific browser session + - Inputs: + - `sessionId` (string): The session ID to use + - `instruction` (string): What to observe + - `returnAction` (boolean, optional): Whether to return the action + +### Multi-Session Example + +Here's an example of using multiple browser sessions in parallel: + +```javascript +// Create two sessions +const searchSession = await createSession({ name: "Search Engine" }); +const newsSession = await createSession({ name: "News Reader" }); + +// Navigate both sessions in parallel +await Promise.all([ + navigateSession(searchSession.id, "https://google.com"), + navigateSession(newsSession.id, "https://news.ycombinator.com") +]); + +// Perform actions on both sessions +await actSession(searchSession.id, "Search for 'AI tools'"); +const news = await extractSession(newsSession.id, "Extract top 5 headlines"); + +// Clean up +await closeSession(searchSession.id); +await closeSession(newsSession.id); +``` + ### Resources The server provides access to screenshot resources: @@ -414,9 +491,10 @@ mcp-server-browserbase/ This server implements the following MCP capabilities: -- **Tools**: 7 tools for comprehensive browser automation +- **Tools**: 14 tools for comprehensive browser automation - 5 Stagehand tools: navigate, act, extract, observe, screenshot - 2 Session management tools: create and close Browserbase sessions + - 7 Multi-session tools: create, list, close, navigate, act, extract, observe with specific sessions - **Prompts**: Prompt templates for common automation tasks - **Resources**: Screenshot resource management with URI-based access diff --git a/src/program.ts b/src/program.ts index 1cc53eb..d3c7681 100644 --- a/src/program.ts +++ b/src/program.ts @@ -6,6 +6,7 @@ import { fileURLToPath } from "url"; import createServerFunction from "./index.js"; import { ServerList } from "./server.js"; import { startHttpTransport, startStdioTransport } from "./transport.js"; +import * as stagehandStore from "./stagehandStore.js"; import { resolveConfig } from "./config.js"; @@ -79,6 +80,7 @@ program function setupExitWatchdog(serverList: ServerList) { const handleExit = async () => { setTimeout(() => process.exit(0), 15000); + await stagehandStore.removeAll(); await serverList.closeAll(); process.exit(0); }; diff --git a/src/stagehandStore.ts b/src/stagehandStore.ts new file mode 100644 index 0000000..3429e79 --- /dev/null +++ b/src/stagehandStore.ts @@ -0,0 +1,153 @@ +import { randomUUID } from "crypto"; +import { Stagehand, AvailableModel } from "@browserbasehq/stagehand"; +import { Page } from "playwright-core"; +import { StagehandSession, CreateSessionParams } from "./types/types.js"; +import type { Config } from "../config.js"; + +// Store for all active sessions +const store = new Map(); + +/** + * Create a new Stagehand session + */ +export const create = async ( + config: Config, + params: CreateSessionParams = {} +): Promise => { + const id = randomUUID(); + + // Merge config with params + const apiKey = params.apiKey || config.browserbaseApiKey; + const projectId = params.projectId || config.browserbaseProjectId; + + if (!apiKey || !projectId) { + throw new Error("Browserbase API Key and Project ID are required"); + } + + process.stderr.write(`[StagehandStore] Creating new session ${id}...\n`); + + const stagehand = new Stagehand({ + env: "BROWSERBASE", + apiKey, + projectId, + modelName: (params.modelName || config.modelName || "google/gemini-2.0-flash") as AvailableModel, + modelClientOptions: { + apiKey: process.env.GEMINI_API_KEY, //TODO: + }, + ...(params.browserbaseSessionID && { browserbaseSessionID: params.browserbaseSessionID }), + browserbaseSessionCreateParams: params.browserbaseSessionCreateParams || { + projectId, + proxies: config.proxies, + browserSettings: { + viewport: { + width: config.viewPort?.browserWidth ?? 1024, + height: config.viewPort?.browserHeight ?? 768, + }, + context: config.context?.contextId + ? { + id: config.context?.contextId, + persist: config.context?.persist ?? true, + } + : undefined, + advancedStealth: config.advancedStealth ?? undefined, + }, + }, + logger: (logLine) => { + console.error(`Stagehand[${id}]: ${logLine.message}`); + }, + }); + + await stagehand.init(); + + const page = stagehand.page as unknown as Page; + const browser = page.context().browser(); + + if (!browser) { + throw new Error("Failed to get browser from Stagehand page context"); + } + + const session: StagehandSession = { + id, + stagehand, + page, + browser, + created: Date.now(), + metadata: { + ...params.meta, + bbSessionId: stagehand.browserbaseSessionID, + }, + }; + + store.set(id, session); + + process.stderr.write( + `[StagehandStore] Session created: ${id} (BB: ${stagehand.browserbaseSessionID})\n` + ); + process.stderr.write( + `[StagehandStore] Live debugger: https://www.browserbase.com/sessions/${stagehand.browserbaseSessionID}\n` + ); + + // Set up disconnect handler + browser.on("disconnected", () => { + process.stderr.write(`[StagehandStore] Session disconnected: ${id}\n`); + store.delete(id); + }); + + return session; +}; + +/** + * Get a session by ID + */ +export const get = (id: string): StagehandSession | null => { + return store.get(id) ?? null; +}; + +/** + * List all active sessions + */ +export const list = (): StagehandSession[] => { + return Array.from(store.values()); +}; + +/** + * Remove and close a session + */ +export const remove = async (id: string): Promise => { + const session = store.get(id); + if (!session) { + process.stderr.write(`[StagehandStore] Session not found for removal: ${id}\n`); + return; + } + + process.stderr.write(`[StagehandStore] Removing session: ${id}\n`); + + try { + await session.stagehand.close(); + process.stderr.write(`[StagehandStore] Session closed: ${id}\n`); + } catch (error) { + process.stderr.write( + `[StagehandStore] Error closing session ${id}: ${ + error instanceof Error ? error.message : String(error) + }\n` + ); + } + + store.delete(id); +}; + +/** + * Remove all sessions + */ +export const removeAll = async (): Promise => { + process.stderr.write(`[StagehandStore] Removing all ${store.size} sessions...\n`); + await Promise.all(list().map(s => remove(s.id))); + process.stderr.write(`[StagehandStore] All sessions removed\n`); +}; + +/** + * Get store size + */ +export const size = (): number => { + return store.size; +}; \ No newline at end of file diff --git a/src/tools/index.ts b/src/tools/index.ts index 16711f0..d5c28c5 100644 --- a/src/tools/index.ts +++ b/src/tools/index.ts @@ -1,10 +1,18 @@ -// Import all individual tools import navigateTool from "./navigate.js"; import actTool from "./act.js"; import extractTool from "./extract.js"; import observeTool from "./observe.js"; import screenshotTool from "./screenshot.js"; import sessionTools from "./session.js"; +import { + createSessionTool, + listSessionsTool, + closeSessionTool, + navigateWithSessionTool, + actWithSessionTool, + extractWithSessionTool, + observeWithSessionTool, +} from "./multiSession.js"; // Export individual tools export { default as navigateTool } from "./navigate.js"; @@ -14,6 +22,17 @@ export { default as observeTool } from "./observe.js"; export { default as screenshotTool } from "./screenshot.js"; export { default as sessionTools } from "./session.js"; +// Multi-session tools array +export const multiSessionTools = [ + createSessionTool, + listSessionsTool, + closeSessionTool, + navigateWithSessionTool, + actWithSessionTool, + extractWithSessionTool, + observeWithSessionTool, +]; + // Export all tools as array export const TOOLS = [ ...sessionTools, @@ -22,6 +41,7 @@ export const TOOLS = [ extractTool, observeTool, screenshotTool, + ...multiSessionTools, ]; export const sessionManagementTools = sessionTools; diff --git a/src/tools/multiSession.ts b/src/tools/multiSession.ts new file mode 100644 index 0000000..ad9c293 --- /dev/null +++ b/src/tools/multiSession.ts @@ -0,0 +1,211 @@ +import { z } from "zod"; +import { defineTool, type Tool, type ToolResult, type InputType } from "./tool.js"; +import * as stagehandStore from "../stagehandStore.js"; +import { CreateSessionParams } from "../types/types.js"; +import type { Context } from "../context.js"; +import navigateTool from "./navigate.js"; +import actTool from "./act.js"; +import extractTool from "./extract.js"; +import observeTool from "./observe.js"; + +/** + * Creates a session-aware version of an existing tool + * This wraps the original tool's handler to work with a specific session + */ +function createMultiSessionAwareTool( + originalTool: Tool, + options: { + namePrefix?: string; + nameSuffix?: string; + } = {} +): Tool { + const { namePrefix = "", nameSuffix = "_session" } = options; + + // Create new input schema that includes sessionId + const originalSchema = originalTool.schema.inputSchema; + let newInputSchema: z.ZodSchema; + + if (originalSchema instanceof z.ZodObject) { + // If it's a ZodObject, we can spread its shape + newInputSchema = z.object({ + sessionId: z.string().describe("The session ID to use"), + ...originalSchema.shape, + }); + } else { + // For other schema types, create an intersection + newInputSchema = z.intersection( + z.object({ sessionId: z.string().describe("The session ID to use") }), + originalSchema + ); + } + + return defineTool({ + capability: originalTool.capability, + schema: { + name: `${namePrefix}${originalTool.schema.name}${nameSuffix}`, + description: `${originalTool.schema.description} (for a specific session)`, + inputSchema: newInputSchema, + }, + handle: async (context: Context, params: any): Promise => { + const { sessionId, ...originalParams } = params; + + // Get the session + const session = stagehandStore.get(sessionId); + if (!session) { + throw new Error(`Session ${sessionId} not found`); + } + + // Create a temporary context that points to the specific session + const sessionContext = Object.create(context); + sessionContext.currentSessionId = session.metadata?.bbSessionId || sessionId; + sessionContext.getStagehand = async () => session.stagehand; + sessionContext.getActivePage = async () => session.page; + sessionContext.getActiveBrowser = async () => session.browser; + + // Call the original tool's handler with the session-specific context + return originalTool.handle(sessionContext, originalParams); + }, + }); +} + +// Create session tool +export const createSessionTool = defineTool({ + capability: "create_session", + schema: { + name: "stagehand_session_create_multi", + description: "Create a new Stagehand browser session. Returns the session ID.", + inputSchema: z.object({ + name: z.string().optional().describe("Optional name for the session"), + browserbaseSessionID: z.string().optional().describe("Resume an existing Browserbase session"), + browserbaseSessionCreateParams: z.any().optional().describe("Custom Browserbase session parameters"), + }), + }, + handle: async (context: Context, { name, browserbaseSessionID, browserbaseSessionCreateParams }): Promise => { + try { + const params: CreateSessionParams = { + browserbaseSessionID, + browserbaseSessionCreateParams, + meta: name ? { name } : undefined, + }; + + const session = await stagehandStore.create(context.config, params); + + return { + action: async () => ({ + content: [ + { + type: "text", + text: `Created session ${session.id}${name ? ` (${name})` : ''}\nBrowserbase session: ${session.metadata?.bbSessionId}`, + }, + ], + }), + waitForNetwork: false, + }; + } catch (error) { + const errorMessage = error instanceof Error ? error.message : String(error); + throw new Error(`Failed to create session: ${errorMessage}`); + } + }, +}); + +// List sessions tool +export const listSessionsTool = defineTool({ + capability: "list_sessions", + schema: { + name: "stagehand_session_list", + description: "List all active Stagehand browser sessions", + inputSchema: z.object({}), + }, + handle: async (): Promise => { + const sessions = stagehandStore.list(); + + if (sessions.length === 0) { + return { + action: async () => ({ + content: [ + { + type: "text", + text: "No active sessions", + }, + ], + }), + waitForNetwork: false, + }; + } + + const sessionInfo = sessions.map(s => ({ + id: s.id, + name: s.metadata?.name, + browserbaseSessionId: s.metadata?.bbSessionId, + created: new Date(s.created).toISOString(), + age: Math.floor((Date.now() - s.created) / 1000), + })); + + return { + action: async () => ({ + content: [ + { + type: "text", + text: `Active sessions (${sessions.length}):\n${sessionInfo + .map(s => `- ${s.id}${s.name ? ` (${s.name})` : ''} - BB: ${s.browserbaseSessionId} - Age: ${s.age}s`) + .join('\n')}`, + }, + ], + }), + waitForNetwork: false, + }; + }, +}); + +// Close session tool +export const closeSessionTool = defineTool({ + capability: "close_session", + schema: { + name: "stagehand_session_close_multi", + description: "Close a specific Stagehand browser session", + inputSchema: z.object({ + sessionId: z.string().describe("The session ID to close"), + }), + }, + handle: async (_context: Context, { sessionId }): Promise => { + const session = stagehandStore.get(sessionId); + if (!session) { + throw new Error(`Session ${sessionId} not found`); + } + + await stagehandStore.remove(sessionId); + + return { + action: async () => ({ + content: [ + { + type: "text", + text: `Closed session ${sessionId}`, + }, + ], + }), + waitForNetwork: false, + }; + }, +}); + +// Create multi-session-aware versions of the core tools +export const navigateWithSessionTool = createMultiSessionAwareTool(navigateTool, { + namePrefix: "multi-", + nameSuffix: "_session", +}); + +export const actWithSessionTool = createMultiSessionAwareTool(actTool, { + namePrefix: "multi-", + nameSuffix: "_session", +}); + +export const extractWithSessionTool = createMultiSessionAwareTool(extractTool, { + namePrefix: "multi-", + nameSuffix: "_session", +}); + +export const observeWithSessionTool = createMultiSessionAwareTool(observeTool, { + namePrefix: "multi-", + nameSuffix: "_session", +}); \ No newline at end of file diff --git a/src/types/types.ts b/src/types/types.ts new file mode 100644 index 0000000..b8c8319 --- /dev/null +++ b/src/types/types.ts @@ -0,0 +1,20 @@ +import { Stagehand } from "@browserbasehq/stagehand"; +import { Browser, Page } from "playwright-core"; + +export type StagehandSession = { + id: string; // MCP-side ID + stagehand: Stagehand; // owns the Browserbase session + page: Page; + browser: Browser; + created: number; + metadata?: Record; // optional extras (proxy, contextId, bbSessionId) +}; + +export type CreateSessionParams = { + apiKey?: string; + projectId?: string; + modelName?: string; + browserbaseSessionID?: string; + browserbaseSessionCreateParams?: any; + meta?: Record; +}; \ No newline at end of file diff --git a/tsconfig.json b/tsconfig.json index 7177886..6c2b6de 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -12,6 +12,6 @@ "rootDir": "src", "noErrorTruncation": false }, - "include": ["src/**/*.ts"], + "include": ["src/**/*.ts", "src/types/types.ts"], "exclude": ["node_modules"] } From a0204a52a07409081db1f39a45132c9e384a643f Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 26 Jun 2025 16:37:54 -0700 Subject: [PATCH 11/32] add husky for commits + pnpm exec husky init + move around mcp specifics + multi-sessions update in readme --- .husky/pre-commit | 2 + README.md | 160 +- package.json | 5 +- pnpm-lock.yaml | 3254 +++++++++++------------------------- src/context.ts | 2 +- src/index.ts | 12 +- src/{ => mcp}/prompts.ts | 19 +- src/{ => mcp}/resources.ts | 2 +- src/stagehandStore.ts | 36 +- src/tools/multiSession.ts | 116 +- src/tools/screenshot.ts | 2 +- src/types/types.ts | 6 +- 12 files changed, 1236 insertions(+), 2380 deletions(-) create mode 100644 .husky/pre-commit rename src/{ => mcp}/prompts.ts (74%) rename src/{ => mcp}/resources.ts (96%) diff --git a/.husky/pre-commit b/.husky/pre-commit new file mode 100644 index 0000000..e3ad1ac --- /dev/null +++ b/.husky/pre-commit @@ -0,0 +1,2 @@ +pnpm lint +pnpm prettier:fix \ No newline at end of file diff --git a/README.md b/README.md index 314cfe5..8352da1 100644 --- a/README.md +++ b/README.md @@ -335,79 +335,73 @@ The Browserbase MCP server provides the following tools for browser automation: ### Multi-Session Management Tools -The server now supports managing multiple browser sessions in parallel, allowing you to control multiple browsers simultaneously: +The server supports managing multiple independent browser sessions in parallel, allowing you to control multiple browsers simultaneously for complex automation workflows: -- **stagehand_session_create_multi** - - Create a new independent Stagehand browser session +#### Session Lifecycle Management + +- **multi-browserbase_stagehand_session_create** + - Create a new independent Stagehand browser session with full web automation capabilities + - Each session is isolated with its own browser instance, cookies, and state - Inputs: - - `name` (string, optional): Optional name for the session - - `browserbaseSessionID` (string, optional): Resume an existing Browserbase session - - `browserbaseSessionCreateParams` (object, optional): Custom Browserbase session parameters + - `name` (string, optional): Human-readable name for tracking (e.g., 'login-flow', 'data-scraping') + - `browserbaseSessionID` (string, optional): Resume an existing Browserbase session by ID + - `browserbaseSessionCreateParams` (object, optional): Advanced Browserbase configuration - Output: - - Session ID and Browserbase session ID + - Session ID and Browserbase session ID with live debugger URL -- **stagehand_session_list** - - List all active Stagehand browser sessions +- **browserbase_stagehand_session_list** + - List all currently active Stagehand browser sessions with detailed metadata + - Shows session IDs, names, Browserbase session IDs, creation time, and age - No inputs required - Output: - - List of active sessions with IDs, names, and metadata + - Comprehensive list of active sessions with status information -- **stagehand_session_close_multi** - - Close a specific Stagehand browser session +- **multi-browserbase_stagehand_session_close** + - Close and clean up a specific Stagehand browser session + - Terminates browser instance, ends Browserbase session, and frees resources - Input: - - `sessionId` (string): The session ID to close + - `sessionId` (string): Exact session ID to close (cannot be undone) - Output: - - Confirmation message + - Confirmation message with session replay URL + +#### Session-Specific Browser Automation -- **stagehand_navigate_session** +All core browser automation tools are available with session-specific variants: + +- **multi-browserbase_stagehand_navigate_session** - Navigate to a URL in a specific browser session - Inputs: - `sessionId` (string): The session ID to use - `url` (string): The URL to navigate to -- **stagehand_act_session** - - Perform an action in a specific browser session +- **multi-browserbase_stagehand_act_session** + - Perform an action in a specific browser session using natural language - Inputs: - `sessionId` (string): The session ID to use - - `action` (string): The action to perform - - `variables` (object, optional): Variables for the action + - `action` (string): The action to perform (e.g., "click the login button") + - `variables` (object, optional): Variables for sensitive data in action templates -- **stagehand_extract_session** - - Extract information from a specific browser session +- **multi-browserbase_stagehand_extract_session** + - Extract structured information from a specific browser session - Inputs: - `sessionId` (string): The session ID to use - - `instruction` (string): What to extract + - `instruction` (string): What to extract from the page -- **stagehand_observe_session** - - Observe elements in a specific browser session +- **multi-browserbase_stagehand_observe_session** + - Observe and find actionable elements in a specific browser session - Inputs: - `sessionId` (string): The session ID to use - - `instruction` (string): What to observe - - `returnAction` (boolean, optional): Whether to return the action - -### Multi-Session Example - -Here's an example of using multiple browser sessions in parallel: - -```javascript -// Create two sessions -const searchSession = await createSession({ name: "Search Engine" }); -const newsSession = await createSession({ name: "News Reader" }); - -// Navigate both sessions in parallel -await Promise.all([ - navigateSession(searchSession.id, "https://google.com"), - navigateSession(newsSession.id, "https://news.ycombinator.com") -]); + - `instruction` (string): What to observe (e.g., "find the login button") + - `returnAction` (boolean, optional): Whether to return the action to perform -// Perform actions on both sessions -await actSession(searchSession.id, "Search for 'AI tools'"); -const news = await extractSession(newsSession.id, "Extract top 5 headlines"); +#### Multi-Session Use Cases -// Clean up -await closeSession(searchSession.id); -await closeSession(newsSession.id); -``` +- **Parallel Data Collection**: Run multiple scraping sessions simultaneously across different websites +- **A/B Testing**: Compare user flows across different browser sessions with varying configurations +- **Authentication Workflows**: Maintain separate authenticated sessions for different user accounts +- **Cross-Site Operations**: Perform coordinated actions across multiple websites or applications +- **Load Testing**: Simulate multiple users interacting with web applications concurrently +- **Backup Sessions**: Keep fallback sessions ready in case primary sessions encounter issues ### Resources @@ -425,21 +419,26 @@ mcp-server-browserbase/ │ ├── config.ts # Configuration management and CLI parsing │ ├── context.ts # Context class managing Stagehand instances │ ├── sessionManager.ts # Browserbase session lifecycle management +│ ├── stagehandStore.ts # Multi-session store for managing parallel browser sessions │ ├── program.ts # CLI program setup using Commander.js │ ├── transport.ts # HTTP/SSE and STDIO transport handlers │ ├── server.ts # Server list management -│ ├── resources.ts # Screenshot resource management -│ ├── prompts.ts # Prompt templates for MCP clients │ ├── utils.ts # Utility functions -│ └── tools/ # Tool definitions and implementations -│ ├── act.ts # Stagehand action execution tool -│ ├── extract.ts # Page content extraction tool -│ ├── navigate.ts # URL navigation tool -│ ├── observe.ts # Element observation tool -│ ├── screenshot.ts # Screenshot capture tool -│ ├── session.ts # Session management tools -│ ├── tool.ts # Tool type definitions -│ └── utils.ts # Tool utility functions +│ ├── mcp/ # MCP protocol implementations +│ │ ├── prompts.ts # Prompt templates and handlers for MCP clients +│ │ └── resources.ts # Resource management (screenshots) with URI-based access +│ ├── tools/ # Tool definitions and implementations +│ │ ├── act.ts # Stagehand action execution tool +│ │ ├── extract.ts # Page content extraction tool +│ │ ├── navigate.ts # URL navigation tool +│ │ ├── observe.ts # Element observation tool +│ │ ├── screenshot.ts # Screenshot capture tool +│ │ ├── session.ts # Single session management tools +│ │ ├── multiSession.ts # Multi-session management and session-aware tools +│ │ ├── tool.ts # Tool type definitions and interfaces +│ │ └── index.ts # Tool exports and registration +│ └── types/ # TypeScript type definitions +│ └── types.ts # Shared type definitions for sessions and configurations ├── dist/ # Compiled JavaScript output ├── assets/ # Images and documentation assets ├── cli.js # Executable entry point for CLI usage @@ -471,13 +470,24 @@ mcp-server-browserbase/ **server.ts** - Server list management providing factory patterns for server creation and handling multiple concurrent connections. -### Tools & Resources +**stagehandStore.ts** - Multi-session store managing parallel browser sessions with lifecycle tracking, automatic cleanup, and session metadata. + +### MCP Protocol Specifics Implementation + +**mcp/prompts.ts** - Prompt template definitions and handlers implementing the MCP prompts specification with argument substitution. + +**mcp/resources.ts** - Resource management implementing the MCP resources specification, handling screenshot storage, URI resolution, and base64-encoded data serving. -**tools/** - Individual tool implementations with type-safe schemas including browser automation (navigate, act, extract, observe, screenshot) and session management tools. +### Tools & Types -**resources.ts** - Screenshot resource management with in-memory storage, URI resolution, and base64-encoded PNG data serving. +**tools/** - Individual tool implementations with type-safe Zod schemas including: +- Core browser automation tools (navigate, act, extract, observe, screenshot) +- Single session management tools (session.ts) +- Multi-session management and session-aware tool variants (multiSession.ts) +- Tool type definitions and interfaces (tool.ts) +- Centralized tool exports and registration (index.ts) -**prompts.ts** - Prompt template definitions and retrieval system for MCP clients. +**types/types.ts** - Shared TypeScript type definitions for sessions, configurations, and MCP protocol structures. **utils.ts** - Message sanitization utilities ensuring proper JSON formatting for MCP messages. @@ -492,22 +502,38 @@ mcp-server-browserbase/ This server implements the following MCP capabilities: - **Tools**: 14 tools for comprehensive browser automation - - 5 Stagehand tools: navigate, act, extract, observe, screenshot - - 2 Session management tools: create and close Browserbase sessions + - 5 Core Stagehand tools: navigate, act, extract, observe, screenshot + - 2 Single-session management tools: create and close Browserbase sessions - 7 Multi-session tools: create, list, close, navigate, act, extract, observe with specific sessions - **Prompts**: Prompt templates for common automation tasks - **Resources**: Screenshot resource management with URI-based access +### Session Management Architecture + +The server supports two session management approaches: + +1. **Single Session Mode**: Traditional approach with one active browser session + - Tools: `browserbase_session_create`, `browserbase_session_close` + - Simpler for basic automation tasks + - Automatically manages the active session + +2. **Multi-Session Mode**: Advanced approach with multiple parallel browser sessions + - Tools: `multi-browserbase_stagehand_session_create`, `multi-browserbase_stagehand_session_close`, `browserbase_stagehand_session_list` + - Session-specific variants of all core tools (with `_session` suffix) + - Ideal for complex workflows requiring parallel browser instances + - Each session maintains independent state, cookies, and browser context + ## Key Features - **AI-Powered Automation**: Natural language commands for web interactions - **Multi-Model Support**: Works with OpenAI, Claude, Gemini, and more -- **Session Management**: Create, manage, and persist browser sessions +- **Advanced Session Management**: Single and multi-session support for parallel browser automation - **Screenshot Capture**: Full-page and element-specific screenshots - **Data Extraction**: Intelligent content extraction from web pages - **Proxy Support**: Enterprise-grade proxy capabilities - **Stealth Mode**: Advanced anti-detection features - **Context Persistence**: Maintain authentication and state across sessions +- **Parallel Workflows**: Run multiple browser sessions simultaneously for complex automation tasks For more information about the Model Context Protocol, visit: @@ -518,4 +544,4 @@ For more information about the Model Context Protocol, visit: Licensed under the MIT License. -Copyright 2025 Browserbase, Inc. +Copyright 2025 Browserbase, Inc. \ No newline at end of file diff --git a/package.json b/package.json index 5535c16..43bd2e2 100644 --- a/package.json +++ b/package.json @@ -20,7 +20,7 @@ ], "scripts": { "build": "tsc && shx chmod +x dist/*.js", - "prepare": "npm run build", + "prepare": "husky", "watch": "tsc --watch", "lint": "eslint . --ext .ts", "prettier:check": "prettier --check .", @@ -37,10 +37,11 @@ "eslint": "^9.29.0", "eslint-plugin-react": "^7.37.5", "globals": "^16.2.0", + "husky": "^9.1.7", "prettier": "^3.6.1", "shx": "^0.3.4", "typescript": "^5.6.2", "typescript-eslint": "^8.35.0" }, - "packageManager": "pnpm@10.10.0+sha512.d615db246fe70f25dcfea6d8d73dee782ce23e2245e3c4f6f888249fb568149318637dca73c2c5c8ef2a4ca0d5657fb9567188bfab47f566d1ee6ce987815c39" + "packageManager": "pnpm@10.12.4+sha512.5ea8b0deed94ed68691c9bad4c955492705c5eeb8a87ef86bc62c74a26b037b08ff9570f108b2e4dbd1dd1a9186fea925e527f141c648e85af45631074680184" } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 9cdb651..69bb841 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1,26 +1,27 @@ -lockfileVersion: "9.0" +lockfileVersion: '9.0' settings: autoInstallPeers: true excludeLinksFromLockfile: false importers: + .: dependencies: - "@browserbasehq/stagehand": + '@browserbasehq/stagehand': specifier: ^2.4.0 version: 2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67) - "@modelcontextprotocol/sdk": + '@modelcontextprotocol/sdk': specifier: ^1.13.1 version: 1.13.1 - "@playwright/test": + '@playwright/test': specifier: ^1.49.0 version: 1.53.1 commander: specifier: ^14.0.0 version: 14.0.0 devDependencies: - "@eslint/js": + '@eslint/js': specifier: ^9.29.0 version: 9.29.0 eslint: @@ -32,6 +33,9 @@ importers: globals: specifier: ^16.2.0 version: 16.2.0 + husky: + specifier: ^9.1.7 + version: 9.1.7 prettier: specifier: ^3.6.1 version: 3.6.1 @@ -46,118 +50,80 @@ importers: version: 8.35.0(eslint@9.29.0)(typescript@5.8.3) packages: - "@ai-sdk/anthropic@1.2.12": - resolution: - { - integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==, - } - engines: { node: ">=18" } + + '@ai-sdk/anthropic@1.2.12': + resolution: {integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/azure@1.3.23": - resolution: - { - integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==, - } - engines: { node: ">=18" } + '@ai-sdk/azure@1.3.23': + resolution: {integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/cerebras@0.2.14": - resolution: - { - integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==, - } - engines: { node: ">=18" } + '@ai-sdk/cerebras@0.2.14': + resolution: {integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/deepseek@0.2.14": - resolution: - { - integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==, - } - engines: { node: ">=18" } + '@ai-sdk/deepseek@0.2.14': + resolution: {integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/google@1.2.19": - resolution: - { - integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==, - } - engines: { node: ">=18" } + '@ai-sdk/google@1.2.19': + resolution: {integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/groq@1.2.9": - resolution: - { - integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==, - } - engines: { node: ">=18" } + '@ai-sdk/groq@1.2.9': + resolution: {integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/mistral@1.2.8": - resolution: - { - integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==, - } - engines: { node: ">=18" } + '@ai-sdk/mistral@1.2.8': + resolution: {integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/openai-compatible@0.2.14": - resolution: - { - integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==, - } - engines: { node: ">=18" } + '@ai-sdk/openai-compatible@0.2.14': + resolution: {integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/openai@1.3.22": - resolution: - { - integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==, - } - engines: { node: ">=18" } + '@ai-sdk/openai@1.3.22': + resolution: {integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/perplexity@1.1.9": - resolution: - { - integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==, - } - engines: { node: ">=18" } + '@ai-sdk/perplexity@1.1.9': + resolution: {integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/provider-utils@2.2.8": - resolution: - { - integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==, - } - engines: { node: ">=18" } + '@ai-sdk/provider-utils@2.2.8': + resolution: {integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.23.8 - "@ai-sdk/provider@1.1.3": - resolution: - { - integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==, - } - engines: { node: ">=18" } - - "@ai-sdk/react@1.2.12": - resolution: - { - integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==, - } - engines: { node: ">=18" } + '@ai-sdk/provider@1.1.3': + resolution: {integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==} + engines: {node: '>=18'} + + '@ai-sdk/react@1.2.12': + resolution: {integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==} + engines: {node: '>=18'} peerDependencies: react: ^18 || ^19 || ^19.0.0-rc zod: ^3.23.8 @@ -165,381 +131,231 @@ packages: zod: optional: true - "@ai-sdk/togetherai@0.2.14": - resolution: - { - integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==, - } - engines: { node: ">=18" } + '@ai-sdk/togetherai@0.2.14': + resolution: {integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/ui-utils@1.2.11": - resolution: - { - integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==, - } - engines: { node: ">=18" } + '@ai-sdk/ui-utils@1.2.11': + resolution: {integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==} + engines: {node: '>=18'} peerDependencies: zod: ^3.23.8 - "@ai-sdk/xai@1.2.16": - resolution: - { - integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==, - } - engines: { node: ">=18" } + '@ai-sdk/xai@1.2.16': + resolution: {integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@anthropic-ai/sdk@0.39.0": - resolution: - { - integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==, - } - - "@browserbasehq/sdk@2.6.0": - resolution: - { - integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==, - } - - "@browserbasehq/stagehand@2.4.0": - resolution: - { - integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==, - } + '@anthropic-ai/sdk@0.39.0': + resolution: {integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==} + + '@browserbasehq/sdk@2.6.0': + resolution: {integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==} + + '@browserbasehq/stagehand@2.4.0': + resolution: {integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==} peerDependencies: deepmerge: ^4.3.1 dotenv: ^16.4.5 zod: ^3.23.8 - "@eslint-community/eslint-utils@4.7.0": - resolution: - { - integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==, - } - engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } + '@eslint-community/eslint-utils@4.7.0': + resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} peerDependencies: eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 - "@eslint-community/regexpp@4.12.1": - resolution: - { - integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==, - } - engines: { node: ^12.0.0 || ^14.0.0 || >=16.0.0 } - - "@eslint/config-array@0.20.1": - resolution: - { - integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/config-helpers@0.2.3": - resolution: - { - integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/core@0.14.0": - resolution: - { - integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/core@0.15.1": - resolution: - { - integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/eslintrc@3.3.1": - resolution: - { - integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/js@9.29.0": - resolution: - { - integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/object-schema@2.1.6": - resolution: - { - integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/plugin-kit@0.3.3": - resolution: - { - integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@google/genai@0.8.0": - resolution: - { - integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==, - } - engines: { node: ">=18.0.0" } - - "@humanfs/core@0.19.1": - resolution: - { - integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==, - } - engines: { node: ">=18.18.0" } - - "@humanfs/node@0.16.6": - resolution: - { - integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==, - } - engines: { node: ">=18.18.0" } - - "@humanwhocodes/module-importer@1.0.1": - resolution: - { - integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==, - } - engines: { node: ">=12.22" } - - "@humanwhocodes/retry@0.3.1": - resolution: - { - integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==, - } - engines: { node: ">=18.18" } - - "@humanwhocodes/retry@0.4.3": - resolution: - { - integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==, - } - engines: { node: ">=18.18" } - - "@modelcontextprotocol/sdk@1.13.1": - resolution: - { - integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==, - } - engines: { node: ">=18" } - - "@nodelib/fs.scandir@2.1.5": - resolution: - { - integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==, - } - engines: { node: ">= 8" } - - "@nodelib/fs.stat@2.0.5": - resolution: - { - integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==, - } - engines: { node: ">= 8" } - - "@nodelib/fs.walk@1.2.8": - resolution: - { - integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==, - } - engines: { node: ">= 8" } - - "@opentelemetry/api@1.9.0": - resolution: - { - integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==, - } - engines: { node: ">=8.0.0" } - - "@playwright/test@1.53.1": - resolution: - { - integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==, - } - engines: { node: ">=18" } + '@eslint-community/regexpp@4.12.1': + resolution: {integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==} + engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} + + '@eslint/config-array@0.20.1': + resolution: {integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/config-helpers@0.2.3': + resolution: {integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/core@0.14.0': + resolution: {integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/core@0.15.1': + resolution: {integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/eslintrc@3.3.1': + resolution: {integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/js@9.29.0': + resolution: {integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/object-schema@2.1.6': + resolution: {integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/plugin-kit@0.3.3': + resolution: {integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@google/genai@0.8.0': + resolution: {integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==} + engines: {node: '>=18.0.0'} + + '@humanfs/core@0.19.1': + resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==} + engines: {node: '>=18.18.0'} + + '@humanfs/node@0.16.6': + resolution: {integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==} + engines: {node: '>=18.18.0'} + + '@humanwhocodes/module-importer@1.0.1': + resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} + engines: {node: '>=12.22'} + + '@humanwhocodes/retry@0.3.1': + resolution: {integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==} + engines: {node: '>=18.18'} + + '@humanwhocodes/retry@0.4.3': + resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} + engines: {node: '>=18.18'} + + '@modelcontextprotocol/sdk@1.13.1': + resolution: {integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==} + engines: {node: '>=18'} + + '@nodelib/fs.scandir@2.1.5': + resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} + engines: {node: '>= 8'} + + '@nodelib/fs.stat@2.0.5': + resolution: {integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==} + engines: {node: '>= 8'} + + '@nodelib/fs.walk@1.2.8': + resolution: {integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==} + engines: {node: '>= 8'} + + '@opentelemetry/api@1.9.0': + resolution: {integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==} + engines: {node: '>=8.0.0'} + + '@playwright/test@1.53.1': + resolution: {integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==} + engines: {node: '>=18'} hasBin: true - "@types/diff-match-patch@1.0.36": - resolution: - { - integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==, - } - - "@types/estree@1.0.8": - resolution: - { - integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==, - } - - "@types/json-schema@7.0.15": - resolution: - { - integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==, - } - - "@types/node-fetch@2.6.12": - resolution: - { - integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==, - } - - "@types/node@18.19.112": - resolution: - { - integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==, - } - - "@typescript-eslint/eslint-plugin@8.35.0": - resolution: - { - integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + '@types/diff-match-patch@1.0.36': + resolution: {integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==} + + '@types/estree@1.0.8': + resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==} + + '@types/json-schema@7.0.15': + resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} + + '@types/node-fetch@2.6.12': + resolution: {integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==} + + '@types/node@18.19.112': + resolution: {integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==} + + '@typescript-eslint/eslint-plugin@8.35.0': + resolution: {integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - "@typescript-eslint/parser": ^8.35.0 + '@typescript-eslint/parser': ^8.35.0 eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/parser@8.35.0": - resolution: - { - integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/parser@8.35.0': + resolution: {integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/project-service@8.35.0": - resolution: - { - integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/project-service@8.35.0': + resolution: {integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/scope-manager@8.35.0": - resolution: - { - integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@typescript-eslint/tsconfig-utils@8.35.0": - resolution: - { - integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/scope-manager@8.35.0': + resolution: {integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@typescript-eslint/tsconfig-utils@8.35.0': + resolution: {integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/type-utils@8.35.0": - resolution: - { - integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/type-utils@8.35.0': + resolution: {integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/types@8.35.0": - resolution: - { - integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@typescript-eslint/typescript-estree@8.35.0": - resolution: - { - integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/types@8.35.0': + resolution: {integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@typescript-eslint/typescript-estree@8.35.0': + resolution: {integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/utils@8.35.0": - resolution: - { - integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/utils@8.35.0': + resolution: {integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" + typescript: '>=4.8.4 <5.9.0' - "@typescript-eslint/visitor-keys@8.35.0": - resolution: - { - integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + '@typescript-eslint/visitor-keys@8.35.0': + resolution: {integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} abort-controller@3.0.0: - resolution: - { - integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==, - } - engines: { node: ">=6.5" } + resolution: {integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==} + engines: {node: '>=6.5'} accepts@2.0.0: - resolution: - { - integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==} + engines: {node: '>= 0.6'} acorn-jsx@5.3.2: - resolution: - { - integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==, - } + resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 acorn@8.15.0: - resolution: - { - integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==, - } - engines: { node: ">=0.4.0" } + resolution: {integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==} + engines: {node: '>=0.4.0'} hasBin: true agent-base@7.1.3: - resolution: - { - integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==, - } - engines: { node: ">= 14" } + resolution: {integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==} + engines: {node: '>= 14'} agentkeepalive@4.6.0: - resolution: - { - integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==, - } - engines: { node: ">= 8.0.0" } + resolution: {integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==} + engines: {node: '>= 8.0.0'} ai@4.3.16: - resolution: - { - integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==} + engines: {node: '>=18'} peerDependencies: react: ^18 || ^19 || ^19.0.0-rc zod: ^3.23.8 @@ -548,1486 +364,840 @@ packages: optional: true ajv@6.12.6: - resolution: - { - integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==, - } + resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} ansi-styles@4.3.0: - resolution: - { - integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} + engines: {node: '>=8'} argparse@2.0.1: - resolution: - { - integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==, - } + resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} array-buffer-byte-length@1.0.2: - resolution: - { - integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==} + engines: {node: '>= 0.4'} array-includes@3.1.9: - resolution: - { - integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==} + engines: {node: '>= 0.4'} array.prototype.findlast@1.2.5: - resolution: - { - integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==} + engines: {node: '>= 0.4'} array.prototype.flat@1.3.3: - resolution: - { - integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==} + engines: {node: '>= 0.4'} array.prototype.flatmap@1.3.3: - resolution: - { - integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==} + engines: {node: '>= 0.4'} array.prototype.tosorted@1.1.4: - resolution: - { - integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==} + engines: {node: '>= 0.4'} arraybuffer.prototype.slice@1.0.4: - resolution: - { - integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==} + engines: {node: '>= 0.4'} async-function@1.0.0: - resolution: - { - integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==} + engines: {node: '>= 0.4'} asynckit@0.4.0: - resolution: - { - integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==, - } + resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} atomic-sleep@1.0.0: - resolution: - { - integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==, - } - engines: { node: ">=8.0.0" } + resolution: {integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==} + engines: {node: '>=8.0.0'} available-typed-arrays@1.0.7: - resolution: - { - integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} + engines: {node: '>= 0.4'} balanced-match@1.0.2: - resolution: - { - integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==, - } + resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} base64-js@1.5.1: - resolution: - { - integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==, - } + resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==} bignumber.js@9.3.0: - resolution: - { - integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==, - } + resolution: {integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==} body-parser@2.2.0: - resolution: - { - integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==} + engines: {node: '>=18'} brace-expansion@1.1.12: - resolution: - { - integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==, - } + resolution: {integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==} brace-expansion@2.0.2: - resolution: - { - integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==, - } + resolution: {integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==} braces@3.0.3: - resolution: - { - integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} + engines: {node: '>=8'} buffer-equal-constant-time@1.0.1: - resolution: - { - integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==, - } + resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} bytes@3.1.2: - resolution: - { - integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==} + engines: {node: '>= 0.8'} call-bind-apply-helpers@1.0.2: - resolution: - { - integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==} + engines: {node: '>= 0.4'} call-bind@1.0.8: - resolution: - { - integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==} + engines: {node: '>= 0.4'} call-bound@1.0.4: - resolution: - { - integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==} + engines: {node: '>= 0.4'} callsites@3.1.0: - resolution: - { - integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} + engines: {node: '>=6'} chalk@4.1.2: - resolution: - { - integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} + engines: {node: '>=10'} chalk@5.4.1: - resolution: - { - integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==, - } - engines: { node: ^12.17.0 || ^14.13 || >=16.0.0 } + resolution: {integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==} + engines: {node: ^12.17.0 || ^14.13 || >=16.0.0} color-convert@2.0.1: - resolution: - { - integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==, - } - engines: { node: ">=7.0.0" } + resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==} + engines: {node: '>=7.0.0'} color-name@1.1.4: - resolution: - { - integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==, - } + resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} colorette@2.0.20: - resolution: - { - integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==, - } + resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} combined-stream@1.0.8: - resolution: - { - integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} + engines: {node: '>= 0.8'} commander@14.0.0: - resolution: - { - integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==, - } - engines: { node: ">=20" } + resolution: {integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==} + engines: {node: '>=20'} concat-map@0.0.1: - resolution: - { - integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==, - } + resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} content-disposition@1.0.0: - resolution: - { - integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==} + engines: {node: '>= 0.6'} content-type@1.0.5: - resolution: - { - integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==} + engines: {node: '>= 0.6'} cookie-signature@1.2.2: - resolution: - { - integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==, - } - engines: { node: ">=6.6.0" } + resolution: {integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==} + engines: {node: '>=6.6.0'} cookie@0.7.2: - resolution: - { - integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} + engines: {node: '>= 0.6'} cors@2.8.5: - resolution: - { - integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==} + engines: {node: '>= 0.10'} cross-spawn@7.0.6: - resolution: - { - integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==, - } - engines: { node: ">= 8" } + resolution: {integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==} + engines: {node: '>= 8'} data-view-buffer@1.0.2: - resolution: - { - integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==} + engines: {node: '>= 0.4'} data-view-byte-length@1.0.2: - resolution: - { - integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==} + engines: {node: '>= 0.4'} data-view-byte-offset@1.0.1: - resolution: - { - integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==} + engines: {node: '>= 0.4'} dateformat@4.6.3: - resolution: - { - integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==, - } + resolution: {integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==} debug@4.4.1: - resolution: - { - integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==, - } - engines: { node: ">=6.0" } + resolution: {integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==} + engines: {node: '>=6.0'} peerDependencies: - supports-color: "*" + supports-color: '*' peerDependenciesMeta: supports-color: optional: true deep-is@0.1.4: - resolution: - { - integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==, - } + resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} deepmerge@4.3.1: - resolution: - { - integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} + engines: {node: '>=0.10.0'} define-data-property@1.1.4: - resolution: - { - integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} + engines: {node: '>= 0.4'} define-properties@1.2.1: - resolution: - { - integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} + engines: {node: '>= 0.4'} delayed-stream@1.0.0: - resolution: - { - integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==, - } - engines: { node: ">=0.4.0" } + resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} + engines: {node: '>=0.4.0'} depd@2.0.0: - resolution: - { - integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==} + engines: {node: '>= 0.8'} dequal@2.0.3: - resolution: - { - integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} + engines: {node: '>=6'} devtools-protocol@0.0.1464554: - resolution: - { - integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==, - } + resolution: {integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==} diff-match-patch@1.0.5: - resolution: - { - integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==, - } + resolution: {integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==} doctrine@2.1.0: - resolution: - { - integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} + engines: {node: '>=0.10.0'} dotenv@16.5.0: - resolution: - { - integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==, - } - engines: { node: ">=12" } + resolution: {integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==} + engines: {node: '>=12'} dunder-proto@1.0.1: - resolution: - { - integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} + engines: {node: '>= 0.4'} ecdsa-sig-formatter@1.0.11: - resolution: - { - integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==, - } + resolution: {integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==} ee-first@1.1.1: - resolution: - { - integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==, - } + resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} encodeurl@2.0.0: - resolution: - { - integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==} + engines: {node: '>= 0.8'} end-of-stream@1.4.5: - resolution: - { - integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==, - } + resolution: {integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==} es-abstract@1.24.0: - resolution: - { - integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==} + engines: {node: '>= 0.4'} es-define-property@1.0.1: - resolution: - { - integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==} + engines: {node: '>= 0.4'} es-errors@1.3.0: - resolution: - { - integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} + engines: {node: '>= 0.4'} es-iterator-helpers@1.2.1: - resolution: - { - integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==} + engines: {node: '>= 0.4'} es-object-atoms@1.1.1: - resolution: - { - integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==} + engines: {node: '>= 0.4'} es-set-tostringtag@2.1.0: - resolution: - { - integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==} + engines: {node: '>= 0.4'} es-shim-unscopables@1.1.0: - resolution: - { - integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==} + engines: {node: '>= 0.4'} es-to-primitive@1.3.0: - resolution: - { - integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==} + engines: {node: '>= 0.4'} escape-html@1.0.3: - resolution: - { - integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==, - } + resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} escape-string-regexp@4.0.0: - resolution: - { - integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} + engines: {node: '>=10'} eslint-plugin-react@7.37.5: - resolution: - { - integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==, - } - engines: { node: ">=4" } + resolution: {integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==} + engines: {node: '>=4'} peerDependencies: eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 eslint-scope@8.4.0: - resolution: - { - integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} eslint-visitor-keys@3.4.3: - resolution: - { - integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==, - } - engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } + resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} eslint-visitor-keys@4.2.1: - resolution: - { - integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} eslint@9.29.0: - resolution: - { - integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} hasBin: true peerDependencies: - jiti: "*" + jiti: '*' peerDependenciesMeta: jiti: optional: true espree@10.4.0: - resolution: - { - integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} esquery@1.6.0: - resolution: - { - integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==, - } - engines: { node: ">=0.10" } + resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} + engines: {node: '>=0.10'} esrecurse@4.3.0: - resolution: - { - integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==, - } - engines: { node: ">=4.0" } + resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} + engines: {node: '>=4.0'} estraverse@5.3.0: - resolution: - { - integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==, - } - engines: { node: ">=4.0" } + resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==} + engines: {node: '>=4.0'} esutils@2.0.3: - resolution: - { - integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} + engines: {node: '>=0.10.0'} etag@1.8.1: - resolution: - { - integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==} + engines: {node: '>= 0.6'} event-target-shim@5.0.1: - resolution: - { - integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==} + engines: {node: '>=6'} eventsource-parser@3.0.3: - resolution: - { - integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==, - } - engines: { node: ">=20.0.0" } + resolution: {integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==} + engines: {node: '>=20.0.0'} eventsource@3.0.7: - resolution: - { - integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==, - } - engines: { node: ">=18.0.0" } + resolution: {integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==} + engines: {node: '>=18.0.0'} express-rate-limit@7.5.1: - resolution: - { - integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==, - } - engines: { node: ">= 16" } + resolution: {integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==} + engines: {node: '>= 16'} peerDependencies: - express: ">= 4.11" + express: '>= 4.11' express@5.1.0: - resolution: - { - integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==} + engines: {node: '>= 18'} extend@3.0.2: - resolution: - { - integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==, - } + resolution: {integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==} fast-copy@3.0.2: - resolution: - { - integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==, - } + resolution: {integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==} fast-deep-equal@3.1.3: - resolution: - { - integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==, - } + resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} fast-glob@3.3.3: - resolution: - { - integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==, - } - engines: { node: ">=8.6.0" } + resolution: {integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==} + engines: {node: '>=8.6.0'} fast-json-stable-stringify@2.1.0: - resolution: - { - integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==, - } + resolution: {integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==} fast-levenshtein@2.0.6: - resolution: - { - integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==, - } + resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} fast-redact@3.5.0: - resolution: - { - integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==} + engines: {node: '>=6'} fast-safe-stringify@2.1.1: - resolution: - { - integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==, - } + resolution: {integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==} fastq@1.19.1: - resolution: - { - integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==, - } + resolution: {integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==} fetch-cookie@3.1.0: - resolution: - { - integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==, - } + resolution: {integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==} file-entry-cache@8.0.0: - resolution: - { - integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==, - } - engines: { node: ">=16.0.0" } + resolution: {integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==} + engines: {node: '>=16.0.0'} fill-range@7.1.1: - resolution: - { - integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} + engines: {node: '>=8'} finalhandler@2.1.0: - resolution: - { - integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==} + engines: {node: '>= 0.8'} find-up@5.0.0: - resolution: - { - integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} + engines: {node: '>=10'} flat-cache@4.0.1: - resolution: - { - integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==, - } - engines: { node: ">=16" } + resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} + engines: {node: '>=16'} flatted@3.3.3: - resolution: - { - integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==, - } + resolution: {integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==} for-each@0.3.5: - resolution: - { - integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==} + engines: {node: '>= 0.4'} form-data-encoder@1.7.2: - resolution: - { - integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==, - } + resolution: {integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==} form-data@4.0.3: - resolution: - { - integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==, - } - engines: { node: ">= 6" } + resolution: {integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==} + engines: {node: '>= 6'} formdata-node@4.4.1: - resolution: - { - integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==, - } - engines: { node: ">= 12.20" } + resolution: {integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==} + engines: {node: '>= 12.20'} forwarded@0.2.0: - resolution: - { - integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==} + engines: {node: '>= 0.6'} fresh@2.0.0: - resolution: - { - integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==} + engines: {node: '>= 0.8'} fs.realpath@1.0.0: - resolution: - { - integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==, - } + resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==} fsevents@2.3.2: - resolution: - { - integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==, - } - engines: { node: ^8.16.0 || ^10.6.0 || >=11.0.0 } + resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==} + engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} os: [darwin] function-bind@1.1.2: - resolution: - { - integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==, - } + resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} function.prototype.name@1.1.8: - resolution: - { - integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==} + engines: {node: '>= 0.4'} functions-have-names@1.2.3: - resolution: - { - integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==, - } + resolution: {integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==} gaxios@6.7.1: - resolution: - { - integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==} + engines: {node: '>=14'} gcp-metadata@6.1.1: - resolution: - { - integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==} + engines: {node: '>=14'} get-intrinsic@1.3.0: - resolution: - { - integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==} + engines: {node: '>= 0.4'} get-proto@1.0.1: - resolution: - { - integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==} + engines: {node: '>= 0.4'} get-symbol-description@1.1.0: - resolution: - { - integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==} + engines: {node: '>= 0.4'} glob-parent@5.1.2: - resolution: - { - integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==, - } - engines: { node: ">= 6" } + resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} + engines: {node: '>= 6'} glob-parent@6.0.2: - resolution: - { - integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==, - } - engines: { node: ">=10.13.0" } + resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} + engines: {node: '>=10.13.0'} glob@7.2.3: - resolution: - { - integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==, - } + resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} deprecated: Glob versions prior to v9 are no longer supported globals@14.0.0: - resolution: - { - integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==} + engines: {node: '>=18'} globals@16.2.0: - resolution: - { - integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==} + engines: {node: '>=18'} globalthis@1.0.4: - resolution: - { - integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==} + engines: {node: '>= 0.4'} google-auth-library@9.15.1: - resolution: - { - integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==} + engines: {node: '>=14'} google-logging-utils@0.0.2: - resolution: - { - integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==} + engines: {node: '>=14'} gopd@1.2.0: - resolution: - { - integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==} + engines: {node: '>= 0.4'} graphemer@1.4.0: - resolution: - { - integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==, - } + resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} gtoken@7.1.0: - resolution: - { - integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==, - } - engines: { node: ">=14.0.0" } + resolution: {integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==} + engines: {node: '>=14.0.0'} has-bigints@1.1.0: - resolution: - { - integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==} + engines: {node: '>= 0.4'} has-flag@4.0.0: - resolution: - { - integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} + engines: {node: '>=8'} has-property-descriptors@1.0.2: - resolution: - { - integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==, - } + resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} has-proto@1.2.0: - resolution: - { - integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==} + engines: {node: '>= 0.4'} has-symbols@1.1.0: - resolution: - { - integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==} + engines: {node: '>= 0.4'} has-tostringtag@1.0.2: - resolution: - { - integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==} + engines: {node: '>= 0.4'} hasown@2.0.2: - resolution: - { - integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} + engines: {node: '>= 0.4'} help-me@5.0.0: - resolution: - { - integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==, - } + resolution: {integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==} http-errors@2.0.0: - resolution: - { - integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==} + engines: {node: '>= 0.8'} https-proxy-agent@7.0.6: - resolution: - { - integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==, - } - engines: { node: ">= 14" } + resolution: {integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==} + engines: {node: '>= 14'} humanize-ms@1.2.1: - resolution: - { - integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==, - } + resolution: {integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==} + + husky@9.1.7: + resolution: {integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==} + engines: {node: '>=18'} + hasBin: true iconv-lite@0.6.3: - resolution: - { - integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} + engines: {node: '>=0.10.0'} ignore@5.3.2: - resolution: - { - integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==, - } - engines: { node: ">= 4" } + resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} + engines: {node: '>= 4'} ignore@7.0.5: - resolution: - { - integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==, - } - engines: { node: ">= 4" } + resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==} + engines: {node: '>= 4'} import-fresh@3.3.1: - resolution: - { - integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==} + engines: {node: '>=6'} imurmurhash@0.1.4: - resolution: - { - integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==, - } - engines: { node: ">=0.8.19" } + resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} + engines: {node: '>=0.8.19'} inflight@1.0.6: - resolution: - { - integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==, - } + resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. inherits@2.0.4: - resolution: - { - integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==, - } + resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} internal-slot@1.1.0: - resolution: - { - integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==} + engines: {node: '>= 0.4'} interpret@1.4.0: - resolution: - { - integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==} + engines: {node: '>= 0.10'} ipaddr.js@1.9.1: - resolution: - { - integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==} + engines: {node: '>= 0.10'} is-array-buffer@3.0.5: - resolution: - { - integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==} + engines: {node: '>= 0.4'} is-async-function@2.1.1: - resolution: - { - integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==} + engines: {node: '>= 0.4'} is-bigint@1.1.0: - resolution: - { - integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==} + engines: {node: '>= 0.4'} is-boolean-object@1.2.2: - resolution: - { - integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==} + engines: {node: '>= 0.4'} is-callable@1.2.7: - resolution: - { - integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==} + engines: {node: '>= 0.4'} is-core-module@2.16.1: - resolution: - { - integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==} + engines: {node: '>= 0.4'} is-data-view@1.0.2: - resolution: - { - integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==} + engines: {node: '>= 0.4'} is-date-object@1.1.0: - resolution: - { - integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==} + engines: {node: '>= 0.4'} is-extglob@2.1.1: - resolution: - { - integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} + engines: {node: '>=0.10.0'} is-finalizationregistry@1.1.1: - resolution: - { - integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==} + engines: {node: '>= 0.4'} is-generator-function@1.1.0: - resolution: - { - integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==} + engines: {node: '>= 0.4'} is-glob@4.0.3: - resolution: - { - integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} + engines: {node: '>=0.10.0'} is-map@2.0.3: - resolution: - { - integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==} + engines: {node: '>= 0.4'} is-negative-zero@2.0.3: - resolution: - { - integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} + engines: {node: '>= 0.4'} is-number-object@1.1.1: - resolution: - { - integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==} + engines: {node: '>= 0.4'} is-number@7.0.0: - resolution: - { - integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==, - } - engines: { node: ">=0.12.0" } + resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} + engines: {node: '>=0.12.0'} is-promise@4.0.0: - resolution: - { - integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==, - } + resolution: {integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==} is-regex@1.2.1: - resolution: - { - integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==} + engines: {node: '>= 0.4'} is-set@2.0.3: - resolution: - { - integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==} + engines: {node: '>= 0.4'} is-shared-array-buffer@1.0.4: - resolution: - { - integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==} + engines: {node: '>= 0.4'} is-stream@2.0.1: - resolution: - { - integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==} + engines: {node: '>=8'} is-string@1.1.1: - resolution: - { - integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==} + engines: {node: '>= 0.4'} is-symbol@1.1.1: - resolution: - { - integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==} + engines: {node: '>= 0.4'} is-typed-array@1.1.15: - resolution: - { - integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==} + engines: {node: '>= 0.4'} is-weakmap@2.0.2: - resolution: - { - integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==} + engines: {node: '>= 0.4'} is-weakref@1.1.1: - resolution: - { - integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==} + engines: {node: '>= 0.4'} is-weakset@2.0.4: - resolution: - { - integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==} + engines: {node: '>= 0.4'} isarray@2.0.5: - resolution: - { - integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==, - } + resolution: {integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==} isexe@2.0.0: - resolution: - { - integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==, - } + resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} iterator.prototype@1.1.5: - resolution: - { - integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==} + engines: {node: '>= 0.4'} joycon@3.1.1: - resolution: - { - integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==} + engines: {node: '>=10'} js-tokens@4.0.0: - resolution: - { - integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==, - } + resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} js-yaml@4.1.0: - resolution: - { - integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==, - } + resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} hasBin: true json-bigint@1.0.0: - resolution: - { - integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==, - } + resolution: {integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==} json-buffer@3.0.1: - resolution: - { - integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==, - } + resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==} json-schema-traverse@0.4.1: - resolution: - { - integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==, - } + resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==} json-schema@0.4.0: - resolution: - { - integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==, - } + resolution: {integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==} json-stable-stringify-without-jsonify@1.0.1: - resolution: - { - integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==, - } + resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} jsondiffpatch@0.6.0: - resolution: - { - integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==, - } - engines: { node: ^18.0.0 || >=20.0.0 } + resolution: {integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==} + engines: {node: ^18.0.0 || >=20.0.0} hasBin: true jsx-ast-utils@3.3.5: - resolution: - { - integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==, - } - engines: { node: ">=4.0" } + resolution: {integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==} + engines: {node: '>=4.0'} jwa@2.0.1: - resolution: - { - integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==, - } + resolution: {integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==} jws@4.0.0: - resolution: - { - integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==, - } + resolution: {integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==} keyv@4.5.4: - resolution: - { - integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==, - } + resolution: {integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==} levn@0.4.1: - resolution: - { - integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} + engines: {node: '>= 0.8.0'} locate-path@6.0.0: - resolution: - { - integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} + engines: {node: '>=10'} lodash.merge@4.6.2: - resolution: - { - integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==, - } + resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} loose-envify@1.4.0: - resolution: - { - integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==, - } + resolution: {integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==} hasBin: true math-intrinsics@1.1.0: - resolution: - { - integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} + engines: {node: '>= 0.4'} media-typer@1.1.0: - resolution: - { - integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==} + engines: {node: '>= 0.8'} merge-descriptors@2.0.0: - resolution: - { - integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==} + engines: {node: '>=18'} merge2@1.4.1: - resolution: - { - integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==, - } - engines: { node: ">= 8" } + resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} + engines: {node: '>= 8'} micromatch@4.0.8: - resolution: - { - integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==, - } - engines: { node: ">=8.6" } + resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} + engines: {node: '>=8.6'} mime-db@1.52.0: - resolution: - { - integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} + engines: {node: '>= 0.6'} mime-db@1.54.0: - resolution: - { - integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==} + engines: {node: '>= 0.6'} mime-types@2.1.35: - resolution: - { - integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==} + engines: {node: '>= 0.6'} mime-types@3.0.1: - resolution: - { - integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==} + engines: {node: '>= 0.6'} minimatch@3.1.2: - resolution: - { - integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==, - } + resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} minimatch@9.0.5: - resolution: - { - integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==, - } - engines: { node: ">=16 || 14 >=14.17" } + resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} + engines: {node: '>=16 || 14 >=14.17'} minimist@1.2.8: - resolution: - { - integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==, - } + resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} ms@2.1.3: - resolution: - { - integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, - } + resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} nanoid@3.3.11: - resolution: - { - integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==, - } - engines: { node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1 } + resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==} + engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} hasBin: true natural-compare@1.4.0: - resolution: - { - integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==, - } + resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} negotiator@1.0.0: - resolution: - { - integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==} + engines: {node: '>= 0.6'} node-domexception@1.0.0: - resolution: - { - integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==, - } - engines: { node: ">=10.5.0" } + resolution: {integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==} + engines: {node: '>=10.5.0'} node-fetch@2.7.0: - resolution: - { - integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==, - } - engines: { node: 4.x || >=6.0.0 } + resolution: {integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==} + engines: {node: 4.x || >=6.0.0} peerDependencies: encoding: ^0.1.0 peerDependenciesMeta: @@ -2035,60 +1205,36 @@ packages: optional: true object-assign@4.1.1: - resolution: - { - integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} + engines: {node: '>=0.10.0'} object-inspect@1.13.4: - resolution: - { - integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==} + engines: {node: '>= 0.4'} object-keys@1.1.1: - resolution: - { - integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} + engines: {node: '>= 0.4'} object.assign@4.1.7: - resolution: - { - integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==} + engines: {node: '>= 0.4'} object.entries@1.1.9: - resolution: - { - integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==} + engines: {node: '>= 0.4'} object.fromentries@2.0.8: - resolution: - { - integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==} + engines: {node: '>= 0.4'} object.values@1.2.1: - resolution: - { - integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==} + engines: {node: '>= 0.4'} ollama-ai-provider@1.2.0: - resolution: - { - integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 peerDependenciesMeta: @@ -2096,30 +1242,18 @@ packages: optional: true on-exit-leak-free@2.1.2: - resolution: - { - integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==, - } - engines: { node: ">=14.0.0" } + resolution: {integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==} + engines: {node: '>=14.0.0'} on-finished@2.4.1: - resolution: - { - integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==} + engines: {node: '>= 0.8'} once@1.4.0: - resolution: - { - integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==, - } + resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==} openai@4.104.0: - resolution: - { - integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==, - } + resolution: {integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==} hasBin: true peerDependencies: ws: ^8.18.0 @@ -2131,823 +1265,469 @@ packages: optional: true optionator@0.9.4: - resolution: - { - integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} + engines: {node: '>= 0.8.0'} own-keys@1.0.1: - resolution: - { - integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==} + engines: {node: '>= 0.4'} p-limit@3.1.0: - resolution: - { - integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} + engines: {node: '>=10'} p-locate@5.0.0: - resolution: - { - integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} + engines: {node: '>=10'} parent-module@1.0.1: - resolution: - { - integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} + engines: {node: '>=6'} parseurl@1.3.3: - resolution: - { - integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==} + engines: {node: '>= 0.8'} partial-json@0.1.7: - resolution: - { - integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==, - } + resolution: {integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==} path-exists@4.0.0: - resolution: - { - integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} + engines: {node: '>=8'} path-is-absolute@1.0.1: - resolution: - { - integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} + engines: {node: '>=0.10.0'} path-key@3.1.1: - resolution: - { - integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==} + engines: {node: '>=8'} path-parse@1.0.7: - resolution: - { - integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==, - } + resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} path-to-regexp@8.2.0: - resolution: - { - integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==, - } - engines: { node: ">=16" } + resolution: {integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==} + engines: {node: '>=16'} picomatch@2.3.1: - resolution: - { - integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==, - } - engines: { node: ">=8.6" } + resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} + engines: {node: '>=8.6'} pino-abstract-transport@2.0.0: - resolution: - { - integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==, - } + resolution: {integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==} pino-pretty@13.0.0: - resolution: - { - integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==, - } + resolution: {integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==} hasBin: true pino-std-serializers@7.0.0: - resolution: - { - integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==, - } + resolution: {integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==} pino@9.7.0: - resolution: - { - integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==, - } + resolution: {integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==} hasBin: true pkce-challenge@5.0.0: - resolution: - { - integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==, - } - engines: { node: ">=16.20.0" } + resolution: {integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==} + engines: {node: '>=16.20.0'} playwright-core@1.53.1: - resolution: - { - integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==} + engines: {node: '>=18'} hasBin: true playwright@1.53.1: - resolution: - { - integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==} + engines: {node: '>=18'} hasBin: true possible-typed-array-names@1.1.0: - resolution: - { - integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==} + engines: {node: '>= 0.4'} prelude-ls@1.2.1: - resolution: - { - integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} + engines: {node: '>= 0.8.0'} prettier@3.6.1: - resolution: - { - integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==} + engines: {node: '>=14'} hasBin: true process-warning@5.0.0: - resolution: - { - integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==, - } + resolution: {integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==} prop-types@15.8.1: - resolution: - { - integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==, - } + resolution: {integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==} proxy-addr@2.0.7: - resolution: - { - integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==} + engines: {node: '>= 0.10'} pump@3.0.3: - resolution: - { - integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==, - } + resolution: {integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==} punycode@2.3.1: - resolution: - { - integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} + engines: {node: '>=6'} qs@6.14.0: - resolution: - { - integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==, - } - engines: { node: ">=0.6" } + resolution: {integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==} + engines: {node: '>=0.6'} queue-microtask@1.2.3: - resolution: - { - integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==, - } + resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} quick-format-unescaped@4.0.4: - resolution: - { - integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==, - } + resolution: {integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==} range-parser@1.2.1: - resolution: - { - integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==} + engines: {node: '>= 0.6'} raw-body@3.0.0: - resolution: - { - integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==} + engines: {node: '>= 0.8'} react-is@16.13.1: - resolution: - { - integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==, - } + resolution: {integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==} react@19.1.0: - resolution: - { - integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==} + engines: {node: '>=0.10.0'} real-require@0.2.0: - resolution: - { - integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==, - } - engines: { node: ">= 12.13.0" } + resolution: {integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==} + engines: {node: '>= 12.13.0'} rechoir@0.6.2: - resolution: - { - integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==} + engines: {node: '>= 0.10'} reflect.getprototypeof@1.0.10: - resolution: - { - integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==} + engines: {node: '>= 0.4'} regexp.prototype.flags@1.5.4: - resolution: - { - integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==} + engines: {node: '>= 0.4'} resolve-from@4.0.0: - resolution: - { - integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==, - } - engines: { node: ">=4" } + resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} + engines: {node: '>=4'} resolve@1.22.10: - resolution: - { - integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} + engines: {node: '>= 0.4'} hasBin: true resolve@2.0.0-next.5: - resolution: - { - integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==, - } + resolution: {integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==} hasBin: true reusify@1.1.0: - resolution: - { - integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==, - } - engines: { iojs: ">=1.0.0", node: ">=0.10.0" } + resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} + engines: {iojs: '>=1.0.0', node: '>=0.10.0'} router@2.2.0: - resolution: - { - integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==} + engines: {node: '>= 18'} run-parallel@1.2.0: - resolution: - { - integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==, - } + resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} safe-array-concat@1.1.3: - resolution: - { - integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==, - } - engines: { node: ">=0.4" } + resolution: {integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==} + engines: {node: '>=0.4'} safe-buffer@5.2.1: - resolution: - { - integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==, - } + resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} safe-push-apply@1.0.0: - resolution: - { - integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==} + engines: {node: '>= 0.4'} safe-regex-test@1.1.0: - resolution: - { - integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==} + engines: {node: '>= 0.4'} safe-stable-stringify@2.5.0: - resolution: - { - integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==} + engines: {node: '>=10'} safer-buffer@2.1.2: - resolution: - { - integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==, - } + resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} secure-json-parse@2.7.0: - resolution: - { - integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==, - } + resolution: {integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==} semver@6.3.1: - resolution: - { - integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==, - } + resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} hasBin: true semver@7.7.2: - resolution: - { - integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==} + engines: {node: '>=10'} hasBin: true send@1.2.0: - resolution: - { - integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==} + engines: {node: '>= 18'} serve-static@2.2.0: - resolution: - { - integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==} + engines: {node: '>= 18'} set-cookie-parser@2.7.1: - resolution: - { - integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==, - } + resolution: {integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==} set-function-length@1.2.2: - resolution: - { - integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==} + engines: {node: '>= 0.4'} set-function-name@2.0.2: - resolution: - { - integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==} + engines: {node: '>= 0.4'} set-proto@1.0.0: - resolution: - { - integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==} + engines: {node: '>= 0.4'} setprototypeof@1.2.0: - resolution: - { - integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==, - } + resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} shebang-command@2.0.0: - resolution: - { - integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==} + engines: {node: '>=8'} shebang-regex@3.0.0: - resolution: - { - integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==} + engines: {node: '>=8'} shelljs@0.8.5: - resolution: - { - integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==, - } - engines: { node: ">=4" } + resolution: {integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==} + engines: {node: '>=4'} hasBin: true shx@0.3.4: - resolution: - { - integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==} + engines: {node: '>=6'} hasBin: true side-channel-list@1.0.0: - resolution: - { - integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==} + engines: {node: '>= 0.4'} side-channel-map@1.0.1: - resolution: - { - integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==} + engines: {node: '>= 0.4'} side-channel-weakmap@1.0.2: - resolution: - { - integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==} + engines: {node: '>= 0.4'} side-channel@1.1.0: - resolution: - { - integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==} + engines: {node: '>= 0.4'} sonic-boom@4.2.0: - resolution: - { - integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==, - } + resolution: {integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==} split2@4.2.0: - resolution: - { - integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==, - } - engines: { node: ">= 10.x" } + resolution: {integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==} + engines: {node: '>= 10.x'} statuses@2.0.1: - resolution: - { - integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==} + engines: {node: '>= 0.8'} statuses@2.0.2: - resolution: - { - integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==} + engines: {node: '>= 0.8'} stop-iteration-iterator@1.1.0: - resolution: - { - integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==} + engines: {node: '>= 0.4'} string.prototype.matchall@4.0.12: - resolution: - { - integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==} + engines: {node: '>= 0.4'} string.prototype.repeat@1.0.0: - resolution: - { - integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==, - } + resolution: {integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==} string.prototype.trim@1.2.10: - resolution: - { - integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==} + engines: {node: '>= 0.4'} string.prototype.trimend@1.0.9: - resolution: - { - integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==} + engines: {node: '>= 0.4'} string.prototype.trimstart@1.0.8: - resolution: - { - integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==} + engines: {node: '>= 0.4'} strip-json-comments@3.1.1: - resolution: - { - integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} + engines: {node: '>=8'} supports-color@7.2.0: - resolution: - { - integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} + engines: {node: '>=8'} supports-preserve-symlinks-flag@1.0.0: - resolution: - { - integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} + engines: {node: '>= 0.4'} swr@2.3.3: - resolution: - { - integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==, - } + resolution: {integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==} peerDependencies: react: ^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 thread-stream@3.1.0: - resolution: - { - integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==, - } + resolution: {integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==} throttleit@2.1.0: - resolution: - { - integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==} + engines: {node: '>=18'} tldts-core@6.1.86: - resolution: - { - integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==, - } + resolution: {integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==} tldts@6.1.86: - resolution: - { - integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==, - } + resolution: {integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==} hasBin: true to-regex-range@5.0.1: - resolution: - { - integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==, - } - engines: { node: ">=8.0" } + resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} + engines: {node: '>=8.0'} toidentifier@1.0.1: - resolution: - { - integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==, - } - engines: { node: ">=0.6" } + resolution: {integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==} + engines: {node: '>=0.6'} tough-cookie@5.1.2: - resolution: - { - integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==, - } - engines: { node: ">=16" } + resolution: {integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==} + engines: {node: '>=16'} tr46@0.0.3: - resolution: - { - integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==, - } + resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} ts-api-utils@2.1.0: - resolution: - { - integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==, - } - engines: { node: ">=18.12" } + resolution: {integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==} + engines: {node: '>=18.12'} peerDependencies: - typescript: ">=4.8.4" + typescript: '>=4.8.4' type-check@0.4.0: - resolution: - { - integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} + engines: {node: '>= 0.8.0'} type-is@2.0.1: - resolution: - { - integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==} + engines: {node: '>= 0.6'} typed-array-buffer@1.0.3: - resolution: - { - integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==} + engines: {node: '>= 0.4'} typed-array-byte-length@1.0.3: - resolution: - { - integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==} + engines: {node: '>= 0.4'} typed-array-byte-offset@1.0.4: - resolution: - { - integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==} + engines: {node: '>= 0.4'} typed-array-length@1.0.7: - resolution: - { - integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==} + engines: {node: '>= 0.4'} typescript-eslint@8.35.0: - resolution: - { - integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" + typescript: '>=4.8.4 <5.9.0' typescript@5.8.3: - resolution: - { - integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==, - } - engines: { node: ">=14.17" } + resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} + engines: {node: '>=14.17'} hasBin: true unbox-primitive@1.1.0: - resolution: - { - integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==} + engines: {node: '>= 0.4'} undici-types@5.26.5: - resolution: - { - integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==, - } + resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} unpipe@1.0.0: - resolution: - { - integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==} + engines: {node: '>= 0.8'} uri-js@4.4.1: - resolution: - { - integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==, - } + resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} use-sync-external-store@1.5.0: - resolution: - { - integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==, - } + resolution: {integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==} peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 uuid@9.0.1: - resolution: - { - integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==, - } + resolution: {integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==} hasBin: true vary@1.1.2: - resolution: - { - integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} + engines: {node: '>= 0.8'} web-streams-polyfill@4.0.0-beta.3: - resolution: - { - integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==, - } - engines: { node: ">= 14" } + resolution: {integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==} + engines: {node: '>= 14'} webidl-conversions@3.0.1: - resolution: - { - integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==, - } + resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==} whatwg-url@5.0.0: - resolution: - { - integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==, - } + resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} which-boxed-primitive@1.1.1: - resolution: - { - integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==} + engines: {node: '>= 0.4'} which-builtin-type@1.2.1: - resolution: - { - integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==} + engines: {node: '>= 0.4'} which-collection@1.0.2: - resolution: - { - integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} + engines: {node: '>= 0.4'} which-typed-array@1.1.19: - resolution: - { - integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==} + engines: {node: '>= 0.4'} which@2.0.2: - resolution: - { - integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==, - } - engines: { node: ">= 8" } + resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} + engines: {node: '>= 8'} hasBin: true word-wrap@1.2.5: - resolution: - { - integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} + engines: {node: '>=0.10.0'} wrappy@1.0.2: - resolution: - { - integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==, - } + resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==} ws@8.18.2: - resolution: - { - integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==, - } - engines: { node: ">=10.0.0" } + resolution: {integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==} + engines: {node: '>=10.0.0'} peerDependencies: bufferutil: ^4.0.1 - utf-8-validate: ">=5.0.2" + utf-8-validate: '>=5.0.2' peerDependenciesMeta: bufferutil: optional: true @@ -2955,148 +1735,140 @@ packages: optional: true yocto-queue@0.1.0: - resolution: - { - integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} + engines: {node: '>=10'} zod-to-json-schema@3.24.6: - resolution: - { - integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==, - } + resolution: {integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==} peerDependencies: zod: ^3.24.1 zod@3.25.67: - resolution: - { - integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==, - } + resolution: {integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==} snapshots: - "@ai-sdk/anthropic@1.2.12(zod@3.25.67)": + + '@ai-sdk/anthropic@1.2.12(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/azure@1.3.23(zod@3.25.67)": + '@ai-sdk/azure@1.3.23(zod@3.25.67)': dependencies: - "@ai-sdk/openai": 1.3.22(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai': 1.3.22(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/cerebras@0.2.14(zod@3.25.67)": + '@ai-sdk/cerebras@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/deepseek@0.2.14(zod@3.25.67)": + '@ai-sdk/deepseek@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/google@1.2.19(zod@3.25.67)": + '@ai-sdk/google@1.2.19(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/groq@1.2.9(zod@3.25.67)": + '@ai-sdk/groq@1.2.9(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/mistral@1.2.8(zod@3.25.67)": + '@ai-sdk/mistral@1.2.8(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)": + '@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/openai@1.3.22(zod@3.25.67)": + '@ai-sdk/openai@1.3.22(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/perplexity@1.1.9(zod@3.25.67)": + '@ai-sdk/perplexity@1.1.9(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/provider-utils@2.2.8(zod@3.25.67)": + '@ai-sdk/provider-utils@2.2.8(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 + '@ai-sdk/provider': 1.1.3 nanoid: 3.3.11 secure-json-parse: 2.7.0 zod: 3.25.67 - "@ai-sdk/provider@1.1.3": + '@ai-sdk/provider@1.1.3': dependencies: json-schema: 0.4.0 - "@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)": + '@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)': dependencies: - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) - "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + '@ai-sdk/ui-utils': 1.2.11(zod@3.25.67) react: 19.1.0 swr: 2.3.3(react@19.1.0) throttleit: 2.1.0 optionalDependencies: zod: 3.25.67 - "@ai-sdk/togetherai@0.2.14(zod@3.25.67)": + '@ai-sdk/togetherai@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/ui-utils@1.2.11(zod@3.25.67)": + '@ai-sdk/ui-utils@1.2.11(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 zod-to-json-schema: 3.24.6(zod@3.25.67) - "@ai-sdk/xai@1.2.16(zod@3.25.67)": + '@ai-sdk/xai@1.2.16(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@anthropic-ai/sdk@0.39.0": + '@anthropic-ai/sdk@0.39.0': dependencies: - "@types/node": 18.19.112 - "@types/node-fetch": 2.6.12 + '@types/node': 18.19.112 + '@types/node-fetch': 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -3105,10 +1877,10 @@ snapshots: transitivePeerDependencies: - encoding - "@browserbasehq/sdk@2.6.0": + '@browserbasehq/sdk@2.6.0': dependencies: - "@types/node": 18.19.112 - "@types/node-fetch": 2.6.12 + '@types/node': 18.19.112 + '@types/node-fetch': 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -3117,11 +1889,11 @@ snapshots: transitivePeerDependencies: - encoding - "@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)": + '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)': dependencies: - "@anthropic-ai/sdk": 0.39.0 - "@browserbasehq/sdk": 2.6.0 - "@google/genai": 0.8.0 + '@anthropic-ai/sdk': 0.39.0 + '@browserbasehq/sdk': 2.6.0 + '@google/genai': 0.8.0 ai: 4.3.16(react@19.1.0)(zod@3.25.67) deepmerge: 4.3.1 devtools-protocol: 0.0.1464554 @@ -3135,17 +1907,17 @@ snapshots: zod: 3.25.67 zod-to-json-schema: 3.24.6(zod@3.25.67) optionalDependencies: - "@ai-sdk/anthropic": 1.2.12(zod@3.25.67) - "@ai-sdk/azure": 1.3.23(zod@3.25.67) - "@ai-sdk/cerebras": 0.2.14(zod@3.25.67) - "@ai-sdk/deepseek": 0.2.14(zod@3.25.67) - "@ai-sdk/google": 1.2.19(zod@3.25.67) - "@ai-sdk/groq": 1.2.9(zod@3.25.67) - "@ai-sdk/mistral": 1.2.8(zod@3.25.67) - "@ai-sdk/openai": 1.3.22(zod@3.25.67) - "@ai-sdk/perplexity": 1.1.9(zod@3.25.67) - "@ai-sdk/togetherai": 0.2.14(zod@3.25.67) - "@ai-sdk/xai": 1.2.16(zod@3.25.67) + '@ai-sdk/anthropic': 1.2.12(zod@3.25.67) + '@ai-sdk/azure': 1.3.23(zod@3.25.67) + '@ai-sdk/cerebras': 0.2.14(zod@3.25.67) + '@ai-sdk/deepseek': 0.2.14(zod@3.25.67) + '@ai-sdk/google': 1.2.19(zod@3.25.67) + '@ai-sdk/groq': 1.2.9(zod@3.25.67) + '@ai-sdk/mistral': 1.2.8(zod@3.25.67) + '@ai-sdk/openai': 1.3.22(zod@3.25.67) + '@ai-sdk/perplexity': 1.1.9(zod@3.25.67) + '@ai-sdk/togetherai': 0.2.14(zod@3.25.67) + '@ai-sdk/xai': 1.2.16(zod@3.25.67) ollama-ai-provider: 1.2.0(zod@3.25.67) transitivePeerDependencies: - bufferutil @@ -3154,32 +1926,32 @@ snapshots: - supports-color - utf-8-validate - "@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)": + '@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)': dependencies: eslint: 9.29.0 eslint-visitor-keys: 3.4.3 - "@eslint-community/regexpp@4.12.1": {} + '@eslint-community/regexpp@4.12.1': {} - "@eslint/config-array@0.20.1": + '@eslint/config-array@0.20.1': dependencies: - "@eslint/object-schema": 2.1.6 + '@eslint/object-schema': 2.1.6 debug: 4.4.1 minimatch: 3.1.2 transitivePeerDependencies: - supports-color - "@eslint/config-helpers@0.2.3": {} + '@eslint/config-helpers@0.2.3': {} - "@eslint/core@0.14.0": + '@eslint/core@0.14.0': dependencies: - "@types/json-schema": 7.0.15 + '@types/json-schema': 7.0.15 - "@eslint/core@0.15.1": + '@eslint/core@0.15.1': dependencies: - "@types/json-schema": 7.0.15 + '@types/json-schema': 7.0.15 - "@eslint/eslintrc@3.3.1": + '@eslint/eslintrc@3.3.1': dependencies: ajv: 6.12.6 debug: 4.4.1 @@ -3193,16 +1965,16 @@ snapshots: transitivePeerDependencies: - supports-color - "@eslint/js@9.29.0": {} + '@eslint/js@9.29.0': {} - "@eslint/object-schema@2.1.6": {} + '@eslint/object-schema@2.1.6': {} - "@eslint/plugin-kit@0.3.3": + '@eslint/plugin-kit@0.3.3': dependencies: - "@eslint/core": 0.15.1 + '@eslint/core': 0.15.1 levn: 0.4.1 - "@google/genai@0.8.0": + '@google/genai@0.8.0': dependencies: google-auth-library: 9.15.1 ws: 8.18.2 @@ -3212,20 +1984,20 @@ snapshots: - supports-color - utf-8-validate - "@humanfs/core@0.19.1": {} + '@humanfs/core@0.19.1': {} - "@humanfs/node@0.16.6": + '@humanfs/node@0.16.6': dependencies: - "@humanfs/core": 0.19.1 - "@humanwhocodes/retry": 0.3.1 + '@humanfs/core': 0.19.1 + '@humanwhocodes/retry': 0.3.1 - "@humanwhocodes/module-importer@1.0.1": {} + '@humanwhocodes/module-importer@1.0.1': {} - "@humanwhocodes/retry@0.3.1": {} + '@humanwhocodes/retry@0.3.1': {} - "@humanwhocodes/retry@0.4.3": {} + '@humanwhocodes/retry@0.4.3': {} - "@modelcontextprotocol/sdk@1.13.1": + '@modelcontextprotocol/sdk@1.13.1': dependencies: ajv: 6.12.6 content-type: 1.0.5 @@ -3241,47 +2013,47 @@ snapshots: transitivePeerDependencies: - supports-color - "@nodelib/fs.scandir@2.1.5": + '@nodelib/fs.scandir@2.1.5': dependencies: - "@nodelib/fs.stat": 2.0.5 + '@nodelib/fs.stat': 2.0.5 run-parallel: 1.2.0 - "@nodelib/fs.stat@2.0.5": {} + '@nodelib/fs.stat@2.0.5': {} - "@nodelib/fs.walk@1.2.8": + '@nodelib/fs.walk@1.2.8': dependencies: - "@nodelib/fs.scandir": 2.1.5 + '@nodelib/fs.scandir': 2.1.5 fastq: 1.19.1 - "@opentelemetry/api@1.9.0": {} + '@opentelemetry/api@1.9.0': {} - "@playwright/test@1.53.1": + '@playwright/test@1.53.1': dependencies: playwright: 1.53.1 - "@types/diff-match-patch@1.0.36": {} + '@types/diff-match-patch@1.0.36': {} - "@types/estree@1.0.8": {} + '@types/estree@1.0.8': {} - "@types/json-schema@7.0.15": {} + '@types/json-schema@7.0.15': {} - "@types/node-fetch@2.6.12": + '@types/node-fetch@2.6.12': dependencies: - "@types/node": 18.19.112 + '@types/node': 18.19.112 form-data: 4.0.3 - "@types/node@18.19.112": + '@types/node@18.19.112': dependencies: undici-types: 5.26.5 - "@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@eslint-community/regexpp": 4.12.1 - "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/scope-manager": 8.35.0 - "@typescript-eslint/type-utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/visitor-keys": 8.35.0 + '@eslint-community/regexpp': 4.12.1 + '@typescript-eslint/parser': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/type-utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.35.0 eslint: 9.29.0 graphemer: 1.4.0 ignore: 7.0.5 @@ -3291,40 +2063,40 @@ snapshots: transitivePeerDependencies: - supports-color - "@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@typescript-eslint/scope-manager": 8.35.0 - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) - "@typescript-eslint/visitor-keys": 8.35.0 + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.35.0 debug: 4.4.1 eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: - supports-color - "@typescript-eslint/project-service@8.35.0(typescript@5.8.3)": + '@typescript-eslint/project-service@8.35.0(typescript@5.8.3)': dependencies: - "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) - "@typescript-eslint/types": 8.35.0 + '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) + '@typescript-eslint/types': 8.35.0 debug: 4.4.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - "@typescript-eslint/scope-manager@8.35.0": + '@typescript-eslint/scope-manager@8.35.0': dependencies: - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/visitor-keys": 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/visitor-keys': 8.35.0 - "@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)": + '@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)': dependencies: typescript: 5.8.3 - "@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) - "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) debug: 4.4.1 eslint: 9.29.0 ts-api-utils: 2.1.0(typescript@5.8.3) @@ -3332,14 +2104,14 @@ snapshots: transitivePeerDependencies: - supports-color - "@typescript-eslint/types@8.35.0": {} + '@typescript-eslint/types@8.35.0': {} - "@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)": + '@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)': dependencies: - "@typescript-eslint/project-service": 8.35.0(typescript@5.8.3) - "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/visitor-keys": 8.35.0 + '@typescript-eslint/project-service': 8.35.0(typescript@5.8.3) + '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/visitor-keys': 8.35.0 debug: 4.4.1 fast-glob: 3.3.3 is-glob: 4.0.3 @@ -3350,20 +2122,20 @@ snapshots: transitivePeerDependencies: - supports-color - "@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) - "@typescript-eslint/scope-manager": 8.35.0 - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0) + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: - supports-color - "@typescript-eslint/visitor-keys@8.35.0": + '@typescript-eslint/visitor-keys@8.35.0': dependencies: - "@typescript-eslint/types": 8.35.0 + '@typescript-eslint/types': 8.35.0 eslint-visitor-keys: 4.2.1 abort-controller@3.0.0: @@ -3389,11 +2161,11 @@ snapshots: ai@4.3.16(react@19.1.0)(zod@3.25.67): dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) - "@ai-sdk/react": 1.2.12(react@19.1.0)(zod@3.25.67) - "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) - "@opentelemetry/api": 1.9.0 + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + '@ai-sdk/react': 1.2.12(react@19.1.0)(zod@3.25.67) + '@ai-sdk/ui-utils': 1.2.11(zod@3.25.67) + '@opentelemetry/api': 1.9.0 jsondiffpatch: 0.6.0 zod: 3.25.67 optionalDependencies: @@ -3791,19 +2563,19 @@ snapshots: eslint@9.29.0: dependencies: - "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) - "@eslint-community/regexpp": 4.12.1 - "@eslint/config-array": 0.20.1 - "@eslint/config-helpers": 0.2.3 - "@eslint/core": 0.14.0 - "@eslint/eslintrc": 3.3.1 - "@eslint/js": 9.29.0 - "@eslint/plugin-kit": 0.3.3 - "@humanfs/node": 0.16.6 - "@humanwhocodes/module-importer": 1.0.1 - "@humanwhocodes/retry": 0.4.3 - "@types/estree": 1.0.8 - "@types/json-schema": 7.0.15 + '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0) + '@eslint-community/regexpp': 4.12.1 + '@eslint/config-array': 0.20.1 + '@eslint/config-helpers': 0.2.3 + '@eslint/core': 0.14.0 + '@eslint/eslintrc': 3.3.1 + '@eslint/js': 9.29.0 + '@eslint/plugin-kit': 0.3.3 + '@humanfs/node': 0.16.6 + '@humanwhocodes/module-importer': 1.0.1 + '@humanwhocodes/retry': 0.4.3 + '@types/estree': 1.0.8 + '@types/json-schema': 7.0.15 ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.6 @@ -3901,8 +2673,8 @@ snapshots: fast-glob@3.3.3: dependencies: - "@nodelib/fs.stat": 2.0.5 - "@nodelib/fs.walk": 1.2.8 + '@nodelib/fs.stat': 2.0.5 + '@nodelib/fs.walk': 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.8 @@ -4135,6 +2907,8 @@ snapshots: dependencies: ms: 2.1.3 + husky@9.1.7: {} + iconv-lite@0.6.3: dependencies: safer-buffer: 2.1.2 @@ -4313,7 +3087,7 @@ snapshots: jsondiffpatch@0.6.0: dependencies: - "@types/diff-match-patch": 1.0.36 + '@types/diff-match-patch': 1.0.36 chalk: 5.4.1 diff-match-patch: 1.0.5 @@ -4441,8 +3215,8 @@ snapshots: ollama-ai-provider@1.2.0(zod@3.25.67): dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) partial-json: 0.1.7 optionalDependencies: zod: 3.25.67 @@ -4460,8 +3234,8 @@ snapshots: openai@4.104.0(ws@8.18.2)(zod@3.25.67): dependencies: - "@types/node": 18.19.112 - "@types/node-fetch": 2.6.12 + '@types/node': 18.19.112 + '@types/node-fetch': 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -4939,9 +3713,9 @@ snapshots: typescript-eslint@8.35.0(eslint@9.29.0)(typescript@5.8.3): dependencies: - "@typescript-eslint/eslint-plugin": 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/eslint-plugin': 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/parser': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: diff --git a/src/context.ts b/src/context.ts index 49127a5..c72460e 100644 --- a/src/context.ts +++ b/src/context.ts @@ -6,7 +6,7 @@ import { TextContent, ImageContent, } from "@modelcontextprotocol/sdk/types.js"; -import { listResources, readResource } from "./resources.js"; +import { listResources, readResource } from "./mcp/resources.js"; import { getSession, defaultSessionId, diff --git a/src/index.ts b/src/index.ts index 5010632..bbda17e 100644 --- a/src/index.ts +++ b/src/index.ts @@ -3,13 +3,15 @@ dotenv.config(); import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js"; import { z } from "zod"; -import type { Tool, InputType } from "./tools/tool.js"; +import type { Tool } from "./tools/tool.js"; import { Context } from "./context.js"; import type { Config } from "../config.js"; import { TOOLS } from "./tools/index.js"; import { AvailableModelSchema } from "@browserbasehq/stagehand"; -import { PROMPTS, getPrompt } from "./prompts.js"; +import { PROMPTS, getPrompt } from "./mcp/prompts.js"; +import { RESOURCE_TEMPLATES } from "./mcp/resources.js"; + import { ListResourcesRequestSchema, ReadResourceRequestSchema, @@ -99,6 +101,8 @@ export default function ({ config }: { config: z.infer }) { const server = new McpServer({ name: "Browserbase MCP Server", version: "2.0.0", + description: + "Cloud browser automation server powered by Browserbase and Stagehand. Enables LLMs to navigate websites, interact with elements, extract data, and capture screenshots using natural language commands.", capabilities: { resources: { subscribe: true, @@ -107,6 +111,7 @@ export default function ({ config }: { config: z.infer }) { prompts: { listChanged: true, }, + sampling: {}, }, }); @@ -123,6 +128,7 @@ export default function ({ config }: { config: z.infer }) { prompts: { listChanged: true, }, + sampling: {}, }); // Add resource handlers @@ -140,7 +146,7 @@ export default function ({ config }: { config: z.infer }) { server.server.setRequestHandler( ListResourceTemplatesRequestSchema, async () => { - return { resourceTemplates: [] }; + return { resourceTemplates: RESOURCE_TEMPLATES }; }, ); diff --git a/src/prompts.ts b/src/mcp/prompts.ts similarity index 74% rename from src/prompts.ts rename to src/mcp/prompts.ts index ff62aea..83b6cc9 100644 --- a/src/prompts.ts +++ b/src/mcp/prompts.ts @@ -9,8 +9,8 @@ export const PROMPTS = [ { name: "click_search_button", description: "A prompt template for clicking on a search button", - arguments: [], // No arguments required for this specific prompt - }, + arguments: [] // No arguments required for this specific prompt + } ]; /** @@ -21,19 +21,18 @@ export const PROMPTS = [ export function getPrompt(name: string) { if (name === "click_search_button") { return { - description: - "This prompt provides instructions for clicking on a search button", + description: "This prompt provides instructions for clicking on a search button", messages: [ { role: "user", content: { type: "text", - text: "Please click on the search button", - }, - }, - ], + text: "Please click on the search button" + } + } + ] }; } - + throw new Error(`Invalid prompt name: ${name}`); -} +} \ No newline at end of file diff --git a/src/resources.ts b/src/mcp/resources.ts similarity index 96% rename from src/resources.ts rename to src/mcp/resources.ts index f5a6c69..0aaa1a3 100644 --- a/src/resources.ts +++ b/src/mcp/resources.ts @@ -1,5 +1,5 @@ /** - * Resources module for the Stagehand MCP server + * Resources module for the Browserbase MCP server * Contains resources definitions and handlers for resource-related requests * Docs: https://modelcontextprotocol.io/docs/concepts/resources */ diff --git a/src/stagehandStore.ts b/src/stagehandStore.ts index 3429e79..676e383 100644 --- a/src/stagehandStore.ts +++ b/src/stagehandStore.ts @@ -12,14 +12,14 @@ const store = new Map(); */ export const create = async ( config: Config, - params: CreateSessionParams = {} + params: CreateSessionParams = {}, ): Promise => { const id = randomUUID(); - + // Merge config with params const apiKey = params.apiKey || config.browserbaseApiKey; const projectId = params.projectId || config.browserbaseProjectId; - + if (!apiKey || !projectId) { throw new Error("Browserbase API Key and Project ID are required"); } @@ -30,11 +30,15 @@ export const create = async ( env: "BROWSERBASE", apiKey, projectId, - modelName: (params.modelName || config.modelName || "google/gemini-2.0-flash") as AvailableModel, + modelName: (params.modelName || + config.modelName || + "google/gemini-2.0-flash") as AvailableModel, modelClientOptions: { - apiKey: process.env.GEMINI_API_KEY, //TODO: + apiKey: process.env.GEMINI_API_KEY, //TODO: }, - ...(params.browserbaseSessionID && { browserbaseSessionID: params.browserbaseSessionID }), + ...(params.browserbaseSessionID && { + browserbaseSessionID: params.browserbaseSessionID, + }), browserbaseSessionCreateParams: params.browserbaseSessionCreateParams || { projectId, proxies: config.proxies, @@ -81,10 +85,10 @@ export const create = async ( store.set(id, session); process.stderr.write( - `[StagehandStore] Session created: ${id} (BB: ${stagehand.browserbaseSessionID})\n` + `[StagehandStore] Session created: ${id} (BB: ${stagehand.browserbaseSessionID})\n`, ); process.stderr.write( - `[StagehandStore] Live debugger: https://www.browserbase.com/sessions/${stagehand.browserbaseSessionID}\n` + `[StagehandStore] Live debugger: https://www.browserbase.com/sessions/${stagehand.browserbaseSessionID}\n`, ); // Set up disconnect handler @@ -116,12 +120,14 @@ export const list = (): StagehandSession[] => { export const remove = async (id: string): Promise => { const session = store.get(id); if (!session) { - process.stderr.write(`[StagehandStore] Session not found for removal: ${id}\n`); + process.stderr.write( + `[StagehandStore] Session not found for removal: ${id}\n`, + ); return; } process.stderr.write(`[StagehandStore] Removing session: ${id}\n`); - + try { await session.stagehand.close(); process.stderr.write(`[StagehandStore] Session closed: ${id}\n`); @@ -129,7 +135,7 @@ export const remove = async (id: string): Promise => { process.stderr.write( `[StagehandStore] Error closing session ${id}: ${ error instanceof Error ? error.message : String(error) - }\n` + }\n`, ); } @@ -140,8 +146,10 @@ export const remove = async (id: string): Promise => { * Remove all sessions */ export const removeAll = async (): Promise => { - process.stderr.write(`[StagehandStore] Removing all ${store.size} sessions...\n`); - await Promise.all(list().map(s => remove(s.id))); + process.stderr.write( + `[StagehandStore] Removing all ${store.size} sessions...\n`, + ); + await Promise.all(list().map((s) => remove(s.id))); process.stderr.write(`[StagehandStore] All sessions removed\n`); }; @@ -150,4 +158,4 @@ export const removeAll = async (): Promise => { */ export const size = (): number => { return store.size; -}; \ No newline at end of file +}; diff --git a/src/tools/multiSession.ts b/src/tools/multiSession.ts index ad9c293..2f640e2 100644 --- a/src/tools/multiSession.ts +++ b/src/tools/multiSession.ts @@ -1,5 +1,10 @@ import { z } from "zod"; -import { defineTool, type Tool, type ToolResult, type InputType } from "./tool.js"; +import { + defineTool, + type Tool, + type ToolResult, + type InputType, +} from "./tool.js"; import * as stagehandStore from "../stagehandStore.js"; import { CreateSessionParams } from "../types/types.js"; import type { Context } from "../context.js"; @@ -17,14 +22,14 @@ function createMultiSessionAwareTool( options: { namePrefix?: string; nameSuffix?: string; - } = {} + } = {}, ): Tool { const { namePrefix = "", nameSuffix = "_session" } = options; - + // Create new input schema that includes sessionId const originalSchema = originalTool.schema.inputSchema; let newInputSchema: z.ZodSchema; - + if (originalSchema instanceof z.ZodObject) { // If it's a ZodObject, we can spread its shape newInputSchema = z.object({ @@ -35,7 +40,7 @@ function createMultiSessionAwareTool( // For other schema types, create an intersection newInputSchema = z.intersection( z.object({ sessionId: z.string().describe("The session ID to use") }), - originalSchema + originalSchema, ); } @@ -48,20 +53,21 @@ function createMultiSessionAwareTool( }, handle: async (context: Context, params: any): Promise => { const { sessionId, ...originalParams } = params; - + // Get the session const session = stagehandStore.get(sessionId); if (!session) { throw new Error(`Session ${sessionId} not found`); } - + // Create a temporary context that points to the specific session const sessionContext = Object.create(context); - sessionContext.currentSessionId = session.metadata?.bbSessionId || sessionId; + sessionContext.currentSessionId = + session.metadata?.bbSessionId || sessionId; sessionContext.getStagehand = async () => session.stagehand; sessionContext.getActivePage = async () => session.page; sessionContext.getActiveBrowser = async () => session.browser; - + // Call the original tool's handler with the session-specific context return originalTool.handle(sessionContext, originalParams); }, @@ -72,38 +78,60 @@ function createMultiSessionAwareTool( export const createSessionTool = defineTool({ capability: "create_session", schema: { - name: "stagehand_session_create_multi", - description: "Create a new Stagehand browser session. Returns the session ID.", + name: "multi-browserbase_stagehand_session_create", + description: + "Create a new Stagehand browser session with full web automation capabilities. This initializes a fresh browser instance that can navigate, interact with elements, extract data, and take screenshots. Each session is isolated and can be managed independently. Use this when you need to start web automation tasks or when you need multiple parallel browser sessions.", inputSchema: z.object({ - name: z.string().optional().describe("Optional name for the session"), - browserbaseSessionID: z.string().optional().describe("Resume an existing Browserbase session"), - browserbaseSessionCreateParams: z.any().optional().describe("Custom Browserbase session parameters"), + name: z + .string() + .optional() + .describe( + "Optional human-readable name for the session to help track multiple sessions (e.g. 'login-flow', 'data-scraping', 'testing-checkout')", + ), + browserbaseSessionID: z + .string() + .optional() + .describe( + "Resume an existing Browserbase session by providing its session ID. Use this to continue work in a previously created browser session that may have been paused or disconnected.", + ), + browserbaseSessionCreateParams: z + .any() + .optional() + .describe( + "Advanced Browserbase session configuration parameters for customizing browser settings, viewport, user agent, etc. Leave empty for default settings.", + ), }), }, - handle: async (context: Context, { name, browserbaseSessionID, browserbaseSessionCreateParams }): Promise => { + handle: async ( + context: Context, + { name, browserbaseSessionID, browserbaseSessionCreateParams }, + ): Promise => { try { const params: CreateSessionParams = { browserbaseSessionID, browserbaseSessionCreateParams, meta: name ? { name } : undefined, }; - + const session = await stagehandStore.create(context.config, params); - + return { action: async () => ({ content: [ { type: "text", - text: `Created session ${session.id}${name ? ` (${name})` : ''}\nBrowserbase session: ${session.metadata?.bbSessionId}`, + text: `Created session ${session.id}${name ? ` (${name})` : ""}\nBrowserbase session: ${session.metadata?.bbSessionId}`, }, ], }), waitForNetwork: false, }; } catch (error) { - const errorMessage = error instanceof Error ? error.message : String(error); - throw new Error(`Failed to create session: ${errorMessage}`); + const errorMessage = + error instanceof Error ? error.message : String(error); + throw new Error( + `Failed to create browser session: ${errorMessage}. Please check your Browserbase credentials and try again.`, + ); } }, }); @@ -112,13 +140,14 @@ export const createSessionTool = defineTool({ export const listSessionsTool = defineTool({ capability: "list_sessions", schema: { - name: "stagehand_session_list", - description: "List all active Stagehand browser sessions", + name: "browserbase_stagehand_session_list", + description: + "List all currently active Stagehand browser sessions with their details. Use this to see what sessions are available, check their status, and get session IDs for use with other tools. Helpful for managing multiple concurrent browser automation tasks.", inputSchema: z.object({}), }, handle: async (): Promise => { const sessions = stagehandStore.list(); - + if (sessions.length === 0) { return { action: async () => ({ @@ -132,23 +161,26 @@ export const listSessionsTool = defineTool({ waitForNetwork: false, }; } - - const sessionInfo = sessions.map(s => ({ + + const sessionInfo = sessions.map((s) => ({ id: s.id, name: s.metadata?.name, browserbaseSessionId: s.metadata?.bbSessionId, created: new Date(s.created).toISOString(), age: Math.floor((Date.now() - s.created) / 1000), })); - + return { action: async () => ({ content: [ { type: "text", text: `Active sessions (${sessions.length}):\n${sessionInfo - .map(s => `- ${s.id}${s.name ? ` (${s.name})` : ''} - BB: ${s.browserbaseSessionId} - Age: ${s.age}s`) - .join('\n')}`, + .map( + (s) => + `- ${s.id}${s.name ? ` (${s.name})` : ""} - BB: ${s.browserbaseSessionId} - Age: ${s.age}s`, + ) + .join("\n")}`, }, ], }), @@ -161,10 +193,15 @@ export const listSessionsTool = defineTool({ export const closeSessionTool = defineTool({ capability: "close_session", schema: { - name: "stagehand_session_close_multi", - description: "Close a specific Stagehand browser session", + name: "multi-browserbase_stagehand_session_close", + description: + "Close and clean up a specific Stagehand browser session. This will terminate the browser instance, end the Browserbase session, and free up resources. Use this when you're done with a session to avoid leaving sessions running unnecessarily. Important: Once closed, the session ID cannot be reused.", inputSchema: z.object({ - sessionId: z.string().describe("The session ID to close"), + sessionId: z + .string() + .describe( + "The exact session ID to close. You can get session IDs from the 'stagehand_session_list' tool. Make sure this is the correct session as this action cannot be undone.", + ), }), }, handle: async (_context: Context, { sessionId }): Promise => { @@ -172,9 +209,9 @@ export const closeSessionTool = defineTool({ if (!session) { throw new Error(`Session ${sessionId} not found`); } - + await stagehandStore.remove(sessionId); - + return { action: async () => ({ content: [ @@ -190,10 +227,13 @@ export const closeSessionTool = defineTool({ }); // Create multi-session-aware versions of the core tools -export const navigateWithSessionTool = createMultiSessionAwareTool(navigateTool, { - namePrefix: "multi-", - nameSuffix: "_session", -}); +export const navigateWithSessionTool = createMultiSessionAwareTool( + navigateTool, + { + namePrefix: "multi-", + nameSuffix: "_session", + }, +); export const actWithSessionTool = createMultiSessionAwareTool(actTool, { namePrefix: "multi-", @@ -208,4 +248,4 @@ export const extractWithSessionTool = createMultiSessionAwareTool(extractTool, { export const observeWithSessionTool = createMultiSessionAwareTool(observeTool, { namePrefix: "multi-", nameSuffix: "_session", -}); \ No newline at end of file +}); diff --git a/src/tools/screenshot.ts b/src/tools/screenshot.ts index ea7ee9f..4a024a7 100644 --- a/src/tools/screenshot.ts +++ b/src/tools/screenshot.ts @@ -2,7 +2,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; import type { ToolActionResult } from "../context.js"; -import { screenshots } from "../resources.js"; +import { screenshots } from "../mcp/resources.js"; const ScreenshotInputSchema = z.object({ name: z.string().optional().describe("The name of the screenshot"), diff --git a/src/types/types.ts b/src/types/types.ts index b8c8319..78752ae 100644 --- a/src/types/types.ts +++ b/src/types/types.ts @@ -2,8 +2,8 @@ import { Stagehand } from "@browserbasehq/stagehand"; import { Browser, Page } from "playwright-core"; export type StagehandSession = { - id: string; // MCP-side ID - stagehand: Stagehand; // owns the Browserbase session + id: string; // MCP-side ID + stagehand: Stagehand; // owns the Browserbase session page: Page; browser: Browser; created: number; @@ -17,4 +17,4 @@ export type CreateSessionParams = { browserbaseSessionID?: string; browserbaseSessionCreateParams?: any; meta?: Record; -}; \ No newline at end of file +}; From 98f4cb0141c4eea138a8314f883e7b77430d6090 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 26 Jun 2025 16:38:24 -0700 Subject: [PATCH 12/32] prettier-fix --- README.md | 3 +- pnpm-lock.yaml | 3251 ++++++++++++++++++++++++++++++-------------- src/mcp/prompts.ts | 19 +- 3 files changed, 2257 insertions(+), 1016 deletions(-) diff --git a/README.md b/README.md index 8352da1..55ab677 100644 --- a/README.md +++ b/README.md @@ -481,6 +481,7 @@ mcp-server-browserbase/ ### Tools & Types **tools/** - Individual tool implementations with type-safe Zod schemas including: + - Core browser automation tools (navigate, act, extract, observe, screenshot) - Single session management tools (session.ts) - Multi-session management and session-aware tool variants (multiSession.ts) @@ -544,4 +545,4 @@ For more information about the Model Context Protocol, visit: Licensed under the MIT License. -Copyright 2025 Browserbase, Inc. \ No newline at end of file +Copyright 2025 Browserbase, Inc. diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 69bb841..b35f54f 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1,27 +1,26 @@ -lockfileVersion: '9.0' +lockfileVersion: "9.0" settings: autoInstallPeers: true excludeLinksFromLockfile: false importers: - .: dependencies: - '@browserbasehq/stagehand': + "@browserbasehq/stagehand": specifier: ^2.4.0 version: 2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67) - '@modelcontextprotocol/sdk': + "@modelcontextprotocol/sdk": specifier: ^1.13.1 version: 1.13.1 - '@playwright/test': + "@playwright/test": specifier: ^1.49.0 version: 1.53.1 commander: specifier: ^14.0.0 version: 14.0.0 devDependencies: - '@eslint/js': + "@eslint/js": specifier: ^9.29.0 version: 9.29.0 eslint: @@ -50,80 +49,118 @@ importers: version: 8.35.0(eslint@9.29.0)(typescript@5.8.3) packages: - - '@ai-sdk/anthropic@1.2.12': - resolution: {integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==} - engines: {node: '>=18'} + "@ai-sdk/anthropic@1.2.12": + resolution: + { + integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/azure@1.3.23': - resolution: {integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==} - engines: {node: '>=18'} + "@ai-sdk/azure@1.3.23": + resolution: + { + integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/cerebras@0.2.14': - resolution: {integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==} - engines: {node: '>=18'} + "@ai-sdk/cerebras@0.2.14": + resolution: + { + integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/deepseek@0.2.14': - resolution: {integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==} - engines: {node: '>=18'} + "@ai-sdk/deepseek@0.2.14": + resolution: + { + integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/google@1.2.19': - resolution: {integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==} - engines: {node: '>=18'} + "@ai-sdk/google@1.2.19": + resolution: + { + integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/groq@1.2.9': - resolution: {integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==} - engines: {node: '>=18'} + "@ai-sdk/groq@1.2.9": + resolution: + { + integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/mistral@1.2.8': - resolution: {integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==} - engines: {node: '>=18'} + "@ai-sdk/mistral@1.2.8": + resolution: + { + integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/openai-compatible@0.2.14': - resolution: {integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==} - engines: {node: '>=18'} + "@ai-sdk/openai-compatible@0.2.14": + resolution: + { + integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/openai@1.3.22': - resolution: {integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==} - engines: {node: '>=18'} + "@ai-sdk/openai@1.3.22": + resolution: + { + integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/perplexity@1.1.9': - resolution: {integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==} - engines: {node: '>=18'} + "@ai-sdk/perplexity@1.1.9": + resolution: + { + integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/provider-utils@2.2.8': - resolution: {integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==} - engines: {node: '>=18'} + "@ai-sdk/provider-utils@2.2.8": + resolution: + { + integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.23.8 - '@ai-sdk/provider@1.1.3': - resolution: {integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==} - engines: {node: '>=18'} - - '@ai-sdk/react@1.2.12': - resolution: {integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==} - engines: {node: '>=18'} + "@ai-sdk/provider@1.1.3": + resolution: + { + integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==, + } + engines: { node: ">=18" } + + "@ai-sdk/react@1.2.12": + resolution: + { + integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==, + } + engines: { node: ">=18" } peerDependencies: react: ^18 || ^19 || ^19.0.0-rc zod: ^3.23.8 @@ -131,231 +168,381 @@ packages: zod: optional: true - '@ai-sdk/togetherai@0.2.14': - resolution: {integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==} - engines: {node: '>=18'} + "@ai-sdk/togetherai@0.2.14": + resolution: + { + integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@ai-sdk/ui-utils@1.2.11': - resolution: {integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==} - engines: {node: '>=18'} + "@ai-sdk/ui-utils@1.2.11": + resolution: + { + integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.23.8 - '@ai-sdk/xai@1.2.16': - resolution: {integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==} - engines: {node: '>=18'} + "@ai-sdk/xai@1.2.16": + resolution: + { + integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 - '@anthropic-ai/sdk@0.39.0': - resolution: {integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==} - - '@browserbasehq/sdk@2.6.0': - resolution: {integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==} - - '@browserbasehq/stagehand@2.4.0': - resolution: {integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==} + "@anthropic-ai/sdk@0.39.0": + resolution: + { + integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==, + } + + "@browserbasehq/sdk@2.6.0": + resolution: + { + integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==, + } + + "@browserbasehq/stagehand@2.4.0": + resolution: + { + integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==, + } peerDependencies: deepmerge: ^4.3.1 dotenv: ^16.4.5 zod: ^3.23.8 - '@eslint-community/eslint-utils@4.7.0': - resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + "@eslint-community/eslint-utils@4.7.0": + resolution: + { + integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==, + } + engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } peerDependencies: eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 - '@eslint-community/regexpp@4.12.1': - resolution: {integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==} - engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} - - '@eslint/config-array@0.20.1': - resolution: {integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/config-helpers@0.2.3': - resolution: {integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/core@0.14.0': - resolution: {integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/core@0.15.1': - resolution: {integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/eslintrc@3.3.1': - resolution: {integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/js@9.29.0': - resolution: {integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/object-schema@2.1.6': - resolution: {integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/plugin-kit@0.3.3': - resolution: {integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@google/genai@0.8.0': - resolution: {integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==} - engines: {node: '>=18.0.0'} - - '@humanfs/core@0.19.1': - resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==} - engines: {node: '>=18.18.0'} - - '@humanfs/node@0.16.6': - resolution: {integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==} - engines: {node: '>=18.18.0'} - - '@humanwhocodes/module-importer@1.0.1': - resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} - engines: {node: '>=12.22'} - - '@humanwhocodes/retry@0.3.1': - resolution: {integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==} - engines: {node: '>=18.18'} - - '@humanwhocodes/retry@0.4.3': - resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} - engines: {node: '>=18.18'} - - '@modelcontextprotocol/sdk@1.13.1': - resolution: {integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==} - engines: {node: '>=18'} - - '@nodelib/fs.scandir@2.1.5': - resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} - engines: {node: '>= 8'} - - '@nodelib/fs.stat@2.0.5': - resolution: {integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==} - engines: {node: '>= 8'} - - '@nodelib/fs.walk@1.2.8': - resolution: {integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==} - engines: {node: '>= 8'} - - '@opentelemetry/api@1.9.0': - resolution: {integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==} - engines: {node: '>=8.0.0'} - - '@playwright/test@1.53.1': - resolution: {integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==} - engines: {node: '>=18'} + "@eslint-community/regexpp@4.12.1": + resolution: + { + integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==, + } + engines: { node: ^12.0.0 || ^14.0.0 || >=16.0.0 } + + "@eslint/config-array@0.20.1": + resolution: + { + integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/config-helpers@0.2.3": + resolution: + { + integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/core@0.14.0": + resolution: + { + integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/core@0.15.1": + resolution: + { + integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/eslintrc@3.3.1": + resolution: + { + integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/js@9.29.0": + resolution: + { + integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/object-schema@2.1.6": + resolution: + { + integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@eslint/plugin-kit@0.3.3": + resolution: + { + integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@google/genai@0.8.0": + resolution: + { + integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==, + } + engines: { node: ">=18.0.0" } + + "@humanfs/core@0.19.1": + resolution: + { + integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==, + } + engines: { node: ">=18.18.0" } + + "@humanfs/node@0.16.6": + resolution: + { + integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==, + } + engines: { node: ">=18.18.0" } + + "@humanwhocodes/module-importer@1.0.1": + resolution: + { + integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==, + } + engines: { node: ">=12.22" } + + "@humanwhocodes/retry@0.3.1": + resolution: + { + integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==, + } + engines: { node: ">=18.18" } + + "@humanwhocodes/retry@0.4.3": + resolution: + { + integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==, + } + engines: { node: ">=18.18" } + + "@modelcontextprotocol/sdk@1.13.1": + resolution: + { + integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==, + } + engines: { node: ">=18" } + + "@nodelib/fs.scandir@2.1.5": + resolution: + { + integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==, + } + engines: { node: ">= 8" } + + "@nodelib/fs.stat@2.0.5": + resolution: + { + integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==, + } + engines: { node: ">= 8" } + + "@nodelib/fs.walk@1.2.8": + resolution: + { + integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==, + } + engines: { node: ">= 8" } + + "@opentelemetry/api@1.9.0": + resolution: + { + integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==, + } + engines: { node: ">=8.0.0" } + + "@playwright/test@1.53.1": + resolution: + { + integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==, + } + engines: { node: ">=18" } hasBin: true - '@types/diff-match-patch@1.0.36': - resolution: {integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==} - - '@types/estree@1.0.8': - resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==} - - '@types/json-schema@7.0.15': - resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} - - '@types/node-fetch@2.6.12': - resolution: {integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==} - - '@types/node@18.19.112': - resolution: {integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==} - - '@typescript-eslint/eslint-plugin@8.35.0': - resolution: {integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@types/diff-match-patch@1.0.36": + resolution: + { + integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==, + } + + "@types/estree@1.0.8": + resolution: + { + integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==, + } + + "@types/json-schema@7.0.15": + resolution: + { + integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==, + } + + "@types/node-fetch@2.6.12": + resolution: + { + integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==, + } + + "@types/node@18.19.112": + resolution: + { + integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==, + } + + "@typescript-eslint/eslint-plugin@8.35.0": + resolution: + { + integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - '@typescript-eslint/parser': ^8.35.0 + "@typescript-eslint/parser": ^8.35.0 eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' - - '@typescript-eslint/parser@8.35.0': - resolution: {integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/parser@8.35.0": + resolution: + { + integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' - - '@typescript-eslint/project-service@8.35.0': - resolution: {integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/project-service@8.35.0": + resolution: + { + integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - typescript: '>=4.8.4 <5.9.0' - - '@typescript-eslint/scope-manager@8.35.0': - resolution: {integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@typescript-eslint/tsconfig-utils@8.35.0': - resolution: {integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/scope-manager@8.35.0": + resolution: + { + integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@typescript-eslint/tsconfig-utils@8.35.0": + resolution: + { + integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - typescript: '>=4.8.4 <5.9.0' - - '@typescript-eslint/type-utils@8.35.0': - resolution: {integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/type-utils@8.35.0": + resolution: + { + integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' - - '@typescript-eslint/types@8.35.0': - resolution: {integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@typescript-eslint/typescript-estree@8.35.0': - resolution: {integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/types@8.35.0": + resolution: + { + integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + + "@typescript-eslint/typescript-estree@8.35.0": + resolution: + { + integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: - typescript: '>=4.8.4 <5.9.0' - - '@typescript-eslint/utils@8.35.0': - resolution: {integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + typescript: ">=4.8.4 <5.9.0" + + "@typescript-eslint/utils@8.35.0": + resolution: + { + integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" - '@typescript-eslint/visitor-keys@8.35.0': - resolution: {integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + "@typescript-eslint/visitor-keys@8.35.0": + resolution: + { + integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } abort-controller@3.0.0: - resolution: {integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==} - engines: {node: '>=6.5'} + resolution: + { + integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==, + } + engines: { node: ">=6.5" } accepts@2.0.0: - resolution: {integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==, + } + engines: { node: ">= 0.6" } acorn-jsx@5.3.2: - resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} + resolution: + { + integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==, + } peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 acorn@8.15.0: - resolution: {integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==} - engines: {node: '>=0.4.0'} + resolution: + { + integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==, + } + engines: { node: ">=0.4.0" } hasBin: true agent-base@7.1.3: - resolution: {integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==} - engines: {node: '>= 14'} + resolution: + { + integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==, + } + engines: { node: ">= 14" } agentkeepalive@4.6.0: - resolution: {integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==} - engines: {node: '>= 8.0.0'} + resolution: + { + integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==, + } + engines: { node: ">= 8.0.0" } ai@4.3.16: - resolution: {integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==, + } + engines: { node: ">=18" } peerDependencies: react: ^18 || ^19 || ^19.0.0-rc zod: ^3.23.8 @@ -364,840 +551,1494 @@ packages: optional: true ajv@6.12.6: - resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} + resolution: + { + integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==, + } ansi-styles@4.3.0: - resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==, + } + engines: { node: ">=8" } argparse@2.0.1: - resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} + resolution: + { + integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==, + } array-buffer-byte-length@1.0.2: - resolution: {integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==, + } + engines: { node: ">= 0.4" } array-includes@3.1.9: - resolution: {integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==, + } + engines: { node: ">= 0.4" } array.prototype.findlast@1.2.5: - resolution: {integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==, + } + engines: { node: ">= 0.4" } array.prototype.flat@1.3.3: - resolution: {integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==, + } + engines: { node: ">= 0.4" } array.prototype.flatmap@1.3.3: - resolution: {integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==, + } + engines: { node: ">= 0.4" } array.prototype.tosorted@1.1.4: - resolution: {integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==, + } + engines: { node: ">= 0.4" } arraybuffer.prototype.slice@1.0.4: - resolution: {integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==, + } + engines: { node: ">= 0.4" } async-function@1.0.0: - resolution: {integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==, + } + engines: { node: ">= 0.4" } asynckit@0.4.0: - resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} + resolution: + { + integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==, + } atomic-sleep@1.0.0: - resolution: {integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==} - engines: {node: '>=8.0.0'} + resolution: + { + integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==, + } + engines: { node: ">=8.0.0" } available-typed-arrays@1.0.7: - resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==, + } + engines: { node: ">= 0.4" } balanced-match@1.0.2: - resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} + resolution: + { + integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==, + } base64-js@1.5.1: - resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==} + resolution: + { + integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==, + } bignumber.js@9.3.0: - resolution: {integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==} + resolution: + { + integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==, + } body-parser@2.2.0: - resolution: {integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==, + } + engines: { node: ">=18" } brace-expansion@1.1.12: - resolution: {integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==} + resolution: + { + integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==, + } brace-expansion@2.0.2: - resolution: {integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==} + resolution: + { + integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==, + } braces@3.0.3: - resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==, + } + engines: { node: ">=8" } buffer-equal-constant-time@1.0.1: - resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} + resolution: + { + integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==, + } bytes@3.1.2: - resolution: {integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==, + } + engines: { node: ">= 0.8" } call-bind-apply-helpers@1.0.2: - resolution: {integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==, + } + engines: { node: ">= 0.4" } call-bind@1.0.8: - resolution: {integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==, + } + engines: { node: ">= 0.4" } call-bound@1.0.4: - resolution: {integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==, + } + engines: { node: ">= 0.4" } callsites@3.1.0: - resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==, + } + engines: { node: ">=6" } chalk@4.1.2: - resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==, + } + engines: { node: ">=10" } chalk@5.4.1: - resolution: {integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==} - engines: {node: ^12.17.0 || ^14.13 || >=16.0.0} + resolution: + { + integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==, + } + engines: { node: ^12.17.0 || ^14.13 || >=16.0.0 } color-convert@2.0.1: - resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==} - engines: {node: '>=7.0.0'} + resolution: + { + integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==, + } + engines: { node: ">=7.0.0" } color-name@1.1.4: - resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} + resolution: + { + integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==, + } colorette@2.0.20: - resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} + resolution: + { + integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==, + } combined-stream@1.0.8: - resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==, + } + engines: { node: ">= 0.8" } commander@14.0.0: - resolution: {integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==} - engines: {node: '>=20'} + resolution: + { + integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==, + } + engines: { node: ">=20" } concat-map@0.0.1: - resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} + resolution: + { + integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==, + } content-disposition@1.0.0: - resolution: {integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==, + } + engines: { node: ">= 0.6" } content-type@1.0.5: - resolution: {integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==, + } + engines: { node: ">= 0.6" } cookie-signature@1.2.2: - resolution: {integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==} - engines: {node: '>=6.6.0'} + resolution: + { + integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==, + } + engines: { node: ">=6.6.0" } cookie@0.7.2: - resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==, + } + engines: { node: ">= 0.6" } cors@2.8.5: - resolution: {integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==} - engines: {node: '>= 0.10'} + resolution: + { + integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==, + } + engines: { node: ">= 0.10" } cross-spawn@7.0.6: - resolution: {integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==, + } + engines: { node: ">= 8" } data-view-buffer@1.0.2: - resolution: {integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==, + } + engines: { node: ">= 0.4" } data-view-byte-length@1.0.2: - resolution: {integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==, + } + engines: { node: ">= 0.4" } data-view-byte-offset@1.0.1: - resolution: {integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==, + } + engines: { node: ">= 0.4" } dateformat@4.6.3: - resolution: {integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==} + resolution: + { + integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==, + } debug@4.4.1: - resolution: {integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==} - engines: {node: '>=6.0'} + resolution: + { + integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==, + } + engines: { node: ">=6.0" } peerDependencies: - supports-color: '*' + supports-color: "*" peerDependenciesMeta: supports-color: optional: true deep-is@0.1.4: - resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} + resolution: + { + integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==, + } deepmerge@4.3.1: - resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==, + } + engines: { node: ">=0.10.0" } define-data-property@1.1.4: - resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==, + } + engines: { node: ">= 0.4" } define-properties@1.2.1: - resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==, + } + engines: { node: ">= 0.4" } delayed-stream@1.0.0: - resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} - engines: {node: '>=0.4.0'} + resolution: + { + integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==, + } + engines: { node: ">=0.4.0" } depd@2.0.0: - resolution: {integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==, + } + engines: { node: ">= 0.8" } dequal@2.0.3: - resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==, + } + engines: { node: ">=6" } devtools-protocol@0.0.1464554: - resolution: {integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==} + resolution: + { + integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==, + } diff-match-patch@1.0.5: - resolution: {integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==} + resolution: + { + integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==, + } doctrine@2.1.0: - resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==, + } + engines: { node: ">=0.10.0" } dotenv@16.5.0: - resolution: {integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==} - engines: {node: '>=12'} + resolution: + { + integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==, + } + engines: { node: ">=12" } dunder-proto@1.0.1: - resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==, + } + engines: { node: ">= 0.4" } ecdsa-sig-formatter@1.0.11: - resolution: {integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==} + resolution: + { + integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==, + } ee-first@1.1.1: - resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} + resolution: + { + integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==, + } encodeurl@2.0.0: - resolution: {integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==, + } + engines: { node: ">= 0.8" } end-of-stream@1.4.5: - resolution: {integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==} + resolution: + { + integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==, + } es-abstract@1.24.0: - resolution: {integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==, + } + engines: { node: ">= 0.4" } es-define-property@1.0.1: - resolution: {integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==, + } + engines: { node: ">= 0.4" } es-errors@1.3.0: - resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==, + } + engines: { node: ">= 0.4" } es-iterator-helpers@1.2.1: - resolution: {integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==, + } + engines: { node: ">= 0.4" } es-object-atoms@1.1.1: - resolution: {integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==, + } + engines: { node: ">= 0.4" } es-set-tostringtag@2.1.0: - resolution: {integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==, + } + engines: { node: ">= 0.4" } es-shim-unscopables@1.1.0: - resolution: {integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==, + } + engines: { node: ">= 0.4" } es-to-primitive@1.3.0: - resolution: {integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==, + } + engines: { node: ">= 0.4" } escape-html@1.0.3: - resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} + resolution: + { + integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==, + } escape-string-regexp@4.0.0: - resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==, + } + engines: { node: ">=10" } eslint-plugin-react@7.37.5: - resolution: {integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==, + } + engines: { node: ">=4" } peerDependencies: eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 eslint-scope@8.4.0: - resolution: {integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } eslint-visitor-keys@3.4.3: - resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + resolution: + { + integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==, + } + engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } eslint-visitor-keys@4.2.1: - resolution: {integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } eslint@9.29.0: - resolution: {integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } hasBin: true peerDependencies: - jiti: '*' + jiti: "*" peerDependenciesMeta: jiti: optional: true espree@10.4.0: - resolution: {integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } esquery@1.6.0: - resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} - engines: {node: '>=0.10'} + resolution: + { + integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==, + } + engines: { node: ">=0.10" } esrecurse@4.3.0: - resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==, + } + engines: { node: ">=4.0" } estraverse@5.3.0: - resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==, + } + engines: { node: ">=4.0" } esutils@2.0.3: - resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==, + } + engines: { node: ">=0.10.0" } etag@1.8.1: - resolution: {integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==, + } + engines: { node: ">= 0.6" } event-target-shim@5.0.1: - resolution: {integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==, + } + engines: { node: ">=6" } eventsource-parser@3.0.3: - resolution: {integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==} - engines: {node: '>=20.0.0'} + resolution: + { + integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==, + } + engines: { node: ">=20.0.0" } eventsource@3.0.7: - resolution: {integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==} - engines: {node: '>=18.0.0'} + resolution: + { + integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==, + } + engines: { node: ">=18.0.0" } express-rate-limit@7.5.1: - resolution: {integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==} - engines: {node: '>= 16'} + resolution: + { + integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==, + } + engines: { node: ">= 16" } peerDependencies: - express: '>= 4.11' + express: ">= 4.11" express@5.1.0: - resolution: {integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==} - engines: {node: '>= 18'} + resolution: + { + integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==, + } + engines: { node: ">= 18" } extend@3.0.2: - resolution: {integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==} + resolution: + { + integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==, + } fast-copy@3.0.2: - resolution: {integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==} + resolution: + { + integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==, + } fast-deep-equal@3.1.3: - resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} + resolution: + { + integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==, + } fast-glob@3.3.3: - resolution: {integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==} - engines: {node: '>=8.6.0'} + resolution: + { + integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==, + } + engines: { node: ">=8.6.0" } fast-json-stable-stringify@2.1.0: - resolution: {integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==} + resolution: + { + integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==, + } fast-levenshtein@2.0.6: - resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} + resolution: + { + integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==, + } fast-redact@3.5.0: - resolution: {integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==, + } + engines: { node: ">=6" } fast-safe-stringify@2.1.1: - resolution: {integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==} + resolution: + { + integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==, + } fastq@1.19.1: - resolution: {integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==} + resolution: + { + integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==, + } fetch-cookie@3.1.0: - resolution: {integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==} + resolution: + { + integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==, + } file-entry-cache@8.0.0: - resolution: {integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==} - engines: {node: '>=16.0.0'} + resolution: + { + integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==, + } + engines: { node: ">=16.0.0" } fill-range@7.1.1: - resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==, + } + engines: { node: ">=8" } finalhandler@2.1.0: - resolution: {integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==, + } + engines: { node: ">= 0.8" } find-up@5.0.0: - resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==, + } + engines: { node: ">=10" } flat-cache@4.0.1: - resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} - engines: {node: '>=16'} + resolution: + { + integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==, + } + engines: { node: ">=16" } flatted@3.3.3: - resolution: {integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==} + resolution: + { + integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==, + } for-each@0.3.5: - resolution: {integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==, + } + engines: { node: ">= 0.4" } form-data-encoder@1.7.2: - resolution: {integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==} + resolution: + { + integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==, + } form-data@4.0.3: - resolution: {integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==} - engines: {node: '>= 6'} + resolution: + { + integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==, + } + engines: { node: ">= 6" } formdata-node@4.4.1: - resolution: {integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==} - engines: {node: '>= 12.20'} + resolution: + { + integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==, + } + engines: { node: ">= 12.20" } forwarded@0.2.0: - resolution: {integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==, + } + engines: { node: ">= 0.6" } fresh@2.0.0: - resolution: {integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==, + } + engines: { node: ">= 0.8" } fs.realpath@1.0.0: - resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==} + resolution: + { + integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==, + } fsevents@2.3.2: - resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==} - engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} + resolution: + { + integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==, + } + engines: { node: ^8.16.0 || ^10.6.0 || >=11.0.0 } os: [darwin] function-bind@1.1.2: - resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} + resolution: + { + integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==, + } function.prototype.name@1.1.8: - resolution: {integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==, + } + engines: { node: ">= 0.4" } functions-have-names@1.2.3: - resolution: {integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==} + resolution: + { + integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==, + } gaxios@6.7.1: - resolution: {integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==, + } + engines: { node: ">=14" } gcp-metadata@6.1.1: - resolution: {integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==, + } + engines: { node: ">=14" } get-intrinsic@1.3.0: - resolution: {integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==, + } + engines: { node: ">= 0.4" } get-proto@1.0.1: - resolution: {integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==, + } + engines: { node: ">= 0.4" } get-symbol-description@1.1.0: - resolution: {integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==, + } + engines: { node: ">= 0.4" } glob-parent@5.1.2: - resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} - engines: {node: '>= 6'} + resolution: + { + integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==, + } + engines: { node: ">= 6" } glob-parent@6.0.2: - resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} - engines: {node: '>=10.13.0'} + resolution: + { + integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==, + } + engines: { node: ">=10.13.0" } glob@7.2.3: - resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} + resolution: + { + integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==, + } deprecated: Glob versions prior to v9 are no longer supported globals@14.0.0: - resolution: {integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==, + } + engines: { node: ">=18" } globals@16.2.0: - resolution: {integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==, + } + engines: { node: ">=18" } globalthis@1.0.4: - resolution: {integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==, + } + engines: { node: ">= 0.4" } google-auth-library@9.15.1: - resolution: {integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==, + } + engines: { node: ">=14" } google-logging-utils@0.0.2: - resolution: {integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==, + } + engines: { node: ">=14" } gopd@1.2.0: - resolution: {integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==, + } + engines: { node: ">= 0.4" } graphemer@1.4.0: - resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} + resolution: + { + integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==, + } gtoken@7.1.0: - resolution: {integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==} - engines: {node: '>=14.0.0'} + resolution: + { + integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==, + } + engines: { node: ">=14.0.0" } has-bigints@1.1.0: - resolution: {integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==, + } + engines: { node: ">= 0.4" } has-flag@4.0.0: - resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==, + } + engines: { node: ">=8" } has-property-descriptors@1.0.2: - resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} + resolution: + { + integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==, + } has-proto@1.2.0: - resolution: {integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==, + } + engines: { node: ">= 0.4" } has-symbols@1.1.0: - resolution: {integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==, + } + engines: { node: ">= 0.4" } has-tostringtag@1.0.2: - resolution: {integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==, + } + engines: { node: ">= 0.4" } hasown@2.0.2: - resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==, + } + engines: { node: ">= 0.4" } help-me@5.0.0: - resolution: {integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==} + resolution: + { + integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==, + } http-errors@2.0.0: - resolution: {integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==, + } + engines: { node: ">= 0.8" } https-proxy-agent@7.0.6: - resolution: {integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==} - engines: {node: '>= 14'} + resolution: + { + integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==, + } + engines: { node: ">= 14" } humanize-ms@1.2.1: - resolution: {integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==} + resolution: + { + integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==, + } husky@9.1.7: - resolution: {integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==, + } + engines: { node: ">=18" } hasBin: true iconv-lite@0.6.3: - resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==, + } + engines: { node: ">=0.10.0" } ignore@5.3.2: - resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} - engines: {node: '>= 4'} + resolution: + { + integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==, + } + engines: { node: ">= 4" } ignore@7.0.5: - resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==} - engines: {node: '>= 4'} + resolution: + { + integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==, + } + engines: { node: ">= 4" } import-fresh@3.3.1: - resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==, + } + engines: { node: ">=6" } imurmurhash@0.1.4: - resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} - engines: {node: '>=0.8.19'} + resolution: + { + integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==, + } + engines: { node: ">=0.8.19" } inflight@1.0.6: - resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} + resolution: + { + integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==, + } deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. inherits@2.0.4: - resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} + resolution: + { + integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==, + } internal-slot@1.1.0: - resolution: {integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==, + } + engines: { node: ">= 0.4" } interpret@1.4.0: - resolution: {integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==} - engines: {node: '>= 0.10'} + resolution: + { + integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==, + } + engines: { node: ">= 0.10" } ipaddr.js@1.9.1: - resolution: {integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==} - engines: {node: '>= 0.10'} + resolution: + { + integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==, + } + engines: { node: ">= 0.10" } is-array-buffer@3.0.5: - resolution: {integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==, + } + engines: { node: ">= 0.4" } is-async-function@2.1.1: - resolution: {integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==, + } + engines: { node: ">= 0.4" } is-bigint@1.1.0: - resolution: {integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==, + } + engines: { node: ">= 0.4" } is-boolean-object@1.2.2: - resolution: {integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==, + } + engines: { node: ">= 0.4" } is-callable@1.2.7: - resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==, + } + engines: { node: ">= 0.4" } is-core-module@2.16.1: - resolution: {integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==, + } + engines: { node: ">= 0.4" } is-data-view@1.0.2: - resolution: {integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==, + } + engines: { node: ">= 0.4" } is-date-object@1.1.0: - resolution: {integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==, + } + engines: { node: ">= 0.4" } is-extglob@2.1.1: - resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==, + } + engines: { node: ">=0.10.0" } is-finalizationregistry@1.1.1: - resolution: {integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==, + } + engines: { node: ">= 0.4" } is-generator-function@1.1.0: - resolution: {integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==, + } + engines: { node: ">= 0.4" } is-glob@4.0.3: - resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==, + } + engines: { node: ">=0.10.0" } is-map@2.0.3: - resolution: {integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==, + } + engines: { node: ">= 0.4" } is-negative-zero@2.0.3: - resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==, + } + engines: { node: ">= 0.4" } is-number-object@1.1.1: - resolution: {integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==, + } + engines: { node: ">= 0.4" } is-number@7.0.0: - resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} - engines: {node: '>=0.12.0'} + resolution: + { + integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==, + } + engines: { node: ">=0.12.0" } is-promise@4.0.0: - resolution: {integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==} + resolution: + { + integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==, + } is-regex@1.2.1: - resolution: {integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==, + } + engines: { node: ">= 0.4" } is-set@2.0.3: - resolution: {integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==, + } + engines: { node: ">= 0.4" } is-shared-array-buffer@1.0.4: - resolution: {integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==, + } + engines: { node: ">= 0.4" } is-stream@2.0.1: - resolution: {integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==, + } + engines: { node: ">=8" } is-string@1.1.1: - resolution: {integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==, + } + engines: { node: ">= 0.4" } is-symbol@1.1.1: - resolution: {integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==, + } + engines: { node: ">= 0.4" } is-typed-array@1.1.15: - resolution: {integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==, + } + engines: { node: ">= 0.4" } is-weakmap@2.0.2: - resolution: {integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==, + } + engines: { node: ">= 0.4" } is-weakref@1.1.1: - resolution: {integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==, + } + engines: { node: ">= 0.4" } is-weakset@2.0.4: - resolution: {integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==, + } + engines: { node: ">= 0.4" } isarray@2.0.5: - resolution: {integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==} + resolution: + { + integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==, + } isexe@2.0.0: - resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} + resolution: + { + integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==, + } iterator.prototype@1.1.5: - resolution: {integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==, + } + engines: { node: ">= 0.4" } joycon@3.1.1: - resolution: {integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==, + } + engines: { node: ">=10" } js-tokens@4.0.0: - resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} + resolution: + { + integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==, + } js-yaml@4.1.0: - resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} + resolution: + { + integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==, + } hasBin: true json-bigint@1.0.0: - resolution: {integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==} + resolution: + { + integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==, + } json-buffer@3.0.1: - resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==} + resolution: + { + integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==, + } json-schema-traverse@0.4.1: - resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==} + resolution: + { + integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==, + } json-schema@0.4.0: - resolution: {integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==} + resolution: + { + integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==, + } json-stable-stringify-without-jsonify@1.0.1: - resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} + resolution: + { + integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==, + } jsondiffpatch@0.6.0: - resolution: {integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==} - engines: {node: ^18.0.0 || >=20.0.0} + resolution: + { + integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==, + } + engines: { node: ^18.0.0 || >=20.0.0 } hasBin: true jsx-ast-utils@3.3.5: - resolution: {integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==} - engines: {node: '>=4.0'} + resolution: + { + integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==, + } + engines: { node: ">=4.0" } jwa@2.0.1: - resolution: {integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==} + resolution: + { + integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==, + } jws@4.0.0: - resolution: {integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==} + resolution: + { + integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==, + } keyv@4.5.4: - resolution: {integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==} + resolution: + { + integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==, + } levn@0.4.1: - resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==, + } + engines: { node: ">= 0.8.0" } locate-path@6.0.0: - resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==, + } + engines: { node: ">=10" } lodash.merge@4.6.2: - resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} + resolution: + { + integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==, + } loose-envify@1.4.0: - resolution: {integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==} + resolution: + { + integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==, + } hasBin: true math-intrinsics@1.1.0: - resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==, + } + engines: { node: ">= 0.4" } media-typer@1.1.0: - resolution: {integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==, + } + engines: { node: ">= 0.8" } merge-descriptors@2.0.0: - resolution: {integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==, + } + engines: { node: ">=18" } merge2@1.4.1: - resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==, + } + engines: { node: ">= 8" } micromatch@4.0.8: - resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} - engines: {node: '>=8.6'} + resolution: + { + integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==, + } + engines: { node: ">=8.6" } mime-db@1.52.0: - resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==, + } + engines: { node: ">= 0.6" } mime-db@1.54.0: - resolution: {integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==, + } + engines: { node: ">= 0.6" } mime-types@2.1.35: - resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==, + } + engines: { node: ">= 0.6" } mime-types@3.0.1: - resolution: {integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==, + } + engines: { node: ">= 0.6" } minimatch@3.1.2: - resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} + resolution: + { + integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==, + } minimatch@9.0.5: - resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} - engines: {node: '>=16 || 14 >=14.17'} + resolution: + { + integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==, + } + engines: { node: ">=16 || 14 >=14.17" } minimist@1.2.8: - resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} + resolution: + { + integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==, + } ms@2.1.3: - resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} + resolution: + { + integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, + } nanoid@3.3.11: - resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==} - engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} + resolution: + { + integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==, + } + engines: { node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1 } hasBin: true natural-compare@1.4.0: - resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} + resolution: + { + integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==, + } negotiator@1.0.0: - resolution: {integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==, + } + engines: { node: ">= 0.6" } node-domexception@1.0.0: - resolution: {integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==} - engines: {node: '>=10.5.0'} + resolution: + { + integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==, + } + engines: { node: ">=10.5.0" } node-fetch@2.7.0: - resolution: {integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==} - engines: {node: 4.x || >=6.0.0} + resolution: + { + integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==, + } + engines: { node: 4.x || >=6.0.0 } peerDependencies: encoding: ^0.1.0 peerDependenciesMeta: @@ -1205,36 +2046,60 @@ packages: optional: true object-assign@4.1.1: - resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==, + } + engines: { node: ">=0.10.0" } object-inspect@1.13.4: - resolution: {integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==, + } + engines: { node: ">= 0.4" } object-keys@1.1.1: - resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==, + } + engines: { node: ">= 0.4" } object.assign@4.1.7: - resolution: {integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==, + } + engines: { node: ">= 0.4" } object.entries@1.1.9: - resolution: {integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==, + } + engines: { node: ">= 0.4" } object.fromentries@2.0.8: - resolution: {integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==, + } + engines: { node: ">= 0.4" } object.values@1.2.1: - resolution: {integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==, + } + engines: { node: ">= 0.4" } ollama-ai-provider@1.2.0: - resolution: {integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==, + } + engines: { node: ">=18" } peerDependencies: zod: ^3.0.0 peerDependenciesMeta: @@ -1242,18 +2107,30 @@ packages: optional: true on-exit-leak-free@2.1.2: - resolution: {integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==} - engines: {node: '>=14.0.0'} + resolution: + { + integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==, + } + engines: { node: ">=14.0.0" } on-finished@2.4.1: - resolution: {integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==, + } + engines: { node: ">= 0.8" } once@1.4.0: - resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==} + resolution: + { + integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==, + } openai@4.104.0: - resolution: {integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==} + resolution: + { + integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==, + } hasBin: true peerDependencies: ws: ^8.18.0 @@ -1265,469 +2142,823 @@ packages: optional: true optionator@0.9.4: - resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==, + } + engines: { node: ">= 0.8.0" } own-keys@1.0.1: - resolution: {integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==, + } + engines: { node: ">= 0.4" } p-limit@3.1.0: - resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==, + } + engines: { node: ">=10" } p-locate@5.0.0: - resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==, + } + engines: { node: ">=10" } parent-module@1.0.1: - resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==, + } + engines: { node: ">=6" } parseurl@1.3.3: - resolution: {integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==, + } + engines: { node: ">= 0.8" } partial-json@0.1.7: - resolution: {integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==} + resolution: + { + integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==, + } path-exists@4.0.0: - resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==, + } + engines: { node: ">=8" } path-is-absolute@1.0.1: - resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==, + } + engines: { node: ">=0.10.0" } path-key@3.1.1: - resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==, + } + engines: { node: ">=8" } path-parse@1.0.7: - resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} + resolution: + { + integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==, + } path-to-regexp@8.2.0: - resolution: {integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==} - engines: {node: '>=16'} + resolution: + { + integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==, + } + engines: { node: ">=16" } picomatch@2.3.1: - resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} - engines: {node: '>=8.6'} + resolution: + { + integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==, + } + engines: { node: ">=8.6" } pino-abstract-transport@2.0.0: - resolution: {integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==} + resolution: + { + integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==, + } pino-pretty@13.0.0: - resolution: {integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==} + resolution: + { + integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==, + } hasBin: true pino-std-serializers@7.0.0: - resolution: {integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==} + resolution: + { + integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==, + } pino@9.7.0: - resolution: {integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==} + resolution: + { + integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==, + } hasBin: true pkce-challenge@5.0.0: - resolution: {integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==} - engines: {node: '>=16.20.0'} + resolution: + { + integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==, + } + engines: { node: ">=16.20.0" } playwright-core@1.53.1: - resolution: {integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==, + } + engines: { node: ">=18" } hasBin: true playwright@1.53.1: - resolution: {integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==, + } + engines: { node: ">=18" } hasBin: true possible-typed-array-names@1.1.0: - resolution: {integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==, + } + engines: { node: ">= 0.4" } prelude-ls@1.2.1: - resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==, + } + engines: { node: ">= 0.8.0" } prettier@3.6.1: - resolution: {integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==} - engines: {node: '>=14'} + resolution: + { + integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==, + } + engines: { node: ">=14" } hasBin: true process-warning@5.0.0: - resolution: {integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==} + resolution: + { + integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==, + } prop-types@15.8.1: - resolution: {integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==} + resolution: + { + integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==, + } proxy-addr@2.0.7: - resolution: {integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==} - engines: {node: '>= 0.10'} + resolution: + { + integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==, + } + engines: { node: ">= 0.10" } pump@3.0.3: - resolution: {integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==} + resolution: + { + integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==, + } punycode@2.3.1: - resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==, + } + engines: { node: ">=6" } qs@6.14.0: - resolution: {integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==} - engines: {node: '>=0.6'} + resolution: + { + integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==, + } + engines: { node: ">=0.6" } queue-microtask@1.2.3: - resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} + resolution: + { + integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==, + } quick-format-unescaped@4.0.4: - resolution: {integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==} + resolution: + { + integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==, + } range-parser@1.2.1: - resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==, + } + engines: { node: ">= 0.6" } raw-body@3.0.0: - resolution: {integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==, + } + engines: { node: ">= 0.8" } react-is@16.13.1: - resolution: {integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==} + resolution: + { + integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==, + } react@19.1.0: - resolution: {integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==, + } + engines: { node: ">=0.10.0" } real-require@0.2.0: - resolution: {integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==} - engines: {node: '>= 12.13.0'} + resolution: + { + integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==, + } + engines: { node: ">= 12.13.0" } rechoir@0.6.2: - resolution: {integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==} - engines: {node: '>= 0.10'} + resolution: + { + integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==, + } + engines: { node: ">= 0.10" } reflect.getprototypeof@1.0.10: - resolution: {integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==, + } + engines: { node: ">= 0.4" } regexp.prototype.flags@1.5.4: - resolution: {integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==, + } + engines: { node: ">= 0.4" } resolve-from@4.0.0: - resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==, + } + engines: { node: ">=4" } resolve@1.22.10: - resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==, + } + engines: { node: ">= 0.4" } hasBin: true resolve@2.0.0-next.5: - resolution: {integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==} + resolution: + { + integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==, + } hasBin: true reusify@1.1.0: - resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} - engines: {iojs: '>=1.0.0', node: '>=0.10.0'} + resolution: + { + integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==, + } + engines: { iojs: ">=1.0.0", node: ">=0.10.0" } router@2.2.0: - resolution: {integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==} - engines: {node: '>= 18'} + resolution: + { + integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==, + } + engines: { node: ">= 18" } run-parallel@1.2.0: - resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} + resolution: + { + integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==, + } safe-array-concat@1.1.3: - resolution: {integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==} - engines: {node: '>=0.4'} + resolution: + { + integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==, + } + engines: { node: ">=0.4" } safe-buffer@5.2.1: - resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} + resolution: + { + integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==, + } safe-push-apply@1.0.0: - resolution: {integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==, + } + engines: { node: ">= 0.4" } safe-regex-test@1.1.0: - resolution: {integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==, + } + engines: { node: ">= 0.4" } safe-stable-stringify@2.5.0: - resolution: {integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==, + } + engines: { node: ">=10" } safer-buffer@2.1.2: - resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} + resolution: + { + integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==, + } secure-json-parse@2.7.0: - resolution: {integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==} + resolution: + { + integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==, + } semver@6.3.1: - resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} + resolution: + { + integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==, + } hasBin: true semver@7.7.2: - resolution: {integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==, + } + engines: { node: ">=10" } hasBin: true send@1.2.0: - resolution: {integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==} - engines: {node: '>= 18'} + resolution: + { + integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==, + } + engines: { node: ">= 18" } serve-static@2.2.0: - resolution: {integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==} - engines: {node: '>= 18'} + resolution: + { + integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==, + } + engines: { node: ">= 18" } set-cookie-parser@2.7.1: - resolution: {integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==} + resolution: + { + integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==, + } set-function-length@1.2.2: - resolution: {integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==, + } + engines: { node: ">= 0.4" } set-function-name@2.0.2: - resolution: {integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==, + } + engines: { node: ">= 0.4" } set-proto@1.0.0: - resolution: {integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==, + } + engines: { node: ">= 0.4" } setprototypeof@1.2.0: - resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} + resolution: + { + integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==, + } shebang-command@2.0.0: - resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==, + } + engines: { node: ">=8" } shebang-regex@3.0.0: - resolution: {integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==, + } + engines: { node: ">=8" } shelljs@0.8.5: - resolution: {integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==} - engines: {node: '>=4'} + resolution: + { + integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==, + } + engines: { node: ">=4" } hasBin: true shx@0.3.4: - resolution: {integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==} - engines: {node: '>=6'} + resolution: + { + integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==, + } + engines: { node: ">=6" } hasBin: true side-channel-list@1.0.0: - resolution: {integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==, + } + engines: { node: ">= 0.4" } side-channel-map@1.0.1: - resolution: {integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==, + } + engines: { node: ">= 0.4" } side-channel-weakmap@1.0.2: - resolution: {integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==, + } + engines: { node: ">= 0.4" } side-channel@1.1.0: - resolution: {integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==, + } + engines: { node: ">= 0.4" } sonic-boom@4.2.0: - resolution: {integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==} + resolution: + { + integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==, + } split2@4.2.0: - resolution: {integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==} - engines: {node: '>= 10.x'} + resolution: + { + integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==, + } + engines: { node: ">= 10.x" } statuses@2.0.1: - resolution: {integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==, + } + engines: { node: ">= 0.8" } statuses@2.0.2: - resolution: {integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==, + } + engines: { node: ">= 0.8" } stop-iteration-iterator@1.1.0: - resolution: {integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==, + } + engines: { node: ">= 0.4" } string.prototype.matchall@4.0.12: - resolution: {integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==, + } + engines: { node: ">= 0.4" } string.prototype.repeat@1.0.0: - resolution: {integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==} + resolution: + { + integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==, + } string.prototype.trim@1.2.10: - resolution: {integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==, + } + engines: { node: ">= 0.4" } string.prototype.trimend@1.0.9: - resolution: {integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==, + } + engines: { node: ">= 0.4" } string.prototype.trimstart@1.0.8: - resolution: {integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==, + } + engines: { node: ">= 0.4" } strip-json-comments@3.1.1: - resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==, + } + engines: { node: ">=8" } supports-color@7.2.0: - resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} - engines: {node: '>=8'} + resolution: + { + integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==, + } + engines: { node: ">=8" } supports-preserve-symlinks-flag@1.0.0: - resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==, + } + engines: { node: ">= 0.4" } swr@2.3.3: - resolution: {integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==} + resolution: + { + integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==, + } peerDependencies: react: ^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 thread-stream@3.1.0: - resolution: {integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==} + resolution: + { + integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==, + } throttleit@2.1.0: - resolution: {integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==} - engines: {node: '>=18'} + resolution: + { + integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==, + } + engines: { node: ">=18" } tldts-core@6.1.86: - resolution: {integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==} + resolution: + { + integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==, + } tldts@6.1.86: - resolution: {integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==} + resolution: + { + integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==, + } hasBin: true to-regex-range@5.0.1: - resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} - engines: {node: '>=8.0'} + resolution: + { + integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==, + } + engines: { node: ">=8.0" } toidentifier@1.0.1: - resolution: {integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==} - engines: {node: '>=0.6'} + resolution: + { + integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==, + } + engines: { node: ">=0.6" } tough-cookie@5.1.2: - resolution: {integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==} - engines: {node: '>=16'} + resolution: + { + integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==, + } + engines: { node: ">=16" } tr46@0.0.3: - resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} + resolution: + { + integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==, + } ts-api-utils@2.1.0: - resolution: {integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==} - engines: {node: '>=18.12'} + resolution: + { + integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==, + } + engines: { node: ">=18.12" } peerDependencies: - typescript: '>=4.8.4' + typescript: ">=4.8.4" type-check@0.4.0: - resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} - engines: {node: '>= 0.8.0'} + resolution: + { + integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==, + } + engines: { node: ">= 0.8.0" } type-is@2.0.1: - resolution: {integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==} - engines: {node: '>= 0.6'} + resolution: + { + integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==, + } + engines: { node: ">= 0.6" } typed-array-buffer@1.0.3: - resolution: {integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==, + } + engines: { node: ">= 0.4" } typed-array-byte-length@1.0.3: - resolution: {integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==, + } + engines: { node: ">= 0.4" } typed-array-byte-offset@1.0.4: - resolution: {integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==, + } + engines: { node: ">= 0.4" } typed-array-length@1.0.7: - resolution: {integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==, + } + engines: { node: ">= 0.4" } typescript-eslint@8.35.0: - resolution: {integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + resolution: + { + integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==, + } + engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + typescript: ">=4.8.4 <5.9.0" typescript@5.8.3: - resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} - engines: {node: '>=14.17'} + resolution: + { + integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==, + } + engines: { node: ">=14.17" } hasBin: true unbox-primitive@1.1.0: - resolution: {integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==, + } + engines: { node: ">= 0.4" } undici-types@5.26.5: - resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} + resolution: + { + integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==, + } unpipe@1.0.0: - resolution: {integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==, + } + engines: { node: ">= 0.8" } uri-js@4.4.1: - resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} + resolution: + { + integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==, + } use-sync-external-store@1.5.0: - resolution: {integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==} + resolution: + { + integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==, + } peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 uuid@9.0.1: - resolution: {integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==} + resolution: + { + integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==, + } hasBin: true vary@1.1.2: - resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} - engines: {node: '>= 0.8'} + resolution: + { + integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==, + } + engines: { node: ">= 0.8" } web-streams-polyfill@4.0.0-beta.3: - resolution: {integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==} - engines: {node: '>= 14'} + resolution: + { + integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==, + } + engines: { node: ">= 14" } webidl-conversions@3.0.1: - resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==} + resolution: + { + integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==, + } whatwg-url@5.0.0: - resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} + resolution: + { + integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==, + } which-boxed-primitive@1.1.1: - resolution: {integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==, + } + engines: { node: ">= 0.4" } which-builtin-type@1.2.1: - resolution: {integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==, + } + engines: { node: ">= 0.4" } which-collection@1.0.2: - resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==, + } + engines: { node: ">= 0.4" } which-typed-array@1.1.19: - resolution: {integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==} - engines: {node: '>= 0.4'} + resolution: + { + integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==, + } + engines: { node: ">= 0.4" } which@2.0.2: - resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} - engines: {node: '>= 8'} + resolution: + { + integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==, + } + engines: { node: ">= 8" } hasBin: true word-wrap@1.2.5: - resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} - engines: {node: '>=0.10.0'} + resolution: + { + integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==, + } + engines: { node: ">=0.10.0" } wrappy@1.0.2: - resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==} + resolution: + { + integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==, + } ws@8.18.2: - resolution: {integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==} - engines: {node: '>=10.0.0'} + resolution: + { + integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==, + } + engines: { node: ">=10.0.0" } peerDependencies: bufferutil: ^4.0.1 - utf-8-validate: '>=5.0.2' + utf-8-validate: ">=5.0.2" peerDependenciesMeta: bufferutil: optional: true @@ -1735,140 +2966,148 @@ packages: optional: true yocto-queue@0.1.0: - resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} - engines: {node: '>=10'} + resolution: + { + integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==, + } + engines: { node: ">=10" } zod-to-json-schema@3.24.6: - resolution: {integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==} + resolution: + { + integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==, + } peerDependencies: zod: ^3.24.1 zod@3.25.67: - resolution: {integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==} + resolution: + { + integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==, + } snapshots: - - '@ai-sdk/anthropic@1.2.12(zod@3.25.67)': + "@ai-sdk/anthropic@1.2.12(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/azure@1.3.23(zod@3.25.67)': + "@ai-sdk/azure@1.3.23(zod@3.25.67)": dependencies: - '@ai-sdk/openai': 1.3.22(zod@3.25.67) - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/openai": 1.3.22(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/cerebras@0.2.14(zod@3.25.67)': + "@ai-sdk/cerebras@0.2.14(zod@3.25.67)": dependencies: - '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/deepseek@0.2.14(zod@3.25.67)': + "@ai-sdk/deepseek@0.2.14(zod@3.25.67)": dependencies: - '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/google@1.2.19(zod@3.25.67)': + "@ai-sdk/google@1.2.19(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/groq@1.2.9(zod@3.25.67)': + "@ai-sdk/groq@1.2.9(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/mistral@1.2.8(zod@3.25.67)': + "@ai-sdk/mistral@1.2.8(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)': + "@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/openai@1.3.22(zod@3.25.67)': + "@ai-sdk/openai@1.3.22(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/perplexity@1.1.9(zod@3.25.67)': + "@ai-sdk/perplexity@1.1.9(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/provider-utils@2.2.8(zod@3.25.67)': + "@ai-sdk/provider-utils@2.2.8(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 + "@ai-sdk/provider": 1.1.3 nanoid: 3.3.11 secure-json-parse: 2.7.0 zod: 3.25.67 - '@ai-sdk/provider@1.1.3': + "@ai-sdk/provider@1.1.3": dependencies: json-schema: 0.4.0 - '@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)': + "@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)": dependencies: - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) - '@ai-sdk/ui-utils': 1.2.11(zod@3.25.67) + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) react: 19.1.0 swr: 2.3.3(react@19.1.0) throttleit: 2.1.0 optionalDependencies: zod: 3.25.67 - '@ai-sdk/togetherai@0.2.14(zod@3.25.67)': + "@ai-sdk/togetherai@0.2.14(zod@3.25.67)": dependencies: - '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@ai-sdk/ui-utils@1.2.11(zod@3.25.67)': + "@ai-sdk/ui-utils@1.2.11(zod@3.25.67)": dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 zod-to-json-schema: 3.24.6(zod@3.25.67) - '@ai-sdk/xai@1.2.16(zod@3.25.67)': + "@ai-sdk/xai@1.2.16(zod@3.25.67)": dependencies: - '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - '@anthropic-ai/sdk@0.39.0': + "@anthropic-ai/sdk@0.39.0": dependencies: - '@types/node': 18.19.112 - '@types/node-fetch': 2.6.12 + "@types/node": 18.19.112 + "@types/node-fetch": 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -1877,10 +3116,10 @@ snapshots: transitivePeerDependencies: - encoding - '@browserbasehq/sdk@2.6.0': + "@browserbasehq/sdk@2.6.0": dependencies: - '@types/node': 18.19.112 - '@types/node-fetch': 2.6.12 + "@types/node": 18.19.112 + "@types/node-fetch": 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -1889,11 +3128,11 @@ snapshots: transitivePeerDependencies: - encoding - '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)': + "@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)": dependencies: - '@anthropic-ai/sdk': 0.39.0 - '@browserbasehq/sdk': 2.6.0 - '@google/genai': 0.8.0 + "@anthropic-ai/sdk": 0.39.0 + "@browserbasehq/sdk": 2.6.0 + "@google/genai": 0.8.0 ai: 4.3.16(react@19.1.0)(zod@3.25.67) deepmerge: 4.3.1 devtools-protocol: 0.0.1464554 @@ -1907,17 +3146,17 @@ snapshots: zod: 3.25.67 zod-to-json-schema: 3.24.6(zod@3.25.67) optionalDependencies: - '@ai-sdk/anthropic': 1.2.12(zod@3.25.67) - '@ai-sdk/azure': 1.3.23(zod@3.25.67) - '@ai-sdk/cerebras': 0.2.14(zod@3.25.67) - '@ai-sdk/deepseek': 0.2.14(zod@3.25.67) - '@ai-sdk/google': 1.2.19(zod@3.25.67) - '@ai-sdk/groq': 1.2.9(zod@3.25.67) - '@ai-sdk/mistral': 1.2.8(zod@3.25.67) - '@ai-sdk/openai': 1.3.22(zod@3.25.67) - '@ai-sdk/perplexity': 1.1.9(zod@3.25.67) - '@ai-sdk/togetherai': 0.2.14(zod@3.25.67) - '@ai-sdk/xai': 1.2.16(zod@3.25.67) + "@ai-sdk/anthropic": 1.2.12(zod@3.25.67) + "@ai-sdk/azure": 1.3.23(zod@3.25.67) + "@ai-sdk/cerebras": 0.2.14(zod@3.25.67) + "@ai-sdk/deepseek": 0.2.14(zod@3.25.67) + "@ai-sdk/google": 1.2.19(zod@3.25.67) + "@ai-sdk/groq": 1.2.9(zod@3.25.67) + "@ai-sdk/mistral": 1.2.8(zod@3.25.67) + "@ai-sdk/openai": 1.3.22(zod@3.25.67) + "@ai-sdk/perplexity": 1.1.9(zod@3.25.67) + "@ai-sdk/togetherai": 0.2.14(zod@3.25.67) + "@ai-sdk/xai": 1.2.16(zod@3.25.67) ollama-ai-provider: 1.2.0(zod@3.25.67) transitivePeerDependencies: - bufferutil @@ -1926,32 +3165,32 @@ snapshots: - supports-color - utf-8-validate - '@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)': + "@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)": dependencies: eslint: 9.29.0 eslint-visitor-keys: 3.4.3 - '@eslint-community/regexpp@4.12.1': {} + "@eslint-community/regexpp@4.12.1": {} - '@eslint/config-array@0.20.1': + "@eslint/config-array@0.20.1": dependencies: - '@eslint/object-schema': 2.1.6 + "@eslint/object-schema": 2.1.6 debug: 4.4.1 minimatch: 3.1.2 transitivePeerDependencies: - supports-color - '@eslint/config-helpers@0.2.3': {} + "@eslint/config-helpers@0.2.3": {} - '@eslint/core@0.14.0': + "@eslint/core@0.14.0": dependencies: - '@types/json-schema': 7.0.15 + "@types/json-schema": 7.0.15 - '@eslint/core@0.15.1': + "@eslint/core@0.15.1": dependencies: - '@types/json-schema': 7.0.15 + "@types/json-schema": 7.0.15 - '@eslint/eslintrc@3.3.1': + "@eslint/eslintrc@3.3.1": dependencies: ajv: 6.12.6 debug: 4.4.1 @@ -1965,16 +3204,16 @@ snapshots: transitivePeerDependencies: - supports-color - '@eslint/js@9.29.0': {} + "@eslint/js@9.29.0": {} - '@eslint/object-schema@2.1.6': {} + "@eslint/object-schema@2.1.6": {} - '@eslint/plugin-kit@0.3.3': + "@eslint/plugin-kit@0.3.3": dependencies: - '@eslint/core': 0.15.1 + "@eslint/core": 0.15.1 levn: 0.4.1 - '@google/genai@0.8.0': + "@google/genai@0.8.0": dependencies: google-auth-library: 9.15.1 ws: 8.18.2 @@ -1984,20 +3223,20 @@ snapshots: - supports-color - utf-8-validate - '@humanfs/core@0.19.1': {} + "@humanfs/core@0.19.1": {} - '@humanfs/node@0.16.6': + "@humanfs/node@0.16.6": dependencies: - '@humanfs/core': 0.19.1 - '@humanwhocodes/retry': 0.3.1 + "@humanfs/core": 0.19.1 + "@humanwhocodes/retry": 0.3.1 - '@humanwhocodes/module-importer@1.0.1': {} + "@humanwhocodes/module-importer@1.0.1": {} - '@humanwhocodes/retry@0.3.1': {} + "@humanwhocodes/retry@0.3.1": {} - '@humanwhocodes/retry@0.4.3': {} + "@humanwhocodes/retry@0.4.3": {} - '@modelcontextprotocol/sdk@1.13.1': + "@modelcontextprotocol/sdk@1.13.1": dependencies: ajv: 6.12.6 content-type: 1.0.5 @@ -2013,47 +3252,47 @@ snapshots: transitivePeerDependencies: - supports-color - '@nodelib/fs.scandir@2.1.5': + "@nodelib/fs.scandir@2.1.5": dependencies: - '@nodelib/fs.stat': 2.0.5 + "@nodelib/fs.stat": 2.0.5 run-parallel: 1.2.0 - '@nodelib/fs.stat@2.0.5': {} + "@nodelib/fs.stat@2.0.5": {} - '@nodelib/fs.walk@1.2.8': + "@nodelib/fs.walk@1.2.8": dependencies: - '@nodelib/fs.scandir': 2.1.5 + "@nodelib/fs.scandir": 2.1.5 fastq: 1.19.1 - '@opentelemetry/api@1.9.0': {} + "@opentelemetry/api@1.9.0": {} - '@playwright/test@1.53.1': + "@playwright/test@1.53.1": dependencies: playwright: 1.53.1 - '@types/diff-match-patch@1.0.36': {} + "@types/diff-match-patch@1.0.36": {} - '@types/estree@1.0.8': {} + "@types/estree@1.0.8": {} - '@types/json-schema@7.0.15': {} + "@types/json-schema@7.0.15": {} - '@types/node-fetch@2.6.12': + "@types/node-fetch@2.6.12": dependencies: - '@types/node': 18.19.112 + "@types/node": 18.19.112 form-data: 4.0.3 - '@types/node@18.19.112': + "@types/node@18.19.112": dependencies: undici-types: 5.26.5 - '@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)': + "@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)": dependencies: - '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 8.35.0(eslint@9.29.0)(typescript@5.8.3) - '@typescript-eslint/scope-manager': 8.35.0 - '@typescript-eslint/type-utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) - '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.35.0 + "@eslint-community/regexpp": 4.12.1 + "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/type-utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/visitor-keys": 8.35.0 eslint: 9.29.0 graphemer: 1.4.0 ignore: 7.0.5 @@ -2063,40 +3302,40 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)': + "@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)": dependencies: - '@typescript-eslint/scope-manager': 8.35.0 - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.35.0 + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + "@typescript-eslint/visitor-keys": 8.35.0 debug: 4.4.1 eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.35.0(typescript@5.8.3)': + "@typescript-eslint/project-service@8.35.0(typescript@5.8.3)": dependencies: - '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) - '@typescript-eslint/types': 8.35.0 + "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) + "@typescript-eslint/types": 8.35.0 debug: 4.4.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.35.0': + "@typescript-eslint/scope-manager@8.35.0": dependencies: - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/visitor-keys': 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/visitor-keys": 8.35.0 - '@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)': + "@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)": dependencies: typescript: 5.8.3 - '@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)': + "@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": dependencies: - '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) - '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) debug: 4.4.1 eslint: 9.29.0 ts-api-utils: 2.1.0(typescript@5.8.3) @@ -2104,14 +3343,14 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.35.0': {} + "@typescript-eslint/types@8.35.0": {} - '@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)': + "@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)": dependencies: - '@typescript-eslint/project-service': 8.35.0(typescript@5.8.3) - '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/visitor-keys': 8.35.0 + "@typescript-eslint/project-service": 8.35.0(typescript@5.8.3) + "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/visitor-keys": 8.35.0 debug: 4.4.1 fast-glob: 3.3.3 is-glob: 4.0.3 @@ -2122,20 +3361,20 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)': + "@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0) - '@typescript-eslint/scope-manager': 8.35.0 - '@typescript-eslint/types': 8.35.0 - '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) + "@typescript-eslint/scope-manager": 8.35.0 + "@typescript-eslint/types": 8.35.0 + "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.35.0': + "@typescript-eslint/visitor-keys@8.35.0": dependencies: - '@typescript-eslint/types': 8.35.0 + "@typescript-eslint/types": 8.35.0 eslint-visitor-keys: 4.2.1 abort-controller@3.0.0: @@ -2161,11 +3400,11 @@ snapshots: ai@4.3.16(react@19.1.0)(zod@3.25.67): dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) - '@ai-sdk/react': 1.2.12(react@19.1.0)(zod@3.25.67) - '@ai-sdk/ui-utils': 1.2.11(zod@3.25.67) - '@opentelemetry/api': 1.9.0 + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + "@ai-sdk/react": 1.2.12(react@19.1.0)(zod@3.25.67) + "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) + "@opentelemetry/api": 1.9.0 jsondiffpatch: 0.6.0 zod: 3.25.67 optionalDependencies: @@ -2563,19 +3802,19 @@ snapshots: eslint@9.29.0: dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0) - '@eslint-community/regexpp': 4.12.1 - '@eslint/config-array': 0.20.1 - '@eslint/config-helpers': 0.2.3 - '@eslint/core': 0.14.0 - '@eslint/eslintrc': 3.3.1 - '@eslint/js': 9.29.0 - '@eslint/plugin-kit': 0.3.3 - '@humanfs/node': 0.16.6 - '@humanwhocodes/module-importer': 1.0.1 - '@humanwhocodes/retry': 0.4.3 - '@types/estree': 1.0.8 - '@types/json-schema': 7.0.15 + "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) + "@eslint-community/regexpp": 4.12.1 + "@eslint/config-array": 0.20.1 + "@eslint/config-helpers": 0.2.3 + "@eslint/core": 0.14.0 + "@eslint/eslintrc": 3.3.1 + "@eslint/js": 9.29.0 + "@eslint/plugin-kit": 0.3.3 + "@humanfs/node": 0.16.6 + "@humanwhocodes/module-importer": 1.0.1 + "@humanwhocodes/retry": 0.4.3 + "@types/estree": 1.0.8 + "@types/json-schema": 7.0.15 ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.6 @@ -2673,8 +3912,8 @@ snapshots: fast-glob@3.3.3: dependencies: - '@nodelib/fs.stat': 2.0.5 - '@nodelib/fs.walk': 1.2.8 + "@nodelib/fs.stat": 2.0.5 + "@nodelib/fs.walk": 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.8 @@ -3087,7 +4326,7 @@ snapshots: jsondiffpatch@0.6.0: dependencies: - '@types/diff-match-patch': 1.0.36 + "@types/diff-match-patch": 1.0.36 chalk: 5.4.1 diff-match-patch: 1.0.5 @@ -3215,8 +4454,8 @@ snapshots: ollama-ai-provider@1.2.0(zod@3.25.67): dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + "@ai-sdk/provider": 1.1.3 + "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) partial-json: 0.1.7 optionalDependencies: zod: 3.25.67 @@ -3234,8 +4473,8 @@ snapshots: openai@4.104.0(ws@8.18.2)(zod@3.25.67): dependencies: - '@types/node': 18.19.112 - '@types/node-fetch': 2.6.12 + "@types/node": 18.19.112 + "@types/node-fetch": 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -3713,9 +4952,9 @@ snapshots: typescript-eslint@8.35.0(eslint@9.29.0)(typescript@5.8.3): dependencies: - '@typescript-eslint/eslint-plugin': 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) - '@typescript-eslint/parser': 8.35.0(eslint@9.29.0)(typescript@5.8.3) - '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/eslint-plugin": 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: diff --git a/src/mcp/prompts.ts b/src/mcp/prompts.ts index 83b6cc9..ff62aea 100644 --- a/src/mcp/prompts.ts +++ b/src/mcp/prompts.ts @@ -9,8 +9,8 @@ export const PROMPTS = [ { name: "click_search_button", description: "A prompt template for clicking on a search button", - arguments: [] // No arguments required for this specific prompt - } + arguments: [], // No arguments required for this specific prompt + }, ]; /** @@ -21,18 +21,19 @@ export const PROMPTS = [ export function getPrompt(name: string) { if (name === "click_search_button") { return { - description: "This prompt provides instructions for clicking on a search button", + description: + "This prompt provides instructions for clicking on a search button", messages: [ { role: "user", content: { type: "text", - text: "Please click on the search button" - } - } - ] + text: "Please click on the search button", + }, + }, + ], }; } - + throw new Error(`Invalid prompt name: ${name}`); -} \ No newline at end of file +} From ff674aa2fad9a5cf7fe0e97cbe6544613d040be5 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 26 Jun 2025 23:12:51 -0700 Subject: [PATCH 13/32] better husky script, multisession prompting updates + stagehand store uses datenow for extra uniqueness --- .husky/pre-commit | 6 +- README.md | 14 +- package.json | 7 + pnpm-lock.yaml | 3484 +++++++++++++------------------------ src/mcp/prompts.ts | 104 ++ src/mcp/sampling.ts | 204 +++ src/stagehandStore.ts | 2 +- src/tools/index.ts | 2 +- src/tools/multiSession.ts | 22 +- src/tools/session.ts | 2 +- 10 files changed, 1579 insertions(+), 2268 deletions(-) mode change 100644 => 100755 .husky/pre-commit create mode 100644 src/mcp/sampling.ts diff --git a/.husky/pre-commit b/.husky/pre-commit old mode 100644 new mode 100755 index e3ad1ac..0312b76 --- a/.husky/pre-commit +++ b/.husky/pre-commit @@ -1,2 +1,4 @@ -pnpm lint -pnpm prettier:fix \ No newline at end of file +#!/usr/bin/env sh +. "$(dirname -- "$0")/_/husky.sh" + +npx lint-staged \ No newline at end of file diff --git a/README.md b/README.md index 55ab677..69a905b 100644 --- a/README.md +++ b/README.md @@ -339,7 +339,7 @@ The server supports managing multiple independent browser sessions in parallel, #### Session Lifecycle Management -- **multi-browserbase_stagehand_session_create** +- **multi_browserbase_stagehand_session_create** - Create a new independent Stagehand browser session with full web automation capabilities - Each session is isolated with its own browser instance, cookies, and state - Inputs: @@ -356,7 +356,7 @@ The server supports managing multiple independent browser sessions in parallel, - Output: - Comprehensive list of active sessions with status information -- **multi-browserbase_stagehand_session_close** +- **multi_browserbase_stagehand_session_close** - Close and clean up a specific Stagehand browser session - Terminates browser instance, ends Browserbase session, and frees resources - Input: @@ -368,26 +368,26 @@ The server supports managing multiple independent browser sessions in parallel, All core browser automation tools are available with session-specific variants: -- **multi-browserbase_stagehand_navigate_session** +- **multi_browserbase_stagehand_navigate_session** - Navigate to a URL in a specific browser session - Inputs: - `sessionId` (string): The session ID to use - `url` (string): The URL to navigate to -- **multi-browserbase_stagehand_act_session** +- **multi_browserbase_stagehand_act_session** - Perform an action in a specific browser session using natural language - Inputs: - `sessionId` (string): The session ID to use - `action` (string): The action to perform (e.g., "click the login button") - `variables` (object, optional): Variables for sensitive data in action templates -- **multi-browserbase_stagehand_extract_session** +- **multi_browserbase_stagehand_extract_session** - Extract structured information from a specific browser session - Inputs: - `sessionId` (string): The session ID to use - `instruction` (string): What to extract from the page -- **multi-browserbase_stagehand_observe_session** +- **multi_browserbase_stagehand_observe_session** - Observe and find actionable elements in a specific browser session - Inputs: - `sessionId` (string): The session ID to use @@ -519,7 +519,7 @@ The server supports two session management approaches: - Automatically manages the active session 2. **Multi-Session Mode**: Advanced approach with multiple parallel browser sessions - - Tools: `multi-browserbase_stagehand_session_create`, `multi-browserbase_stagehand_session_close`, `browserbase_stagehand_session_list` + - Tools: `multi_browserbase_stagehand_session_create`, `multi_browserbase_stagehand_session_close`, `browserbase_stagehand_session_list` - Session-specific variants of all core tools (with `_session` suffix) - Ideal for complex workflows requiring parallel browser instances - Each session maintains independent state, cookies, and browser context diff --git a/package.json b/package.json index 43bd2e2..472f026 100644 --- a/package.json +++ b/package.json @@ -26,6 +26,12 @@ "prettier:check": "prettier --check .", "prettier:fix": "prettier --write ." }, + "lint-staged": { + "*.{js,jsx,ts,tsx,json,css,scss,md}": [ + "prettier --write", + "eslint --fix" + ] + }, "dependencies": { "@browserbasehq/stagehand": "^2.4.0", "@modelcontextprotocol/sdk": "^1.13.1", @@ -38,6 +44,7 @@ "eslint-plugin-react": "^7.37.5", "globals": "^16.2.0", "husky": "^9.1.7", + "lint-staged": "^16.1.2", "prettier": "^3.6.1", "shx": "^0.3.4", "typescript": "^5.6.2", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index b35f54f..f090304 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1,26 +1,27 @@ -lockfileVersion: "9.0" +lockfileVersion: '9.0' settings: autoInstallPeers: true excludeLinksFromLockfile: false importers: + .: dependencies: - "@browserbasehq/stagehand": + '@browserbasehq/stagehand': specifier: ^2.4.0 version: 2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67) - "@modelcontextprotocol/sdk": + '@modelcontextprotocol/sdk': specifier: ^1.13.1 version: 1.13.1 - "@playwright/test": + '@playwright/test': specifier: ^1.49.0 version: 1.53.1 commander: specifier: ^14.0.0 version: 14.0.0 devDependencies: - "@eslint/js": + '@eslint/js': specifier: ^9.29.0 version: 9.29.0 eslint: @@ -35,6 +36,9 @@ importers: husky: specifier: ^9.1.7 version: 9.1.7 + lint-staged: + specifier: ^16.1.2 + version: 16.1.2 prettier: specifier: ^3.6.1 version: 3.6.1 @@ -49,118 +53,80 @@ importers: version: 8.35.0(eslint@9.29.0)(typescript@5.8.3) packages: - "@ai-sdk/anthropic@1.2.12": - resolution: - { - integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==, - } - engines: { node: ">=18" } + + '@ai-sdk/anthropic@1.2.12': + resolution: {integrity: sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/azure@1.3.23": - resolution: - { - integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==, - } - engines: { node: ">=18" } + '@ai-sdk/azure@1.3.23': + resolution: {integrity: sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/cerebras@0.2.14": - resolution: - { - integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==, - } - engines: { node: ">=18" } + '@ai-sdk/cerebras@0.2.14': + resolution: {integrity: sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/deepseek@0.2.14": - resolution: - { - integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==, - } - engines: { node: ">=18" } + '@ai-sdk/deepseek@0.2.14': + resolution: {integrity: sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/google@1.2.19": - resolution: - { - integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==, - } - engines: { node: ">=18" } + '@ai-sdk/google@1.2.19': + resolution: {integrity: sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/groq@1.2.9": - resolution: - { - integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==, - } - engines: { node: ">=18" } + '@ai-sdk/groq@1.2.9': + resolution: {integrity: sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/mistral@1.2.8": - resolution: - { - integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==, - } - engines: { node: ">=18" } + '@ai-sdk/mistral@1.2.8': + resolution: {integrity: sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/openai-compatible@0.2.14": - resolution: - { - integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==, - } - engines: { node: ">=18" } + '@ai-sdk/openai-compatible@0.2.14': + resolution: {integrity: sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/openai@1.3.22": - resolution: - { - integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==, - } - engines: { node: ">=18" } + '@ai-sdk/openai@1.3.22': + resolution: {integrity: sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/perplexity@1.1.9": - resolution: - { - integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==, - } - engines: { node: ">=18" } + '@ai-sdk/perplexity@1.1.9': + resolution: {integrity: sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/provider-utils@2.2.8": - resolution: - { - integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==, - } - engines: { node: ">=18" } + '@ai-sdk/provider-utils@2.2.8': + resolution: {integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.23.8 - "@ai-sdk/provider@1.1.3": - resolution: - { - integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==, - } - engines: { node: ">=18" } - - "@ai-sdk/react@1.2.12": - resolution: - { - integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==, - } - engines: { node: ">=18" } + '@ai-sdk/provider@1.1.3': + resolution: {integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==} + engines: {node: '>=18'} + + '@ai-sdk/react@1.2.12': + resolution: {integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==} + engines: {node: '>=18'} peerDependencies: react: ^18 || ^19 || ^19.0.0-rc zod: ^3.23.8 @@ -168,381 +134,231 @@ packages: zod: optional: true - "@ai-sdk/togetherai@0.2.14": - resolution: - { - integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==, - } - engines: { node: ">=18" } + '@ai-sdk/togetherai@0.2.14': + resolution: {integrity: sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@ai-sdk/ui-utils@1.2.11": - resolution: - { - integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==, - } - engines: { node: ">=18" } + '@ai-sdk/ui-utils@1.2.11': + resolution: {integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==} + engines: {node: '>=18'} peerDependencies: zod: ^3.23.8 - "@ai-sdk/xai@1.2.16": - resolution: - { - integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==, - } - engines: { node: ">=18" } + '@ai-sdk/xai@1.2.16': + resolution: {integrity: sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 - "@anthropic-ai/sdk@0.39.0": - resolution: - { - integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==, - } - - "@browserbasehq/sdk@2.6.0": - resolution: - { - integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==, - } - - "@browserbasehq/stagehand@2.4.0": - resolution: - { - integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==, - } + '@anthropic-ai/sdk@0.39.0': + resolution: {integrity: sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==} + + '@browserbasehq/sdk@2.6.0': + resolution: {integrity: sha512-83iXP5D7xMm8Wyn66TUaUrgoByCmAJuoMoZQI3sGg3JAiMlTfnCIMqyVBoNSaItaPIkaCnrsj6LiusmXV2X9YA==} + + '@browserbasehq/stagehand@2.4.0': + resolution: {integrity: sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==} peerDependencies: deepmerge: ^4.3.1 dotenv: ^16.4.5 zod: ^3.23.8 - "@eslint-community/eslint-utils@4.7.0": - resolution: - { - integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==, - } - engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } + '@eslint-community/eslint-utils@4.7.0': + resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} peerDependencies: eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 - "@eslint-community/regexpp@4.12.1": - resolution: - { - integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==, - } - engines: { node: ^12.0.0 || ^14.0.0 || >=16.0.0 } - - "@eslint/config-array@0.20.1": - resolution: - { - integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/config-helpers@0.2.3": - resolution: - { - integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/core@0.14.0": - resolution: - { - integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/core@0.15.1": - resolution: - { - integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/eslintrc@3.3.1": - resolution: - { - integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/js@9.29.0": - resolution: - { - integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/object-schema@2.1.6": - resolution: - { - integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@eslint/plugin-kit@0.3.3": - resolution: - { - integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@google/genai@0.8.0": - resolution: - { - integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==, - } - engines: { node: ">=18.0.0" } - - "@humanfs/core@0.19.1": - resolution: - { - integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==, - } - engines: { node: ">=18.18.0" } - - "@humanfs/node@0.16.6": - resolution: - { - integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==, - } - engines: { node: ">=18.18.0" } - - "@humanwhocodes/module-importer@1.0.1": - resolution: - { - integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==, - } - engines: { node: ">=12.22" } - - "@humanwhocodes/retry@0.3.1": - resolution: - { - integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==, - } - engines: { node: ">=18.18" } - - "@humanwhocodes/retry@0.4.3": - resolution: - { - integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==, - } - engines: { node: ">=18.18" } - - "@modelcontextprotocol/sdk@1.13.1": - resolution: - { - integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==, - } - engines: { node: ">=18" } - - "@nodelib/fs.scandir@2.1.5": - resolution: - { - integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==, - } - engines: { node: ">= 8" } - - "@nodelib/fs.stat@2.0.5": - resolution: - { - integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==, - } - engines: { node: ">= 8" } - - "@nodelib/fs.walk@1.2.8": - resolution: - { - integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==, - } - engines: { node: ">= 8" } - - "@opentelemetry/api@1.9.0": - resolution: - { - integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==, - } - engines: { node: ">=8.0.0" } - - "@playwright/test@1.53.1": - resolution: - { - integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==, - } - engines: { node: ">=18" } + '@eslint-community/regexpp@4.12.1': + resolution: {integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==} + engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} + + '@eslint/config-array@0.20.1': + resolution: {integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/config-helpers@0.2.3': + resolution: {integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/core@0.14.0': + resolution: {integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/core@0.15.1': + resolution: {integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/eslintrc@3.3.1': + resolution: {integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/js@9.29.0': + resolution: {integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/object-schema@2.1.6': + resolution: {integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@eslint/plugin-kit@0.3.3': + resolution: {integrity: sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@google/genai@0.8.0': + resolution: {integrity: sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==} + engines: {node: '>=18.0.0'} + + '@humanfs/core@0.19.1': + resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==} + engines: {node: '>=18.18.0'} + + '@humanfs/node@0.16.6': + resolution: {integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==} + engines: {node: '>=18.18.0'} + + '@humanwhocodes/module-importer@1.0.1': + resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} + engines: {node: '>=12.22'} + + '@humanwhocodes/retry@0.3.1': + resolution: {integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==} + engines: {node: '>=18.18'} + + '@humanwhocodes/retry@0.4.3': + resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} + engines: {node: '>=18.18'} + + '@modelcontextprotocol/sdk@1.13.1': + resolution: {integrity: sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==} + engines: {node: '>=18'} + + '@nodelib/fs.scandir@2.1.5': + resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} + engines: {node: '>= 8'} + + '@nodelib/fs.stat@2.0.5': + resolution: {integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==} + engines: {node: '>= 8'} + + '@nodelib/fs.walk@1.2.8': + resolution: {integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==} + engines: {node: '>= 8'} + + '@opentelemetry/api@1.9.0': + resolution: {integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==} + engines: {node: '>=8.0.0'} + + '@playwright/test@1.53.1': + resolution: {integrity: sha512-Z4c23LHV0muZ8hfv4jw6HngPJkbbtZxTkxPNIg7cJcTc9C28N/p2q7g3JZS2SiKBBHJ3uM1dgDye66bB7LEk5w==} + engines: {node: '>=18'} hasBin: true - "@types/diff-match-patch@1.0.36": - resolution: - { - integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==, - } - - "@types/estree@1.0.8": - resolution: - { - integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==, - } - - "@types/json-schema@7.0.15": - resolution: - { - integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==, - } - - "@types/node-fetch@2.6.12": - resolution: - { - integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==, - } - - "@types/node@18.19.112": - resolution: - { - integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==, - } - - "@typescript-eslint/eslint-plugin@8.35.0": - resolution: - { - integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + '@types/diff-match-patch@1.0.36': + resolution: {integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==} + + '@types/estree@1.0.8': + resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==} + + '@types/json-schema@7.0.15': + resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} + + '@types/node-fetch@2.6.12': + resolution: {integrity: sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==} + + '@types/node@18.19.112': + resolution: {integrity: sha512-i+Vukt9POdS/MBI7YrrkkI5fMfwFtOjphSmt4WXYLfwqsfr6z/HdCx7LqT9M7JktGob8WNgj8nFB4TbGNE4Cog==} + + '@typescript-eslint/eslint-plugin@8.35.0': + resolution: {integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - "@typescript-eslint/parser": ^8.35.0 + '@typescript-eslint/parser': ^8.35.0 eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/parser@8.35.0": - resolution: - { - integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/parser@8.35.0': + resolution: {integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/project-service@8.35.0": - resolution: - { - integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/project-service@8.35.0': + resolution: {integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/scope-manager@8.35.0": - resolution: - { - integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@typescript-eslint/tsconfig-utils@8.35.0": - resolution: - { - integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/scope-manager@8.35.0': + resolution: {integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@typescript-eslint/tsconfig-utils@8.35.0': + resolution: {integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/type-utils@8.35.0": - resolution: - { - integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/type-utils@8.35.0': + resolution: {integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/types@8.35.0": - resolution: - { - integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } - - "@typescript-eslint/typescript-estree@8.35.0": - resolution: - { - integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/types@8.35.0': + resolution: {integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + + '@typescript-eslint/typescript-estree@8.35.0': + resolution: {integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: ">=4.8.4 <5.9.0" - - "@typescript-eslint/utils@8.35.0": - resolution: - { - integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + typescript: '>=4.8.4 <5.9.0' + + '@typescript-eslint/utils@8.35.0': + resolution: {integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" + typescript: '>=4.8.4 <5.9.0' - "@typescript-eslint/visitor-keys@8.35.0": - resolution: - { - integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + '@typescript-eslint/visitor-keys@8.35.0': + resolution: {integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} abort-controller@3.0.0: - resolution: - { - integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==, - } - engines: { node: ">=6.5" } + resolution: {integrity: sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==} + engines: {node: '>=6.5'} accepts@2.0.0: - resolution: - { - integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==} + engines: {node: '>= 0.6'} acorn-jsx@5.3.2: - resolution: - { - integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==, - } + resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 acorn@8.15.0: - resolution: - { - integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==, - } - engines: { node: ">=0.4.0" } + resolution: {integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==} + engines: {node: '>=0.4.0'} hasBin: true agent-base@7.1.3: - resolution: - { - integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==, - } - engines: { node: ">= 14" } + resolution: {integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==} + engines: {node: '>= 14'} agentkeepalive@4.6.0: - resolution: - { - integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==, - } - engines: { node: ">= 8.0.0" } + resolution: {integrity: sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==} + engines: {node: '>= 8.0.0'} ai@4.3.16: - resolution: - { - integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==} + engines: {node: '>=18'} peerDependencies: react: ^18 || ^19 || ^19.0.0-rc zod: ^3.23.8 @@ -551,1494 +367,907 @@ packages: optional: true ajv@6.12.6: - resolution: - { - integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==, - } + resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} + + ansi-escapes@7.0.0: + resolution: {integrity: sha512-GdYO7a61mR0fOlAsvC9/rIHf7L96sBc6dEWzeOu+KAea5bZyQRPIpojrVoI4AXGJS/ycu/fBTdLrUkA4ODrvjw==} + engines: {node: '>=18'} + + ansi-regex@6.1.0: + resolution: {integrity: sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==} + engines: {node: '>=12'} ansi-styles@4.3.0: - resolution: - { - integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} + engines: {node: '>=8'} + + ansi-styles@6.2.1: + resolution: {integrity: sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==} + engines: {node: '>=12'} argparse@2.0.1: - resolution: - { - integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==, - } + resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} array-buffer-byte-length@1.0.2: - resolution: - { - integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==} + engines: {node: '>= 0.4'} array-includes@3.1.9: - resolution: - { - integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==} + engines: {node: '>= 0.4'} array.prototype.findlast@1.2.5: - resolution: - { - integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==} + engines: {node: '>= 0.4'} array.prototype.flat@1.3.3: - resolution: - { - integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==} + engines: {node: '>= 0.4'} array.prototype.flatmap@1.3.3: - resolution: - { - integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==} + engines: {node: '>= 0.4'} array.prototype.tosorted@1.1.4: - resolution: - { - integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==} + engines: {node: '>= 0.4'} arraybuffer.prototype.slice@1.0.4: - resolution: - { - integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==} + engines: {node: '>= 0.4'} async-function@1.0.0: - resolution: - { - integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==} + engines: {node: '>= 0.4'} asynckit@0.4.0: - resolution: - { - integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==, - } + resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} atomic-sleep@1.0.0: - resolution: - { - integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==, - } - engines: { node: ">=8.0.0" } + resolution: {integrity: sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==} + engines: {node: '>=8.0.0'} available-typed-arrays@1.0.7: - resolution: - { - integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} + engines: {node: '>= 0.4'} balanced-match@1.0.2: - resolution: - { - integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==, - } + resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} base64-js@1.5.1: - resolution: - { - integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==, - } + resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==} bignumber.js@9.3.0: - resolution: - { - integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==, - } + resolution: {integrity: sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==} body-parser@2.2.0: - resolution: - { - integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==} + engines: {node: '>=18'} brace-expansion@1.1.12: - resolution: - { - integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==, - } + resolution: {integrity: sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==} brace-expansion@2.0.2: - resolution: - { - integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==, - } + resolution: {integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==} braces@3.0.3: - resolution: - { - integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} + engines: {node: '>=8'} buffer-equal-constant-time@1.0.1: - resolution: - { - integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==, - } + resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} bytes@3.1.2: - resolution: - { - integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==} + engines: {node: '>= 0.8'} call-bind-apply-helpers@1.0.2: - resolution: - { - integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==} + engines: {node: '>= 0.4'} call-bind@1.0.8: - resolution: - { - integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==} + engines: {node: '>= 0.4'} call-bound@1.0.4: - resolution: - { - integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==} + engines: {node: '>= 0.4'} callsites@3.1.0: - resolution: - { - integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} + engines: {node: '>=6'} chalk@4.1.2: - resolution: - { - integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} + engines: {node: '>=10'} chalk@5.4.1: - resolution: - { - integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==, - } - engines: { node: ^12.17.0 || ^14.13 || >=16.0.0 } + resolution: {integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==} + engines: {node: ^12.17.0 || ^14.13 || >=16.0.0} + + cli-cursor@5.0.0: + resolution: {integrity: sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==} + engines: {node: '>=18'} + + cli-truncate@4.0.0: + resolution: {integrity: sha512-nPdaFdQ0h/GEigbPClz11D0v/ZJEwxmeVZGeMo3Z5StPtUTkA9o1lD6QwoirYiSDzbcwn2XcjwmCp68W1IS4TA==} + engines: {node: '>=18'} color-convert@2.0.1: - resolution: - { - integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==, - } - engines: { node: ">=7.0.0" } + resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==} + engines: {node: '>=7.0.0'} color-name@1.1.4: - resolution: - { - integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==, - } + resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} colorette@2.0.20: - resolution: - { - integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==, - } + resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} combined-stream@1.0.8: - resolution: - { - integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} + engines: {node: '>= 0.8'} commander@14.0.0: - resolution: - { - integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==, - } - engines: { node: ">=20" } + resolution: {integrity: sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==} + engines: {node: '>=20'} concat-map@0.0.1: - resolution: - { - integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==, - } + resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} content-disposition@1.0.0: - resolution: - { - integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==} + engines: {node: '>= 0.6'} content-type@1.0.5: - resolution: - { - integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==} + engines: {node: '>= 0.6'} cookie-signature@1.2.2: - resolution: - { - integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==, - } - engines: { node: ">=6.6.0" } + resolution: {integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==} + engines: {node: '>=6.6.0'} cookie@0.7.2: - resolution: - { - integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} + engines: {node: '>= 0.6'} cors@2.8.5: - resolution: - { - integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==} + engines: {node: '>= 0.10'} cross-spawn@7.0.6: - resolution: - { - integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==, - } - engines: { node: ">= 8" } + resolution: {integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==} + engines: {node: '>= 8'} data-view-buffer@1.0.2: - resolution: - { - integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==} + engines: {node: '>= 0.4'} data-view-byte-length@1.0.2: - resolution: - { - integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==} + engines: {node: '>= 0.4'} data-view-byte-offset@1.0.1: - resolution: - { - integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==} + engines: {node: '>= 0.4'} dateformat@4.6.3: - resolution: - { - integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==, - } + resolution: {integrity: sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==} debug@4.4.1: - resolution: - { - integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==, - } - engines: { node: ">=6.0" } + resolution: {integrity: sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==} + engines: {node: '>=6.0'} peerDependencies: - supports-color: "*" + supports-color: '*' peerDependenciesMeta: supports-color: optional: true deep-is@0.1.4: - resolution: - { - integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==, - } + resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} deepmerge@4.3.1: - resolution: - { - integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} + engines: {node: '>=0.10.0'} define-data-property@1.1.4: - resolution: - { - integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} + engines: {node: '>= 0.4'} define-properties@1.2.1: - resolution: - { - integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} + engines: {node: '>= 0.4'} delayed-stream@1.0.0: - resolution: - { - integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==, - } - engines: { node: ">=0.4.0" } + resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} + engines: {node: '>=0.4.0'} depd@2.0.0: - resolution: - { - integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==} + engines: {node: '>= 0.8'} dequal@2.0.3: - resolution: - { - integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} + engines: {node: '>=6'} devtools-protocol@0.0.1464554: - resolution: - { - integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==, - } + resolution: {integrity: sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==} diff-match-patch@1.0.5: - resolution: - { - integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==, - } + resolution: {integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==} doctrine@2.1.0: - resolution: - { - integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} + engines: {node: '>=0.10.0'} dotenv@16.5.0: - resolution: - { - integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==, - } - engines: { node: ">=12" } + resolution: {integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==} + engines: {node: '>=12'} dunder-proto@1.0.1: - resolution: - { - integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} + engines: {node: '>= 0.4'} ecdsa-sig-formatter@1.0.11: - resolution: - { - integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==, - } + resolution: {integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==} ee-first@1.1.1: - resolution: - { - integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==, - } + resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} + + emoji-regex@10.4.0: + resolution: {integrity: sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw==} encodeurl@2.0.0: - resolution: - { - integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==} + engines: {node: '>= 0.8'} end-of-stream@1.4.5: - resolution: - { - integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==, - } + resolution: {integrity: sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==} + + environment@1.1.0: + resolution: {integrity: sha512-xUtoPkMggbz0MPyPiIWr1Kp4aeWJjDZ6SMvURhimjdZgsRuDplF5/s9hcgGhyXMhs+6vpnuoiZ2kFiu3FMnS8Q==} + engines: {node: '>=18'} es-abstract@1.24.0: - resolution: - { - integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==} + engines: {node: '>= 0.4'} es-define-property@1.0.1: - resolution: - { - integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==} + engines: {node: '>= 0.4'} es-errors@1.3.0: - resolution: - { - integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} + engines: {node: '>= 0.4'} es-iterator-helpers@1.2.1: - resolution: - { - integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==} + engines: {node: '>= 0.4'} es-object-atoms@1.1.1: - resolution: - { - integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==} + engines: {node: '>= 0.4'} es-set-tostringtag@2.1.0: - resolution: - { - integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==} + engines: {node: '>= 0.4'} es-shim-unscopables@1.1.0: - resolution: - { - integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==} + engines: {node: '>= 0.4'} es-to-primitive@1.3.0: - resolution: - { - integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==} + engines: {node: '>= 0.4'} escape-html@1.0.3: - resolution: - { - integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==, - } + resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} escape-string-regexp@4.0.0: - resolution: - { - integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} + engines: {node: '>=10'} eslint-plugin-react@7.37.5: - resolution: - { - integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==, - } - engines: { node: ">=4" } + resolution: {integrity: sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==} + engines: {node: '>=4'} peerDependencies: eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 eslint-scope@8.4.0: - resolution: - { - integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} eslint-visitor-keys@3.4.3: - resolution: - { - integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==, - } - engines: { node: ^12.22.0 || ^14.17.0 || >=16.0.0 } + resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} eslint-visitor-keys@4.2.1: - resolution: - { - integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} eslint@9.29.0: - resolution: - { - integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} hasBin: true peerDependencies: - jiti: "*" + jiti: '*' peerDependenciesMeta: jiti: optional: true espree@10.4.0: - resolution: - { - integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} esquery@1.6.0: - resolution: - { - integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==, - } - engines: { node: ">=0.10" } + resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} + engines: {node: '>=0.10'} esrecurse@4.3.0: - resolution: - { - integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==, - } - engines: { node: ">=4.0" } + resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} + engines: {node: '>=4.0'} estraverse@5.3.0: - resolution: - { - integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==, - } - engines: { node: ">=4.0" } + resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==} + engines: {node: '>=4.0'} esutils@2.0.3: - resolution: - { - integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} + engines: {node: '>=0.10.0'} etag@1.8.1: - resolution: - { - integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==} + engines: {node: '>= 0.6'} event-target-shim@5.0.1: - resolution: - { - integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==} + engines: {node: '>=6'} + + eventemitter3@5.0.1: + resolution: {integrity: sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==} eventsource-parser@3.0.3: - resolution: - { - integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==, - } - engines: { node: ">=20.0.0" } + resolution: {integrity: sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==} + engines: {node: '>=20.0.0'} eventsource@3.0.7: - resolution: - { - integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==, - } - engines: { node: ">=18.0.0" } + resolution: {integrity: sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==} + engines: {node: '>=18.0.0'} express-rate-limit@7.5.1: - resolution: - { - integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==, - } - engines: { node: ">= 16" } + resolution: {integrity: sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==} + engines: {node: '>= 16'} peerDependencies: - express: ">= 4.11" + express: '>= 4.11' express@5.1.0: - resolution: - { - integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==} + engines: {node: '>= 18'} extend@3.0.2: - resolution: - { - integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==, - } + resolution: {integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==} fast-copy@3.0.2: - resolution: - { - integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==, - } + resolution: {integrity: sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==} fast-deep-equal@3.1.3: - resolution: - { - integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==, - } + resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} fast-glob@3.3.3: - resolution: - { - integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==, - } - engines: { node: ">=8.6.0" } + resolution: {integrity: sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==} + engines: {node: '>=8.6.0'} fast-json-stable-stringify@2.1.0: - resolution: - { - integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==, - } + resolution: {integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==} fast-levenshtein@2.0.6: - resolution: - { - integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==, - } + resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} fast-redact@3.5.0: - resolution: - { - integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==} + engines: {node: '>=6'} fast-safe-stringify@2.1.1: - resolution: - { - integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==, - } + resolution: {integrity: sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==} fastq@1.19.1: - resolution: - { - integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==, - } + resolution: {integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==} fetch-cookie@3.1.0: - resolution: - { - integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==, - } + resolution: {integrity: sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==} file-entry-cache@8.0.0: - resolution: - { - integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==, - } - engines: { node: ">=16.0.0" } + resolution: {integrity: sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==} + engines: {node: '>=16.0.0'} fill-range@7.1.1: - resolution: - { - integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} + engines: {node: '>=8'} finalhandler@2.1.0: - resolution: - { - integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==} + engines: {node: '>= 0.8'} find-up@5.0.0: - resolution: - { - integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} + engines: {node: '>=10'} flat-cache@4.0.1: - resolution: - { - integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==, - } - engines: { node: ">=16" } + resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} + engines: {node: '>=16'} flatted@3.3.3: - resolution: - { - integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==, - } + resolution: {integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==} for-each@0.3.5: - resolution: - { - integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==} + engines: {node: '>= 0.4'} form-data-encoder@1.7.2: - resolution: - { - integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==, - } + resolution: {integrity: sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==} form-data@4.0.3: - resolution: - { - integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==, - } - engines: { node: ">= 6" } + resolution: {integrity: sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA==} + engines: {node: '>= 6'} formdata-node@4.4.1: - resolution: - { - integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==, - } - engines: { node: ">= 12.20" } + resolution: {integrity: sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==} + engines: {node: '>= 12.20'} forwarded@0.2.0: - resolution: - { - integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==} + engines: {node: '>= 0.6'} fresh@2.0.0: - resolution: - { - integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==} + engines: {node: '>= 0.8'} fs.realpath@1.0.0: - resolution: - { - integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==, - } + resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==} fsevents@2.3.2: - resolution: - { - integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==, - } - engines: { node: ^8.16.0 || ^10.6.0 || >=11.0.0 } + resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==} + engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} os: [darwin] function-bind@1.1.2: - resolution: - { - integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==, - } + resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} function.prototype.name@1.1.8: - resolution: - { - integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==} + engines: {node: '>= 0.4'} functions-have-names@1.2.3: - resolution: - { - integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==, - } + resolution: {integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==} gaxios@6.7.1: - resolution: - { - integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==} + engines: {node: '>=14'} gcp-metadata@6.1.1: - resolution: - { - integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==} + engines: {node: '>=14'} + + get-east-asian-width@1.3.0: + resolution: {integrity: sha512-vpeMIQKxczTD/0s2CdEWHcb0eeJe6TFjxb+J5xgX7hScxqrGuyjmv4c1D4A/gelKfyox0gJJwIHF+fLjeaM8kQ==} + engines: {node: '>=18'} get-intrinsic@1.3.0: - resolution: - { - integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==} + engines: {node: '>= 0.4'} get-proto@1.0.1: - resolution: - { - integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==} + engines: {node: '>= 0.4'} get-symbol-description@1.1.0: - resolution: - { - integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==} + engines: {node: '>= 0.4'} glob-parent@5.1.2: - resolution: - { - integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==, - } - engines: { node: ">= 6" } + resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} + engines: {node: '>= 6'} glob-parent@6.0.2: - resolution: - { - integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==, - } - engines: { node: ">=10.13.0" } + resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} + engines: {node: '>=10.13.0'} glob@7.2.3: - resolution: - { - integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==, - } + resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} deprecated: Glob versions prior to v9 are no longer supported globals@14.0.0: - resolution: - { - integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==} + engines: {node: '>=18'} globals@16.2.0: - resolution: - { - integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==} + engines: {node: '>=18'} globalthis@1.0.4: - resolution: - { - integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==} + engines: {node: '>= 0.4'} google-auth-library@9.15.1: - resolution: - { - integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==} + engines: {node: '>=14'} google-logging-utils@0.0.2: - resolution: - { - integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==} + engines: {node: '>=14'} gopd@1.2.0: - resolution: - { - integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==} + engines: {node: '>= 0.4'} graphemer@1.4.0: - resolution: - { - integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==, - } + resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} gtoken@7.1.0: - resolution: - { - integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==, - } - engines: { node: ">=14.0.0" } + resolution: {integrity: sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==} + engines: {node: '>=14.0.0'} has-bigints@1.1.0: - resolution: - { - integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==} + engines: {node: '>= 0.4'} has-flag@4.0.0: - resolution: - { - integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} + engines: {node: '>=8'} has-property-descriptors@1.0.2: - resolution: - { - integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==, - } + resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} has-proto@1.2.0: - resolution: - { - integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==} + engines: {node: '>= 0.4'} has-symbols@1.1.0: - resolution: - { - integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==} + engines: {node: '>= 0.4'} has-tostringtag@1.0.2: - resolution: - { - integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==} + engines: {node: '>= 0.4'} hasown@2.0.2: - resolution: - { - integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} + engines: {node: '>= 0.4'} help-me@5.0.0: - resolution: - { - integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==, - } + resolution: {integrity: sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==} http-errors@2.0.0: - resolution: - { - integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==} + engines: {node: '>= 0.8'} https-proxy-agent@7.0.6: - resolution: - { - integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==, - } - engines: { node: ">= 14" } + resolution: {integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==} + engines: {node: '>= 14'} humanize-ms@1.2.1: - resolution: - { - integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==, - } + resolution: {integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==} husky@9.1.7: - resolution: - { - integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==} + engines: {node: '>=18'} hasBin: true iconv-lite@0.6.3: - resolution: - { - integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} + engines: {node: '>=0.10.0'} ignore@5.3.2: - resolution: - { - integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==, - } - engines: { node: ">= 4" } + resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} + engines: {node: '>= 4'} ignore@7.0.5: - resolution: - { - integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==, - } - engines: { node: ">= 4" } + resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==} + engines: {node: '>= 4'} import-fresh@3.3.1: - resolution: - { - integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==} + engines: {node: '>=6'} imurmurhash@0.1.4: - resolution: - { - integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==, - } - engines: { node: ">=0.8.19" } + resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} + engines: {node: '>=0.8.19'} inflight@1.0.6: - resolution: - { - integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==, - } + resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. inherits@2.0.4: - resolution: - { - integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==, - } + resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} internal-slot@1.1.0: - resolution: - { - integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==} + engines: {node: '>= 0.4'} interpret@1.4.0: - resolution: - { - integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==} + engines: {node: '>= 0.10'} ipaddr.js@1.9.1: - resolution: - { - integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==} + engines: {node: '>= 0.10'} is-array-buffer@3.0.5: - resolution: - { - integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==} + engines: {node: '>= 0.4'} is-async-function@2.1.1: - resolution: - { - integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==} + engines: {node: '>= 0.4'} is-bigint@1.1.0: - resolution: - { - integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==} + engines: {node: '>= 0.4'} is-boolean-object@1.2.2: - resolution: - { - integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==} + engines: {node: '>= 0.4'} is-callable@1.2.7: - resolution: - { - integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==} + engines: {node: '>= 0.4'} is-core-module@2.16.1: - resolution: - { - integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==} + engines: {node: '>= 0.4'} is-data-view@1.0.2: - resolution: - { - integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==} + engines: {node: '>= 0.4'} is-date-object@1.1.0: - resolution: - { - integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==} + engines: {node: '>= 0.4'} is-extglob@2.1.1: - resolution: - { - integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} + engines: {node: '>=0.10.0'} is-finalizationregistry@1.1.1: - resolution: - { - integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==} + engines: {node: '>= 0.4'} + + is-fullwidth-code-point@4.0.0: + resolution: {integrity: sha512-O4L094N2/dZ7xqVdrXhh9r1KODPJpFms8B5sGdJLPy664AgvXsreZUyCQQNItZRDlYug4xStLjNp/sz3HvBowQ==} + engines: {node: '>=12'} + + is-fullwidth-code-point@5.0.0: + resolution: {integrity: sha512-OVa3u9kkBbw7b8Xw5F9P+D/T9X+Z4+JruYVNapTjPYZYUznQ5YfWeFkOj606XYYW8yugTfC8Pj0hYqvi4ryAhA==} + engines: {node: '>=18'} is-generator-function@1.1.0: - resolution: - { - integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==} + engines: {node: '>= 0.4'} is-glob@4.0.3: - resolution: - { - integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} + engines: {node: '>=0.10.0'} is-map@2.0.3: - resolution: - { - integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==} + engines: {node: '>= 0.4'} is-negative-zero@2.0.3: - resolution: - { - integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} + engines: {node: '>= 0.4'} is-number-object@1.1.1: - resolution: - { - integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==} + engines: {node: '>= 0.4'} is-number@7.0.0: - resolution: - { - integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==, - } - engines: { node: ">=0.12.0" } + resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} + engines: {node: '>=0.12.0'} is-promise@4.0.0: - resolution: - { - integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==, - } + resolution: {integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==} is-regex@1.2.1: - resolution: - { - integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==} + engines: {node: '>= 0.4'} is-set@2.0.3: - resolution: - { - integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==} + engines: {node: '>= 0.4'} is-shared-array-buffer@1.0.4: - resolution: - { - integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==} + engines: {node: '>= 0.4'} is-stream@2.0.1: - resolution: - { - integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==} + engines: {node: '>=8'} is-string@1.1.1: - resolution: - { - integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==} + engines: {node: '>= 0.4'} is-symbol@1.1.1: - resolution: - { - integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==} + engines: {node: '>= 0.4'} is-typed-array@1.1.15: - resolution: - { - integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==} + engines: {node: '>= 0.4'} is-weakmap@2.0.2: - resolution: - { - integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==} + engines: {node: '>= 0.4'} is-weakref@1.1.1: - resolution: - { - integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==} + engines: {node: '>= 0.4'} is-weakset@2.0.4: - resolution: - { - integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==} + engines: {node: '>= 0.4'} isarray@2.0.5: - resolution: - { - integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==, - } + resolution: {integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==} isexe@2.0.0: - resolution: - { - integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==, - } + resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} iterator.prototype@1.1.5: - resolution: - { - integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==} + engines: {node: '>= 0.4'} joycon@3.1.1: - resolution: - { - integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==} + engines: {node: '>=10'} js-tokens@4.0.0: - resolution: - { - integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==, - } + resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} js-yaml@4.1.0: - resolution: - { - integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==, - } + resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} hasBin: true json-bigint@1.0.0: - resolution: - { - integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==, - } + resolution: {integrity: sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==} json-buffer@3.0.1: - resolution: - { - integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==, - } + resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==} json-schema-traverse@0.4.1: - resolution: - { - integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==, - } + resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==} json-schema@0.4.0: - resolution: - { - integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==, - } + resolution: {integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==} json-stable-stringify-without-jsonify@1.0.1: - resolution: - { - integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==, - } + resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} jsondiffpatch@0.6.0: - resolution: - { - integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==, - } - engines: { node: ^18.0.0 || >=20.0.0 } + resolution: {integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==} + engines: {node: ^18.0.0 || >=20.0.0} hasBin: true jsx-ast-utils@3.3.5: - resolution: - { - integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==, - } - engines: { node: ">=4.0" } + resolution: {integrity: sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==} + engines: {node: '>=4.0'} jwa@2.0.1: - resolution: - { - integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==, - } + resolution: {integrity: sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==} jws@4.0.0: - resolution: - { - integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==, - } + resolution: {integrity: sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==} keyv@4.5.4: - resolution: - { - integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==, - } + resolution: {integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==} levn@0.4.1: - resolution: - { - integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} + engines: {node: '>= 0.8.0'} + + lilconfig@3.1.3: + resolution: {integrity: sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==} + engines: {node: '>=14'} + + lint-staged@16.1.2: + resolution: {integrity: sha512-sQKw2Si2g9KUZNY3XNvRuDq4UJqpHwF0/FQzZR2M7I5MvtpWvibikCjUVJzZdGE0ByurEl3KQNvsGetd1ty1/Q==} + engines: {node: '>=20.17'} + hasBin: true + + listr2@8.3.3: + resolution: {integrity: sha512-LWzX2KsqcB1wqQ4AHgYb4RsDXauQiqhjLk+6hjbaeHG4zpjjVAB6wC/gz6X0l+Du1cN3pUB5ZlrvTbhGSNnUQQ==} + engines: {node: '>=18.0.0'} locate-path@6.0.0: - resolution: - { - integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} + engines: {node: '>=10'} lodash.merge@4.6.2: - resolution: - { - integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==, - } + resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} + + log-update@6.1.0: + resolution: {integrity: sha512-9ie8ItPR6tjY5uYJh8K/Zrv/RMZ5VOlOWvtZdEHYSTFKZfIBPQa9tOAEeAWhd+AnIneLJ22w5fjOYtoutpWq5w==} + engines: {node: '>=18'} loose-envify@1.4.0: - resolution: - { - integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==, - } + resolution: {integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==} hasBin: true math-intrinsics@1.1.0: - resolution: - { - integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} + engines: {node: '>= 0.4'} media-typer@1.1.0: - resolution: - { - integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==} + engines: {node: '>= 0.8'} merge-descriptors@2.0.0: - resolution: - { - integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==} + engines: {node: '>=18'} merge2@1.4.1: - resolution: - { - integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==, - } - engines: { node: ">= 8" } + resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} + engines: {node: '>= 8'} micromatch@4.0.8: - resolution: - { - integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==, - } - engines: { node: ">=8.6" } + resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} + engines: {node: '>=8.6'} mime-db@1.52.0: - resolution: - { - integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} + engines: {node: '>= 0.6'} mime-db@1.54.0: - resolution: - { - integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==} + engines: {node: '>= 0.6'} mime-types@2.1.35: - resolution: - { - integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==} + engines: {node: '>= 0.6'} mime-types@3.0.1: - resolution: - { - integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==} + engines: {node: '>= 0.6'} + + mimic-function@5.0.1: + resolution: {integrity: sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==} + engines: {node: '>=18'} minimatch@3.1.2: - resolution: - { - integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==, - } + resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} minimatch@9.0.5: - resolution: - { - integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==, - } - engines: { node: ">=16 || 14 >=14.17" } + resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} + engines: {node: '>=16 || 14 >=14.17'} minimist@1.2.8: - resolution: - { - integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==, - } + resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} ms@2.1.3: - resolution: - { - integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, - } + resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} + + nano-spawn@1.0.2: + resolution: {integrity: sha512-21t+ozMQDAL/UGgQVBbZ/xXvNO10++ZPuTmKRO8k9V3AClVRht49ahtDjfY8l1q6nSHOrE5ASfthzH3ol6R/hg==} + engines: {node: '>=20.17'} nanoid@3.3.11: - resolution: - { - integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==, - } - engines: { node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1 } + resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==} + engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} hasBin: true natural-compare@1.4.0: - resolution: - { - integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==, - } + resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} negotiator@1.0.0: - resolution: - { - integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==} + engines: {node: '>= 0.6'} node-domexception@1.0.0: - resolution: - { - integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==, - } - engines: { node: ">=10.5.0" } + resolution: {integrity: sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==} + engines: {node: '>=10.5.0'} node-fetch@2.7.0: - resolution: - { - integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==, - } - engines: { node: 4.x || >=6.0.0 } + resolution: {integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==} + engines: {node: 4.x || >=6.0.0} peerDependencies: encoding: ^0.1.0 peerDependenciesMeta: @@ -2046,60 +1275,36 @@ packages: optional: true object-assign@4.1.1: - resolution: - { - integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} + engines: {node: '>=0.10.0'} object-inspect@1.13.4: - resolution: - { - integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==} + engines: {node: '>= 0.4'} object-keys@1.1.1: - resolution: - { - integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} + engines: {node: '>= 0.4'} object.assign@4.1.7: - resolution: - { - integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==} + engines: {node: '>= 0.4'} object.entries@1.1.9: - resolution: - { - integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==} + engines: {node: '>= 0.4'} object.fromentries@2.0.8: - resolution: - { - integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==} + engines: {node: '>= 0.4'} object.values@1.2.1: - resolution: - { - integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==} + engines: {node: '>= 0.4'} ollama-ai-provider@1.2.0: - resolution: - { - integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==} + engines: {node: '>=18'} peerDependencies: zod: ^3.0.0 peerDependenciesMeta: @@ -2107,30 +1312,22 @@ packages: optional: true on-exit-leak-free@2.1.2: - resolution: - { - integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==, - } - engines: { node: ">=14.0.0" } + resolution: {integrity: sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==} + engines: {node: '>=14.0.0'} on-finished@2.4.1: - resolution: - { - integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==} + engines: {node: '>= 0.8'} once@1.4.0: - resolution: - { - integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==, - } + resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==} + + onetime@7.0.0: + resolution: {integrity: sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==} + engines: {node: '>=18'} openai@4.104.0: - resolution: - { - integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==, - } + resolution: {integrity: sha512-p99EFNsA/yX6UhVO93f5kJsDRLAg+CTA2RBqdHK4RtK8u5IJw32Hyb2dTGKbnnFmnuoBv5r7Z2CURI9sGZpSuA==} hasBin: true peerDependencies: ws: ^8.18.0 @@ -2142,972 +1339,655 @@ packages: optional: true optionator@0.9.4: - resolution: - { - integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} + engines: {node: '>= 0.8.0'} own-keys@1.0.1: - resolution: - { - integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==} + engines: {node: '>= 0.4'} p-limit@3.1.0: - resolution: - { - integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} + engines: {node: '>=10'} p-locate@5.0.0: - resolution: - { - integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} + engines: {node: '>=10'} parent-module@1.0.1: - resolution: - { - integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} + engines: {node: '>=6'} parseurl@1.3.3: - resolution: - { - integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==} + engines: {node: '>= 0.8'} partial-json@0.1.7: - resolution: - { - integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==, - } + resolution: {integrity: sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==} path-exists@4.0.0: - resolution: - { - integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} + engines: {node: '>=8'} path-is-absolute@1.0.1: - resolution: - { - integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} + engines: {node: '>=0.10.0'} path-key@3.1.1: - resolution: - { - integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==} + engines: {node: '>=8'} path-parse@1.0.7: - resolution: - { - integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==, - } + resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} path-to-regexp@8.2.0: - resolution: - { - integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==, - } - engines: { node: ">=16" } + resolution: {integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==} + engines: {node: '>=16'} picomatch@2.3.1: - resolution: - { - integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==, - } - engines: { node: ">=8.6" } + resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} + engines: {node: '>=8.6'} + + pidtree@0.6.0: + resolution: {integrity: sha512-eG2dWTVw5bzqGRztnHExczNxt5VGsE6OwTeCG3fdUf9KBsZzO3R5OIIIzWR+iZA0NtZ+RDVdaoE2dK1cn6jH4g==} + engines: {node: '>=0.10'} + hasBin: true pino-abstract-transport@2.0.0: - resolution: - { - integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==, - } + resolution: {integrity: sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==} pino-pretty@13.0.0: - resolution: - { - integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==, - } + resolution: {integrity: sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==} hasBin: true pino-std-serializers@7.0.0: - resolution: - { - integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==, - } + resolution: {integrity: sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==} pino@9.7.0: - resolution: - { - integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==, - } + resolution: {integrity: sha512-vnMCM6xZTb1WDmLvtG2lE/2p+t9hDEIvTWJsu6FejkE62vB7gDhvzrpFR4Cw2to+9JNQxVnkAKVPA1KPB98vWg==} hasBin: true pkce-challenge@5.0.0: - resolution: - { - integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==, - } - engines: { node: ">=16.20.0" } + resolution: {integrity: sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==} + engines: {node: '>=16.20.0'} playwright-core@1.53.1: - resolution: - { - integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==} + engines: {node: '>=18'} hasBin: true playwright@1.53.1: - resolution: - { - integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==} + engines: {node: '>=18'} hasBin: true possible-typed-array-names@1.1.0: - resolution: - { - integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==} + engines: {node: '>= 0.4'} prelude-ls@1.2.1: - resolution: - { - integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} + engines: {node: '>= 0.8.0'} prettier@3.6.1: - resolution: - { - integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==, - } - engines: { node: ">=14" } + resolution: {integrity: sha512-5xGWRa90Sp2+x1dQtNpIpeOQpTDBs9cZDmA/qs2vDNN2i18PdapqY7CmBeyLlMuGqXJRIOPaCaVZTLNQRWUH/A==} + engines: {node: '>=14'} hasBin: true process-warning@5.0.0: - resolution: - { - integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==, - } + resolution: {integrity: sha512-a39t9ApHNx2L4+HBnQKqxxHNs1r7KF+Intd8Q/g1bUh6q0WIp9voPXJ/x0j+ZL45KF1pJd9+q2jLIRMfvEshkA==} prop-types@15.8.1: - resolution: - { - integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==, - } + resolution: {integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==} proxy-addr@2.0.7: - resolution: - { - integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==} + engines: {node: '>= 0.10'} pump@3.0.3: - resolution: - { - integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==, - } + resolution: {integrity: sha512-todwxLMY7/heScKmntwQG8CXVkWUOdYxIvY2s0VWAAMh/nd8SoYiRaKjlr7+iCs984f2P8zvrfWcDDYVb73NfA==} punycode@2.3.1: - resolution: - { - integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} + engines: {node: '>=6'} qs@6.14.0: - resolution: - { - integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==, - } - engines: { node: ">=0.6" } + resolution: {integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==} + engines: {node: '>=0.6'} queue-microtask@1.2.3: - resolution: - { - integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==, - } + resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} quick-format-unescaped@4.0.4: - resolution: - { - integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==, - } + resolution: {integrity: sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==} range-parser@1.2.1: - resolution: - { - integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==} + engines: {node: '>= 0.6'} raw-body@3.0.0: - resolution: - { - integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==} + engines: {node: '>= 0.8'} react-is@16.13.1: - resolution: - { - integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==, - } + resolution: {integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==} react@19.1.0: - resolution: - { - integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==} + engines: {node: '>=0.10.0'} real-require@0.2.0: - resolution: - { - integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==, - } - engines: { node: ">= 12.13.0" } + resolution: {integrity: sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==} + engines: {node: '>= 12.13.0'} rechoir@0.6.2: - resolution: - { - integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==, - } - engines: { node: ">= 0.10" } + resolution: {integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==} + engines: {node: '>= 0.10'} reflect.getprototypeof@1.0.10: - resolution: - { - integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==} + engines: {node: '>= 0.4'} regexp.prototype.flags@1.5.4: - resolution: - { - integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==} + engines: {node: '>= 0.4'} resolve-from@4.0.0: - resolution: - { - integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==, - } - engines: { node: ">=4" } + resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} + engines: {node: '>=4'} resolve@1.22.10: - resolution: - { - integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} + engines: {node: '>= 0.4'} hasBin: true resolve@2.0.0-next.5: - resolution: - { - integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==, - } + resolution: {integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==} hasBin: true + restore-cursor@5.1.0: + resolution: {integrity: sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==} + engines: {node: '>=18'} + reusify@1.1.0: - resolution: - { - integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==, - } - engines: { iojs: ">=1.0.0", node: ">=0.10.0" } + resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} + engines: {iojs: '>=1.0.0', node: '>=0.10.0'} + + rfdc@1.4.1: + resolution: {integrity: sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==} router@2.2.0: - resolution: - { - integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==} + engines: {node: '>= 18'} run-parallel@1.2.0: - resolution: - { - integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==, - } + resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} safe-array-concat@1.1.3: - resolution: - { - integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==, - } - engines: { node: ">=0.4" } + resolution: {integrity: sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==} + engines: {node: '>=0.4'} safe-buffer@5.2.1: - resolution: - { - integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==, - } + resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} safe-push-apply@1.0.0: - resolution: - { - integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==} + engines: {node: '>= 0.4'} safe-regex-test@1.1.0: - resolution: - { - integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==} + engines: {node: '>= 0.4'} safe-stable-stringify@2.5.0: - resolution: - { - integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==} + engines: {node: '>=10'} safer-buffer@2.1.2: - resolution: - { - integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==, - } + resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} secure-json-parse@2.7.0: - resolution: - { - integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==, - } + resolution: {integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==} semver@6.3.1: - resolution: - { - integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==, - } + resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} hasBin: true semver@7.7.2: - resolution: - { - integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==} + engines: {node: '>=10'} hasBin: true send@1.2.0: - resolution: - { - integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==} + engines: {node: '>= 18'} serve-static@2.2.0: - resolution: - { - integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==, - } - engines: { node: ">= 18" } + resolution: {integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==} + engines: {node: '>= 18'} set-cookie-parser@2.7.1: - resolution: - { - integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==, - } + resolution: {integrity: sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==} set-function-length@1.2.2: - resolution: - { - integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==} + engines: {node: '>= 0.4'} set-function-name@2.0.2: - resolution: - { - integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==} + engines: {node: '>= 0.4'} set-proto@1.0.0: - resolution: - { - integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==} + engines: {node: '>= 0.4'} setprototypeof@1.2.0: - resolution: - { - integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==, - } + resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} shebang-command@2.0.0: - resolution: - { - integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==} + engines: {node: '>=8'} shebang-regex@3.0.0: - resolution: - { - integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==} + engines: {node: '>=8'} shelljs@0.8.5: - resolution: - { - integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==, - } - engines: { node: ">=4" } + resolution: {integrity: sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==} + engines: {node: '>=4'} hasBin: true shx@0.3.4: - resolution: - { - integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==, - } - engines: { node: ">=6" } + resolution: {integrity: sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==} + engines: {node: '>=6'} hasBin: true side-channel-list@1.0.0: - resolution: - { - integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==} + engines: {node: '>= 0.4'} side-channel-map@1.0.1: - resolution: - { - integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==} + engines: {node: '>= 0.4'} side-channel-weakmap@1.0.2: - resolution: - { - integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==} + engines: {node: '>= 0.4'} side-channel@1.1.0: - resolution: - { - integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==} + engines: {node: '>= 0.4'} + + signal-exit@4.1.0: + resolution: {integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==} + engines: {node: '>=14'} + + slice-ansi@5.0.0: + resolution: {integrity: sha512-FC+lgizVPfie0kkhqUScwRu1O/lF6NOgJmlCgK+/LYxDCTk8sGelYaHDhFcDN+Sn3Cv+3VSa4Byeo+IMCzpMgQ==} + engines: {node: '>=12'} + + slice-ansi@7.1.0: + resolution: {integrity: sha512-bSiSngZ/jWeX93BqeIAbImyTbEihizcwNjFoRUIY/T1wWQsfsm2Vw1agPKylXvQTU7iASGdHhyqRlqQzfz+Htg==} + engines: {node: '>=18'} sonic-boom@4.2.0: - resolution: - { - integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==, - } + resolution: {integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==} split2@4.2.0: - resolution: - { - integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==, - } - engines: { node: ">= 10.x" } + resolution: {integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==} + engines: {node: '>= 10.x'} statuses@2.0.1: - resolution: - { - integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==} + engines: {node: '>= 0.8'} statuses@2.0.2: - resolution: - { - integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==} + engines: {node: '>= 0.8'} stop-iteration-iterator@1.1.0: - resolution: - { - integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==} + engines: {node: '>= 0.4'} + + string-argv@0.3.2: + resolution: {integrity: sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==} + engines: {node: '>=0.6.19'} + + string-width@7.2.0: + resolution: {integrity: sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==} + engines: {node: '>=18'} string.prototype.matchall@4.0.12: - resolution: - { - integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==} + engines: {node: '>= 0.4'} string.prototype.repeat@1.0.0: - resolution: - { - integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==, - } + resolution: {integrity: sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==} string.prototype.trim@1.2.10: - resolution: - { - integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==} + engines: {node: '>= 0.4'} string.prototype.trimend@1.0.9: - resolution: - { - integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==} + engines: {node: '>= 0.4'} string.prototype.trimstart@1.0.8: - resolution: - { - integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==} + engines: {node: '>= 0.4'} + + strip-ansi@7.1.0: + resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==} + engines: {node: '>=12'} strip-json-comments@3.1.1: - resolution: - { - integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} + engines: {node: '>=8'} supports-color@7.2.0: - resolution: - { - integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==, - } - engines: { node: ">=8" } + resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} + engines: {node: '>=8'} supports-preserve-symlinks-flag@1.0.0: - resolution: - { - integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} + engines: {node: '>= 0.4'} swr@2.3.3: - resolution: - { - integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==, - } + resolution: {integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==} peerDependencies: react: ^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 thread-stream@3.1.0: - resolution: - { - integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==, - } + resolution: {integrity: sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==} throttleit@2.1.0: - resolution: - { - integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==, - } - engines: { node: ">=18" } + resolution: {integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==} + engines: {node: '>=18'} tldts-core@6.1.86: - resolution: - { - integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==, - } + resolution: {integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==} tldts@6.1.86: - resolution: - { - integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==, - } + resolution: {integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==} hasBin: true to-regex-range@5.0.1: - resolution: - { - integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==, - } - engines: { node: ">=8.0" } + resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} + engines: {node: '>=8.0'} toidentifier@1.0.1: - resolution: - { - integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==, - } - engines: { node: ">=0.6" } + resolution: {integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==} + engines: {node: '>=0.6'} tough-cookie@5.1.2: - resolution: - { - integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==, - } - engines: { node: ">=16" } + resolution: {integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==} + engines: {node: '>=16'} tr46@0.0.3: - resolution: - { - integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==, - } + resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} ts-api-utils@2.1.0: - resolution: - { - integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==, - } - engines: { node: ">=18.12" } + resolution: {integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==} + engines: {node: '>=18.12'} peerDependencies: - typescript: ">=4.8.4" + typescript: '>=4.8.4' type-check@0.4.0: - resolution: - { - integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==, - } - engines: { node: ">= 0.8.0" } + resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} + engines: {node: '>= 0.8.0'} type-is@2.0.1: - resolution: - { - integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==, - } - engines: { node: ">= 0.6" } + resolution: {integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==} + engines: {node: '>= 0.6'} typed-array-buffer@1.0.3: - resolution: - { - integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==} + engines: {node: '>= 0.4'} typed-array-byte-length@1.0.3: - resolution: - { - integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==} + engines: {node: '>= 0.4'} typed-array-byte-offset@1.0.4: - resolution: - { - integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==} + engines: {node: '>= 0.4'} typed-array-length@1.0.7: - resolution: - { - integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==} + engines: {node: '>= 0.4'} typescript-eslint@8.35.0: - resolution: - { - integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==, - } - engines: { node: ^18.18.0 || ^20.9.0 || >=21.1.0 } + resolution: {integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 - typescript: ">=4.8.4 <5.9.0" + typescript: '>=4.8.4 <5.9.0' typescript@5.8.3: - resolution: - { - integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==, - } - engines: { node: ">=14.17" } + resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} + engines: {node: '>=14.17'} hasBin: true unbox-primitive@1.1.0: - resolution: - { - integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==} + engines: {node: '>= 0.4'} undici-types@5.26.5: - resolution: - { - integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==, - } + resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} unpipe@1.0.0: - resolution: - { - integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==} + engines: {node: '>= 0.8'} uri-js@4.4.1: - resolution: - { - integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==, - } + resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} use-sync-external-store@1.5.0: - resolution: - { - integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==, - } + resolution: {integrity: sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==} peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 uuid@9.0.1: - resolution: - { - integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==, - } + resolution: {integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==} hasBin: true vary@1.1.2: - resolution: - { - integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==, - } - engines: { node: ">= 0.8" } + resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} + engines: {node: '>= 0.8'} web-streams-polyfill@4.0.0-beta.3: - resolution: - { - integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==, - } - engines: { node: ">= 14" } + resolution: {integrity: sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==} + engines: {node: '>= 14'} webidl-conversions@3.0.1: - resolution: - { - integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==, - } + resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==} whatwg-url@5.0.0: - resolution: - { - integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==, - } + resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} which-boxed-primitive@1.1.1: - resolution: - { - integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==} + engines: {node: '>= 0.4'} which-builtin-type@1.2.1: - resolution: - { - integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==} + engines: {node: '>= 0.4'} which-collection@1.0.2: - resolution: - { - integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} + engines: {node: '>= 0.4'} which-typed-array@1.1.19: - resolution: - { - integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==, - } - engines: { node: ">= 0.4" } + resolution: {integrity: sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==} + engines: {node: '>= 0.4'} which@2.0.2: - resolution: - { - integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==, - } - engines: { node: ">= 8" } + resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} + engines: {node: '>= 8'} hasBin: true word-wrap@1.2.5: - resolution: - { - integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==, - } - engines: { node: ">=0.10.0" } + resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} + engines: {node: '>=0.10.0'} + + wrap-ansi@9.0.0: + resolution: {integrity: sha512-G8ura3S+3Z2G+mkgNRq8dqaFZAuxfsxpBB8OCTGRTCtp+l/v9nbFNmCUP1BZMts3G1142MsZfn6eeUKrr4PD1Q==} + engines: {node: '>=18'} wrappy@1.0.2: - resolution: - { - integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==, - } + resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==} ws@8.18.2: - resolution: - { - integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==, - } - engines: { node: ">=10.0.0" } + resolution: {integrity: sha512-DMricUmwGZUVr++AEAe2uiVM7UoO9MAVZMDu05UQOaUII0lp+zOzLLU4Xqh/JvTqklB1T4uELaaPBKyjE1r4fQ==} + engines: {node: '>=10.0.0'} peerDependencies: bufferutil: ^4.0.1 - utf-8-validate: ">=5.0.2" + utf-8-validate: '>=5.0.2' peerDependenciesMeta: bufferutil: optional: true utf-8-validate: optional: true + yaml@2.8.0: + resolution: {integrity: sha512-4lLa/EcQCB0cJkyts+FpIRx5G/llPxfP6VQU5KByHEhLxY3IJCH0f0Hy1MHI8sClTvsIb8qwRJ6R/ZdlDJ/leQ==} + engines: {node: '>= 14.6'} + hasBin: true + yocto-queue@0.1.0: - resolution: - { - integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==, - } - engines: { node: ">=10" } + resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} + engines: {node: '>=10'} zod-to-json-schema@3.24.6: - resolution: - { - integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==, - } + resolution: {integrity: sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==} peerDependencies: zod: ^3.24.1 zod@3.25.67: - resolution: - { - integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==, - } + resolution: {integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==} snapshots: - "@ai-sdk/anthropic@1.2.12(zod@3.25.67)": + + '@ai-sdk/anthropic@1.2.12(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/azure@1.3.23(zod@3.25.67)": + '@ai-sdk/azure@1.3.23(zod@3.25.67)': dependencies: - "@ai-sdk/openai": 1.3.22(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai': 1.3.22(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/cerebras@0.2.14(zod@3.25.67)": + '@ai-sdk/cerebras@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/deepseek@0.2.14(zod@3.25.67)": + '@ai-sdk/deepseek@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/google@1.2.19(zod@3.25.67)": + '@ai-sdk/google@1.2.19(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/groq@1.2.9(zod@3.25.67)": + '@ai-sdk/groq@1.2.9(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/mistral@1.2.8(zod@3.25.67)": + '@ai-sdk/mistral@1.2.8(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)": + '@ai-sdk/openai-compatible@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/openai@1.3.22(zod@3.25.67)": + '@ai-sdk/openai@1.3.22(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/perplexity@1.1.9(zod@3.25.67)": + '@ai-sdk/perplexity@1.1.9(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/provider-utils@2.2.8(zod@3.25.67)": + '@ai-sdk/provider-utils@2.2.8(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 + '@ai-sdk/provider': 1.1.3 nanoid: 3.3.11 secure-json-parse: 2.7.0 zod: 3.25.67 - "@ai-sdk/provider@1.1.3": + '@ai-sdk/provider@1.1.3': dependencies: json-schema: 0.4.0 - "@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)": + '@ai-sdk/react@1.2.12(react@19.1.0)(zod@3.25.67)': dependencies: - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) - "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + '@ai-sdk/ui-utils': 1.2.11(zod@3.25.67) react: 19.1.0 swr: 2.3.3(react@19.1.0) throttleit: 2.1.0 optionalDependencies: zod: 3.25.67 - "@ai-sdk/togetherai@0.2.14(zod@3.25.67)": + '@ai-sdk/togetherai@0.2.14(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@ai-sdk/ui-utils@1.2.11(zod@3.25.67)": + '@ai-sdk/ui-utils@1.2.11(zod@3.25.67)': dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 zod-to-json-schema: 3.24.6(zod@3.25.67) - "@ai-sdk/xai@1.2.16(zod@3.25.67)": + '@ai-sdk/xai@1.2.16(zod@3.25.67)': dependencies: - "@ai-sdk/openai-compatible": 0.2.14(zod@3.25.67) - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/openai-compatible': 0.2.14(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) zod: 3.25.67 optional: true - "@anthropic-ai/sdk@0.39.0": + '@anthropic-ai/sdk@0.39.0': dependencies: - "@types/node": 18.19.112 - "@types/node-fetch": 2.6.12 + '@types/node': 18.19.112 + '@types/node-fetch': 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -3116,10 +1996,10 @@ snapshots: transitivePeerDependencies: - encoding - "@browserbasehq/sdk@2.6.0": + '@browserbasehq/sdk@2.6.0': dependencies: - "@types/node": 18.19.112 - "@types/node-fetch": 2.6.12 + '@types/node': 18.19.112 + '@types/node-fetch': 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -3128,11 +2008,11 @@ snapshots: transitivePeerDependencies: - encoding - "@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)": + '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)': dependencies: - "@anthropic-ai/sdk": 0.39.0 - "@browserbasehq/sdk": 2.6.0 - "@google/genai": 0.8.0 + '@anthropic-ai/sdk': 0.39.0 + '@browserbasehq/sdk': 2.6.0 + '@google/genai': 0.8.0 ai: 4.3.16(react@19.1.0)(zod@3.25.67) deepmerge: 4.3.1 devtools-protocol: 0.0.1464554 @@ -3146,17 +2026,17 @@ snapshots: zod: 3.25.67 zod-to-json-schema: 3.24.6(zod@3.25.67) optionalDependencies: - "@ai-sdk/anthropic": 1.2.12(zod@3.25.67) - "@ai-sdk/azure": 1.3.23(zod@3.25.67) - "@ai-sdk/cerebras": 0.2.14(zod@3.25.67) - "@ai-sdk/deepseek": 0.2.14(zod@3.25.67) - "@ai-sdk/google": 1.2.19(zod@3.25.67) - "@ai-sdk/groq": 1.2.9(zod@3.25.67) - "@ai-sdk/mistral": 1.2.8(zod@3.25.67) - "@ai-sdk/openai": 1.3.22(zod@3.25.67) - "@ai-sdk/perplexity": 1.1.9(zod@3.25.67) - "@ai-sdk/togetherai": 0.2.14(zod@3.25.67) - "@ai-sdk/xai": 1.2.16(zod@3.25.67) + '@ai-sdk/anthropic': 1.2.12(zod@3.25.67) + '@ai-sdk/azure': 1.3.23(zod@3.25.67) + '@ai-sdk/cerebras': 0.2.14(zod@3.25.67) + '@ai-sdk/deepseek': 0.2.14(zod@3.25.67) + '@ai-sdk/google': 1.2.19(zod@3.25.67) + '@ai-sdk/groq': 1.2.9(zod@3.25.67) + '@ai-sdk/mistral': 1.2.8(zod@3.25.67) + '@ai-sdk/openai': 1.3.22(zod@3.25.67) + '@ai-sdk/perplexity': 1.1.9(zod@3.25.67) + '@ai-sdk/togetherai': 0.2.14(zod@3.25.67) + '@ai-sdk/xai': 1.2.16(zod@3.25.67) ollama-ai-provider: 1.2.0(zod@3.25.67) transitivePeerDependencies: - bufferutil @@ -3165,32 +2045,32 @@ snapshots: - supports-color - utf-8-validate - "@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)": + '@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)': dependencies: eslint: 9.29.0 eslint-visitor-keys: 3.4.3 - "@eslint-community/regexpp@4.12.1": {} + '@eslint-community/regexpp@4.12.1': {} - "@eslint/config-array@0.20.1": + '@eslint/config-array@0.20.1': dependencies: - "@eslint/object-schema": 2.1.6 + '@eslint/object-schema': 2.1.6 debug: 4.4.1 minimatch: 3.1.2 transitivePeerDependencies: - supports-color - "@eslint/config-helpers@0.2.3": {} + '@eslint/config-helpers@0.2.3': {} - "@eslint/core@0.14.0": + '@eslint/core@0.14.0': dependencies: - "@types/json-schema": 7.0.15 + '@types/json-schema': 7.0.15 - "@eslint/core@0.15.1": + '@eslint/core@0.15.1': dependencies: - "@types/json-schema": 7.0.15 + '@types/json-schema': 7.0.15 - "@eslint/eslintrc@3.3.1": + '@eslint/eslintrc@3.3.1': dependencies: ajv: 6.12.6 debug: 4.4.1 @@ -3204,16 +2084,16 @@ snapshots: transitivePeerDependencies: - supports-color - "@eslint/js@9.29.0": {} + '@eslint/js@9.29.0': {} - "@eslint/object-schema@2.1.6": {} + '@eslint/object-schema@2.1.6': {} - "@eslint/plugin-kit@0.3.3": + '@eslint/plugin-kit@0.3.3': dependencies: - "@eslint/core": 0.15.1 + '@eslint/core': 0.15.1 levn: 0.4.1 - "@google/genai@0.8.0": + '@google/genai@0.8.0': dependencies: google-auth-library: 9.15.1 ws: 8.18.2 @@ -3223,20 +2103,20 @@ snapshots: - supports-color - utf-8-validate - "@humanfs/core@0.19.1": {} + '@humanfs/core@0.19.1': {} - "@humanfs/node@0.16.6": + '@humanfs/node@0.16.6': dependencies: - "@humanfs/core": 0.19.1 - "@humanwhocodes/retry": 0.3.1 + '@humanfs/core': 0.19.1 + '@humanwhocodes/retry': 0.3.1 - "@humanwhocodes/module-importer@1.0.1": {} + '@humanwhocodes/module-importer@1.0.1': {} - "@humanwhocodes/retry@0.3.1": {} + '@humanwhocodes/retry@0.3.1': {} - "@humanwhocodes/retry@0.4.3": {} + '@humanwhocodes/retry@0.4.3': {} - "@modelcontextprotocol/sdk@1.13.1": + '@modelcontextprotocol/sdk@1.13.1': dependencies: ajv: 6.12.6 content-type: 1.0.5 @@ -3252,47 +2132,47 @@ snapshots: transitivePeerDependencies: - supports-color - "@nodelib/fs.scandir@2.1.5": + '@nodelib/fs.scandir@2.1.5': dependencies: - "@nodelib/fs.stat": 2.0.5 + '@nodelib/fs.stat': 2.0.5 run-parallel: 1.2.0 - "@nodelib/fs.stat@2.0.5": {} + '@nodelib/fs.stat@2.0.5': {} - "@nodelib/fs.walk@1.2.8": + '@nodelib/fs.walk@1.2.8': dependencies: - "@nodelib/fs.scandir": 2.1.5 + '@nodelib/fs.scandir': 2.1.5 fastq: 1.19.1 - "@opentelemetry/api@1.9.0": {} + '@opentelemetry/api@1.9.0': {} - "@playwright/test@1.53.1": + '@playwright/test@1.53.1': dependencies: playwright: 1.53.1 - "@types/diff-match-patch@1.0.36": {} + '@types/diff-match-patch@1.0.36': {} - "@types/estree@1.0.8": {} + '@types/estree@1.0.8': {} - "@types/json-schema@7.0.15": {} + '@types/json-schema@7.0.15': {} - "@types/node-fetch@2.6.12": + '@types/node-fetch@2.6.12': dependencies: - "@types/node": 18.19.112 + '@types/node': 18.19.112 form-data: 4.0.3 - "@types/node@18.19.112": + '@types/node@18.19.112': dependencies: undici-types: 5.26.5 - "@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@eslint-community/regexpp": 4.12.1 - "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/scope-manager": 8.35.0 - "@typescript-eslint/type-utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/visitor-keys": 8.35.0 + '@eslint-community/regexpp': 4.12.1 + '@typescript-eslint/parser': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/type-utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.35.0 eslint: 9.29.0 graphemer: 1.4.0 ignore: 7.0.5 @@ -3302,40 +2182,40 @@ snapshots: transitivePeerDependencies: - supports-color - "@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@typescript-eslint/scope-manager": 8.35.0 - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) - "@typescript-eslint/visitor-keys": 8.35.0 + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.35.0 debug: 4.4.1 eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: - supports-color - "@typescript-eslint/project-service@8.35.0(typescript@5.8.3)": + '@typescript-eslint/project-service@8.35.0(typescript@5.8.3)': dependencies: - "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) - "@typescript-eslint/types": 8.35.0 + '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) + '@typescript-eslint/types': 8.35.0 debug: 4.4.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - "@typescript-eslint/scope-manager@8.35.0": + '@typescript-eslint/scope-manager@8.35.0': dependencies: - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/visitor-keys": 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/visitor-keys': 8.35.0 - "@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)": + '@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)': dependencies: typescript: 5.8.3 - "@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/type-utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) - "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) debug: 4.4.1 eslint: 9.29.0 ts-api-utils: 2.1.0(typescript@5.8.3) @@ -3343,14 +2223,14 @@ snapshots: transitivePeerDependencies: - supports-color - "@typescript-eslint/types@8.35.0": {} + '@typescript-eslint/types@8.35.0': {} - "@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)": + '@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)': dependencies: - "@typescript-eslint/project-service": 8.35.0(typescript@5.8.3) - "@typescript-eslint/tsconfig-utils": 8.35.0(typescript@5.8.3) - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/visitor-keys": 8.35.0 + '@typescript-eslint/project-service': 8.35.0(typescript@5.8.3) + '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/visitor-keys': 8.35.0 debug: 4.4.1 fast-glob: 3.3.3 is-glob: 4.0.3 @@ -3361,20 +2241,20 @@ snapshots: transitivePeerDependencies: - supports-color - "@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)": + '@typescript-eslint/utils@8.35.0(eslint@9.29.0)(typescript@5.8.3)': dependencies: - "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) - "@typescript-eslint/scope-manager": 8.35.0 - "@typescript-eslint/types": 8.35.0 - "@typescript-eslint/typescript-estree": 8.35.0(typescript@5.8.3) + '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0) + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: - supports-color - "@typescript-eslint/visitor-keys@8.35.0": + '@typescript-eslint/visitor-keys@8.35.0': dependencies: - "@typescript-eslint/types": 8.35.0 + '@typescript-eslint/types': 8.35.0 eslint-visitor-keys: 4.2.1 abort-controller@3.0.0: @@ -3400,11 +2280,11 @@ snapshots: ai@4.3.16(react@19.1.0)(zod@3.25.67): dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) - "@ai-sdk/react": 1.2.12(react@19.1.0)(zod@3.25.67) - "@ai-sdk/ui-utils": 1.2.11(zod@3.25.67) - "@opentelemetry/api": 1.9.0 + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) + '@ai-sdk/react': 1.2.12(react@19.1.0)(zod@3.25.67) + '@ai-sdk/ui-utils': 1.2.11(zod@3.25.67) + '@opentelemetry/api': 1.9.0 jsondiffpatch: 0.6.0 zod: 3.25.67 optionalDependencies: @@ -3417,10 +2297,18 @@ snapshots: json-schema-traverse: 0.4.1 uri-js: 4.4.1 + ansi-escapes@7.0.0: + dependencies: + environment: 1.1.0 + + ansi-regex@6.1.0: {} + ansi-styles@4.3.0: dependencies: color-convert: 2.0.1 + ansi-styles@6.2.1: {} + argparse@2.0.1: {} array-buffer-byte-length@1.0.2: @@ -3553,6 +2441,15 @@ snapshots: chalk@5.4.1: {} + cli-cursor@5.0.0: + dependencies: + restore-cursor: 5.1.0 + + cli-truncate@4.0.0: + dependencies: + slice-ansi: 5.0.0 + string-width: 7.2.0 + color-convert@2.0.1: dependencies: color-name: 1.1.4 @@ -3658,12 +2555,16 @@ snapshots: ee-first@1.1.1: {} + emoji-regex@10.4.0: {} + encodeurl@2.0.0: {} end-of-stream@1.4.5: dependencies: once: 1.4.0 + environment@1.1.0: {} + es-abstract@1.24.0: dependencies: array-buffer-byte-length: 1.0.2 @@ -3802,19 +2703,19 @@ snapshots: eslint@9.29.0: dependencies: - "@eslint-community/eslint-utils": 4.7.0(eslint@9.29.0) - "@eslint-community/regexpp": 4.12.1 - "@eslint/config-array": 0.20.1 - "@eslint/config-helpers": 0.2.3 - "@eslint/core": 0.14.0 - "@eslint/eslintrc": 3.3.1 - "@eslint/js": 9.29.0 - "@eslint/plugin-kit": 0.3.3 - "@humanfs/node": 0.16.6 - "@humanwhocodes/module-importer": 1.0.1 - "@humanwhocodes/retry": 0.4.3 - "@types/estree": 1.0.8 - "@types/json-schema": 7.0.15 + '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0) + '@eslint-community/regexpp': 4.12.1 + '@eslint/config-array': 0.20.1 + '@eslint/config-helpers': 0.2.3 + '@eslint/core': 0.14.0 + '@eslint/eslintrc': 3.3.1 + '@eslint/js': 9.29.0 + '@eslint/plugin-kit': 0.3.3 + '@humanfs/node': 0.16.6 + '@humanwhocodes/module-importer': 1.0.1 + '@humanwhocodes/retry': 0.4.3 + '@types/estree': 1.0.8 + '@types/json-schema': 7.0.15 ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.6 @@ -3862,6 +2763,8 @@ snapshots: event-target-shim@5.0.1: {} + eventemitter3@5.0.1: {} + eventsource-parser@3.0.3: {} eventsource@3.0.7: @@ -3912,8 +2815,8 @@ snapshots: fast-glob@3.3.3: dependencies: - "@nodelib/fs.stat": 2.0.5 - "@nodelib/fs.walk": 1.2.8 + '@nodelib/fs.stat': 2.0.5 + '@nodelib/fs.walk': 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.8 @@ -4027,6 +2930,8 @@ snapshots: - encoding - supports-color + get-east-asian-width@1.3.0: {} + get-intrinsic@1.3.0: dependencies: call-bind-apply-helpers: 1.0.2 @@ -4226,6 +3131,12 @@ snapshots: dependencies: call-bound: 1.0.4 + is-fullwidth-code-point@4.0.0: {} + + is-fullwidth-code-point@5.0.0: + dependencies: + get-east-asian-width: 1.3.0 + is-generator-function@1.1.0: dependencies: call-bound: 1.0.4 @@ -4326,7 +3237,7 @@ snapshots: jsondiffpatch@0.6.0: dependencies: - "@types/diff-match-patch": 1.0.36 + '@types/diff-match-patch': 1.0.36 chalk: 5.4.1 diff-match-patch: 1.0.5 @@ -4357,12 +3268,46 @@ snapshots: prelude-ls: 1.2.1 type-check: 0.4.0 + lilconfig@3.1.3: {} + + lint-staged@16.1.2: + dependencies: + chalk: 5.4.1 + commander: 14.0.0 + debug: 4.4.1 + lilconfig: 3.1.3 + listr2: 8.3.3 + micromatch: 4.0.8 + nano-spawn: 1.0.2 + pidtree: 0.6.0 + string-argv: 0.3.2 + yaml: 2.8.0 + transitivePeerDependencies: + - supports-color + + listr2@8.3.3: + dependencies: + cli-truncate: 4.0.0 + colorette: 2.0.20 + eventemitter3: 5.0.1 + log-update: 6.1.0 + rfdc: 1.4.1 + wrap-ansi: 9.0.0 + locate-path@6.0.0: dependencies: p-locate: 5.0.0 lodash.merge@4.6.2: {} + log-update@6.1.0: + dependencies: + ansi-escapes: 7.0.0 + cli-cursor: 5.0.0 + slice-ansi: 7.1.0 + strip-ansi: 7.1.0 + wrap-ansi: 9.0.0 + loose-envify@1.4.0: dependencies: js-tokens: 4.0.0 @@ -4392,6 +3337,8 @@ snapshots: dependencies: mime-db: 1.54.0 + mimic-function@5.0.1: {} + minimatch@3.1.2: dependencies: brace-expansion: 1.1.12 @@ -4404,6 +3351,8 @@ snapshots: ms@2.1.3: {} + nano-spawn@1.0.2: {} + nanoid@3.3.11: {} natural-compare@1.4.0: {} @@ -4454,8 +3403,8 @@ snapshots: ollama-ai-provider@1.2.0(zod@3.25.67): dependencies: - "@ai-sdk/provider": 1.1.3 - "@ai-sdk/provider-utils": 2.2.8(zod@3.25.67) + '@ai-sdk/provider': 1.1.3 + '@ai-sdk/provider-utils': 2.2.8(zod@3.25.67) partial-json: 0.1.7 optionalDependencies: zod: 3.25.67 @@ -4471,10 +3420,14 @@ snapshots: dependencies: wrappy: 1.0.2 + onetime@7.0.0: + dependencies: + mimic-function: 5.0.1 + openai@4.104.0(ws@8.18.2)(zod@3.25.67): dependencies: - "@types/node": 18.19.112 - "@types/node-fetch": 2.6.12 + '@types/node': 18.19.112 + '@types/node-fetch': 2.6.12 abort-controller: 3.0.0 agentkeepalive: 4.6.0 form-data-encoder: 1.7.2 @@ -4530,6 +3483,8 @@ snapshots: picomatch@2.3.1: {} + pidtree@0.6.0: {} + pino-abstract-transport@2.0.0: dependencies: split2: 4.2.0 @@ -4663,8 +3618,15 @@ snapshots: path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 + restore-cursor@5.1.0: + dependencies: + onetime: 7.0.0 + signal-exit: 4.1.0 + reusify@1.1.0: {} + rfdc@1.4.1: {} + router@2.2.0: dependencies: debug: 4.4.1 @@ -4806,6 +3768,18 @@ snapshots: side-channel-map: 1.0.1 side-channel-weakmap: 1.0.2 + signal-exit@4.1.0: {} + + slice-ansi@5.0.0: + dependencies: + ansi-styles: 6.2.1 + is-fullwidth-code-point: 4.0.0 + + slice-ansi@7.1.0: + dependencies: + ansi-styles: 6.2.1 + is-fullwidth-code-point: 5.0.0 + sonic-boom@4.2.0: dependencies: atomic-sleep: 1.0.0 @@ -4821,6 +3795,14 @@ snapshots: es-errors: 1.3.0 internal-slot: 1.1.0 + string-argv@0.3.2: {} + + string-width@7.2.0: + dependencies: + emoji-regex: 10.4.0 + get-east-asian-width: 1.3.0 + strip-ansi: 7.1.0 + string.prototype.matchall@4.0.12: dependencies: call-bind: 1.0.8 @@ -4865,6 +3847,10 @@ snapshots: define-properties: 1.2.1 es-object-atoms: 1.1.1 + strip-ansi@7.1.0: + dependencies: + ansi-regex: 6.1.0 + strip-json-comments@3.1.1: {} supports-color@7.2.0: @@ -4952,9 +3938,9 @@ snapshots: typescript-eslint@8.35.0(eslint@9.29.0)(typescript@5.8.3): dependencies: - "@typescript-eslint/eslint-plugin": 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/parser": 8.35.0(eslint@9.29.0)(typescript@5.8.3) - "@typescript-eslint/utils": 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/eslint-plugin': 8.35.0(@typescript-eslint/parser@8.35.0(eslint@9.29.0)(typescript@5.8.3))(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/parser': 8.35.0(eslint@9.29.0)(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@9.29.0)(typescript@5.8.3) eslint: 9.29.0 typescript: 5.8.3 transitivePeerDependencies: @@ -5041,10 +4027,18 @@ snapshots: word-wrap@1.2.5: {} + wrap-ansi@9.0.0: + dependencies: + ansi-styles: 6.2.1 + string-width: 7.2.0 + strip-ansi: 7.1.0 + wrappy@1.0.2: {} ws@8.18.2: {} + yaml@2.8.0: {} + yocto-queue@0.1.0: {} zod-to-json-schema@3.24.6(zod@3.25.67): diff --git a/src/mcp/prompts.ts b/src/mcp/prompts.ts index ff62aea..ad4871d 100644 --- a/src/mcp/prompts.ts +++ b/src/mcp/prompts.ts @@ -6,6 +6,18 @@ // Define the prompts export const PROMPTS = [ + { + name: "browserbase_system", + description: + "System prompt defining the scope and capabilities of Browserbase MCP server", + arguments: [], + }, + { + name: "multi_session_guidance", + description: + "Guidance on when and how to use multi-session browser automation", + arguments: [], + }, { name: "click_search_button", description: "A prompt template for clicking on a search button", @@ -19,6 +31,98 @@ export const PROMPTS = [ * @returns The prompt definition or throws an error if not found */ export function getPrompt(name: string) { + if (name === "browserbase_system") { + return { + description: "System prompt for Browserbase MCP server capabilities", + messages: [ + { + role: "system", + content: { + type: "text", + text: `You have access to a powerful browser automation server via Browserbase MCP. This server provides: + +CAPABILITIES: +- Cloud browser automation using Browserbase infrastructure +- AI-powered web interactions via Stagehand +- Parallel browser sessions for concurrent tasks +- Advanced stealth mode for anti-detection +- Proxy support for geo-location and privacy +- Context persistence for maintaining authentication +- Screenshot capture and visual analysis +- Structured data extraction from any webpage + +TOOL SELECTION GUIDE: +For SINGLE browser tasks: Use "browserbase_session_create" then regular tools +For MULTIPLE browser tasks: Use "multi_browserbase_stagehand_session_create" then session-specific tools + +MULTI-SESSION INDICATORS - Use multi-session tools when you see: +- "parallel", "multiple", "simultaneously", "concurrent" +- "different accounts", "A/B test", "compare" +- "multiple sites", "batch processing" +- Any task requiring more than one browser instance + +MULTI-SESSION WORKFLOW: +1. Create sessions: "multi_browserbase_stagehand_session_create" (give descriptive names) +2. Track sessions: "browserbase_stagehand_session_list" +3. Use session tools: "multi_browserbase_stagehand_navigate_session", etc. +4. Cleanup: "multi_browserbase_stagehand_session_close" + +BEST PRACTICES: +- Use descriptive session names for easier tracking +- Always close sessions when done to free resources +- Take screenshots for visual confirmation or debugging +- Each session maintains independent state and authentication + +When using this server, think of it as controlling real browsers in the cloud. You can navigate, click, type, extract data, and capture screenshots just like a human would, but with the precision and scale of automation.`, + }, + }, + ], + }; + } + + if (name === "multi_session_guidance") { + return { + description: "Comprehensive guidance on multi-session browser automation", + messages: [ + { + role: "system", + content: { + type: "text", + text: `Multi-Session Browser Automation Guidance + +WHEN TO USE MULTI-SESSION TOOLS: +- Parallel data collection from multiple websites +- A/B testing with different user flows +- Authentication with multiple user accounts simultaneously +- Cross-site operations requiring coordination +- Load testing or performance simulation +- Any task requiring more than one browser instance + +TOOL NAMING PATTERNS: +- Session Management: "multi_browserbase_stagehand_session_*" +- Browser Actions: "multi_browserbase_stagehand_*_session" + +RECOMMENDED WORKFLOW: +1. Create sessions: "multi_browserbase_stagehand_session_create" (give each a descriptive name) +2. List sessions: "browserbase_stagehand_session_list" (to track active sessions) +3. Use session-specific tools: "multi_browserbase_stagehand_navigate_session", "multi_browserbase_stagehand_act_session", etc. +4. Clean up: "multi_browserbase_stagehand_session_close" when done + +IMPORTANT RULES: +- Always use session-specific tools (with "_session" suffix) when working with multiple sessions +- Each session maintains independent cookies, authentication, and browser state +- Always close sessions when finished to free resources +- Use descriptive session names for easier tracking + +SINGLE VS MULTI-SESSION: +- Single: "browserbase_session_create" → "browserbase_stagehand_navigate" +- Multi: "multi_browserbase_stagehand_session_create" → "multi_browserbase_stagehand_navigate_session"`, + }, + }, + ], + }; + } + if (name === "click_search_button") { return { description: diff --git a/src/mcp/sampling.ts b/src/mcp/sampling.ts new file mode 100644 index 0000000..d1e0b79 --- /dev/null +++ b/src/mcp/sampling.ts @@ -0,0 +1,204 @@ +/** + * Sampling module for the Browserbase MCP server + * Implements sampling capability to request LLM completions from clients + * Docs: https://modelcontextprotocol.io/docs/concepts/sampling + */ + +/** + * Sampling capability configuration + * This indicates that the server can request LLM completions + */ +export const SAMPLING_CAPABILITY = {}; + +/** + * Note: Sampling in MCP is initiated BY the server TO the client. + * The server sends sampling/createMessage requests to ask the client + * for LLM completions. This is useful for intelligent browser automation + * where the server needs AI assistance to analyze pages and make decisions. + * + * Currently, sampling support depends on the MCP client implementation. + * Not all clients support sampling yet. (ie claude desktop) + */ + +/** + * Type definitions for sampling messages + */ +export type SamplingMessage = { + role: "user" | "assistant"; + content: { + type: "text" | "image"; + text?: string; + data?: string; // base64 for images + mimeType?: string; + }; +}; + +/** + * Pre-built sampling templates for common browser automation scenarios + */ +export const SAMPLING_TEMPLATES = { + /** + * Analyze a page to determine what actions are available + */ + analyzePageActions: ( + pageContent: string, + screenshot?: string, + ): SamplingMessage[] => [ + { + role: "user", + content: { + type: "text", + text: `Analyze this webpage and identify the main interactive elements and possible actions. + +Page content: +${pageContent} + +Please list: +1. Main navigation elements +2. Forms and input fields +3. Buttons and clickable elements +4. Key information displayed +5. Suggested next actions for common automation tasks`, + }, + }, + ...(screenshot + ? [ + { + role: "user" as const, + content: { + type: "image" as const, + data: screenshot, + mimeType: "image/png", + }, + }, + ] + : []), + ], + + /** + * Determine next steps in a multi-step process + */ + determineNextStep: ( + currentState: string, + goal: string, + ): SamplingMessage[] => [ + { + role: "user", + content: { + type: "text", + text: `Current state of the browser automation: +${currentState} + +Goal: ${goal} + +What should be the next action to take? Consider: +1. Are we on the right page? +2. What elements need to be interacted with? +3. Is there any data to extract first? +4. Are there any errors or blockers visible? + +Provide a specific, actionable next step.`, + }, + }, + ], + + /** + * Extract structured data from a page + */ + extractStructuredData: ( + pageContent: string, + dataSchema: string, + ): SamplingMessage[] => [ + { + role: "user", + content: { + type: "text", + text: `Extract structured data from this webpage according to the schema. + +Page content: +${pageContent} + +Expected data schema: +${dataSchema} + +Return the extracted data as valid JSON matching the schema. If any fields cannot be found, use null.`, + }, + }, + ], + + /** + * Handle error or unexpected state + */ + handleError: (error: string, pageState: string): SamplingMessage[] => [ + { + role: "user", + content: { + type: "text", + text: `The browser automation encountered an error: + +Error: ${error} + +Current page state: +${pageState} + +Suggest how to recover from this error: +1. What might have caused this? +2. What alternative actions could be taken? +3. Should we retry, navigate elsewhere, or try a different approach?`, + }, + }, + ], + + /** + * Interpret complex UI patterns + */ + interpretUI: (screenshot: string, instruction: string): SamplingMessage[] => [ + { + role: "user", + content: { + type: "text", + text: `Analyze this screenshot and help with: ${instruction}`, + }, + }, + { + role: "user", + content: { + type: "image", + data: screenshot, + mimeType: "image/png", + }, + }, + ], +}; + +/** + * Helper function to create a sampling request structure + * This shows what a sampling request would look like when sent to the client + */ +export function createSamplingRequest( + messages: SamplingMessage[], + options?: { + systemPrompt?: string; + temperature?: number; + maxTokens?: number; + includeContext?: "none" | "thisServer" | "allServers"; + }, +) { + return { + method: "sampling/createMessage", + params: { + messages, + systemPrompt: + options?.systemPrompt || + "You are an expert browser automation assistant helping to analyze web pages and determine optimal automation strategies.", + temperature: options?.temperature || 0.7, + maxTokens: options?.maxTokens || 1000, + includeContext: options?.includeContext || "thisServer", + modelPreferences: { + hints: [{ name: "claude-3" }, { name: "gpt-4" }], + intelligencePriority: 0.8, + speedPriority: 0.2, + }, + }, + }; +} diff --git a/src/stagehandStore.ts b/src/stagehandStore.ts index 676e383..4bef116 100644 --- a/src/stagehandStore.ts +++ b/src/stagehandStore.ts @@ -14,7 +14,7 @@ export const create = async ( config: Config, params: CreateSessionParams = {}, ): Promise => { - const id = randomUUID(); + const id = randomUUID() + "_" + Date.now(); // Merge config with params const apiKey = params.apiKey || config.browserbaseApiKey; diff --git a/src/tools/index.ts b/src/tools/index.ts index d5c28c5..e27feba 100644 --- a/src/tools/index.ts +++ b/src/tools/index.ts @@ -35,13 +35,13 @@ export const multiSessionTools = [ // Export all tools as array export const TOOLS = [ + ...multiSessionTools, ...sessionTools, navigateTool, actTool, extractTool, observeTool, screenshotTool, - ...multiSessionTools, ]; export const sessionManagementTools = sessionTools; diff --git a/src/tools/multiSession.ts b/src/tools/multiSession.ts index 2f640e2..bfcf464 100644 --- a/src/tools/multiSession.ts +++ b/src/tools/multiSession.ts @@ -78,15 +78,15 @@ function createMultiSessionAwareTool( export const createSessionTool = defineTool({ capability: "create_session", schema: { - name: "multi-browserbase_stagehand_session_create", + name: "multi_browserbase_stagehand_session_create", description: - "Create a new Stagehand browser session with full web automation capabilities. This initializes a fresh browser instance that can navigate, interact with elements, extract data, and take screenshots. Each session is isolated and can be managed independently. Use this when you need to start web automation tasks or when you need multiple parallel browser sessions.", + "Create parallel browser session for multi-session workflows. Use this when you need multiple browser instances running simultaneously: parallel data scraping, concurrent automation, A/B testing, multiple user accounts, cross-site operations, batch processing, or any task requiring more than one browser. Creates an isolated browser session with independent cookies, authentication, and state. Always pair with session-specific tools (those ending with '_session'). Perfect for scaling automation tasks that require multiple browsers working in parallel.", inputSchema: z.object({ name: z .string() .optional() .describe( - "Optional human-readable name for the session to help track multiple sessions (e.g. 'login-flow', 'data-scraping', 'testing-checkout')", + "Highly recommended: Descriptive name for tracking multiple sessions (e.g. 'amazon-scraper', 'user-login-flow', 'checkout-test-1'). Makes debugging and session management much easier!", ), browserbaseSessionID: z .string() @@ -142,7 +142,7 @@ export const listSessionsTool = defineTool({ schema: { name: "browserbase_stagehand_session_list", description: - "List all currently active Stagehand browser sessions with their details. Use this to see what sessions are available, check their status, and get session IDs for use with other tools. Helpful for managing multiple concurrent browser automation tasks.", + "Track all parallel sessions: Critical tool for multi-session management! Shows all active browser sessions with their IDs, names, ages, and Browserbase session IDs. Use this frequently to monitor your parallel automation workflows, verify sessions are running, and get session IDs for session-specific tools. Essential for debugging and resource management in complex multi-browser scenarios.", inputSchema: z.object({}), }, handle: async (): Promise => { @@ -193,14 +193,14 @@ export const listSessionsTool = defineTool({ export const closeSessionTool = defineTool({ capability: "close_session", schema: { - name: "multi-browserbase_stagehand_session_close", + name: "multi_browserbase_stagehand_session_close", description: - "Close and clean up a specific Stagehand browser session. This will terminate the browser instance, end the Browserbase session, and free up resources. Use this when you're done with a session to avoid leaving sessions running unnecessarily. Important: Once closed, the session ID cannot be reused.", + "Cleanup parallel session for multi-session workflows. Properly terminates a browser session, ends the Browserbase session, and frees cloud resources. Always use this when finished with a session to avoid resource waste and billing charges. Critical for responsible multi-session automation - each unclosed session continues consuming resources!", inputSchema: z.object({ sessionId: z .string() .describe( - "The exact session ID to close. You can get session IDs from the 'stagehand_session_list' tool. Make sure this is the correct session as this action cannot be undone.", + "Exact session ID to close (get from 'browserbase_stagehand_session_list'). Double-check this ID - once closed, the session cannot be recovered!", ), }), }, @@ -230,22 +230,22 @@ export const closeSessionTool = defineTool({ export const navigateWithSessionTool = createMultiSessionAwareTool( navigateTool, { - namePrefix: "multi-", + namePrefix: "multi_", nameSuffix: "_session", }, ); export const actWithSessionTool = createMultiSessionAwareTool(actTool, { - namePrefix: "multi-", + namePrefix: "multi_", nameSuffix: "_session", }); export const extractWithSessionTool = createMultiSessionAwareTool(extractTool, { - namePrefix: "multi-", + namePrefix: "multi_", nameSuffix: "_session", }); export const observeWithSessionTool = createMultiSessionAwareTool(observeTool, { - namePrefix: "multi-", + namePrefix: "multi_", nameSuffix: "_session", }); diff --git a/src/tools/session.ts b/src/tools/session.ts index 6024b75..838bf6c 100644 --- a/src/tools/session.ts +++ b/src/tools/session.ts @@ -28,7 +28,7 @@ type CreateSessionInput = z.infer; const createSessionSchema: ToolSchema = { name: "browserbase_session_create", description: - "Create or reuse a cloud browser session using Browserbase with fully initialized Stagehand. This creates the browser session with all configuration flags (proxies, stealth, viewport, cookies, etc.) and initializes Stagehand to work with that session. Updates the active session.", + "Create or reuse a single cloud browser session using Browserbase with fully initialized Stagehand. WARNING: This tool is for SINGLE browser workflows only. If you need multiple browser sessions running simultaneously (parallel scraping, A/B testing, multiple accounts), use 'multi_browserbase_stagehand_session_create' instead. This creates one browser session with all configuration flags (proxies, stealth, viewport, cookies, etc.) and initializes Stagehand to work with that session. Updates the active session.", inputSchema: CreateSessionInputSchema, }; From 9c4a5338b03c711c9c27f40a70b0b28f9f41f066 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Mon, 30 Jun 2025 12:43:31 -0700 Subject: [PATCH 14/32] zod fix --- package.json | 3 ++- pnpm-lock.yaml | 3 +++ src/index.ts | 1 - src/mcp/prompts.ts | 2 ++ 4 files changed, 7 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 472f026..bbb04b8 100644 --- a/package.json +++ b/package.json @@ -36,7 +36,8 @@ "@browserbasehq/stagehand": "^2.4.0", "@modelcontextprotocol/sdk": "^1.13.1", "@playwright/test": "^1.49.0", - "commander": "^14.0.0" + "commander": "^14.0.0", + "zod": "^3.25.67" }, "devDependencies": { "@eslint/js": "^9.29.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index f090304..4ff701f 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -20,6 +20,9 @@ importers: commander: specifier: ^14.0.0 version: 14.0.0 + zod: + specifier: ^3.25.67 + version: 3.25.67 devDependencies: '@eslint/js': specifier: ^9.29.0 diff --git a/src/index.ts b/src/index.ts index bbda17e..fbeacb7 100644 --- a/src/index.ts +++ b/src/index.ts @@ -32,7 +32,6 @@ const cookieSchema = z.object({ }); // Configuration schema for Smithery - matches existing Config interface -// @ts-expect-error Type instantiation is excessively deep and possibly infinite with complex Zod schemas export const configSchema = z.object({ browserbaseApiKey: z.string().describe("The Browserbase API Key to use"), browserbaseProjectId: z diff --git a/src/mcp/prompts.ts b/src/mcp/prompts.ts index ad4871d..98e7171 100644 --- a/src/mcp/prompts.ts +++ b/src/mcp/prompts.ts @@ -72,6 +72,7 @@ BEST PRACTICES: - Always close sessions when done to free resources - Take screenshots for visual confirmation or debugging - Each session maintains independent state and authentication +- No need to create backup sessions - sessions are reliable and persistent When using this server, think of it as controlling real browsers in the cloud. You can navigate, click, type, extract data, and capture screenshots just like a human would, but with the precision and scale of automation.`, }, @@ -113,6 +114,7 @@ IMPORTANT RULES: - Each session maintains independent cookies, authentication, and browser state - Always close sessions when finished to free resources - Use descriptive session names for easier tracking +- No need to create backup sessions - sessions are reliable and persistent SINGLE VS MULTI-SESSION: - Single: "browserbase_session_create" → "browserbase_stagehand_navigate" From 70d99c4d40f1ffcfa5d31e0ff39b076385b7a5a1 Mon Sep 17 00:00:00 2001 From: Roaring <216452114+the-roaring@users.noreply.github.com> Date: Mon, 30 Jun 2025 12:46:11 -0700 Subject: [PATCH 15/32] add deps --- package.json | 2 ++ pnpm-lock.yaml | 25 +++++++++++++++++++------ 2 files changed, 21 insertions(+), 6 deletions(-) diff --git a/package.json b/package.json index bbb04b8..99d2014 100644 --- a/package.json +++ b/package.json @@ -37,6 +37,8 @@ "@modelcontextprotocol/sdk": "^1.13.1", "@playwright/test": "^1.49.0", "commander": "^14.0.0", + "dotenv": "^17.0.0", + "playwright-core": "^1.53.2", "zod": "^3.25.67" }, "devDependencies": { diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 4ff701f..bc46436 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -10,7 +10,7 @@ importers: dependencies: '@browserbasehq/stagehand': specifier: ^2.4.0 - version: 2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67) + version: 2.4.0(deepmerge@4.3.1)(dotenv@17.0.0)(react@19.1.0)(zod@3.25.67) '@modelcontextprotocol/sdk': specifier: ^1.13.1 version: 1.13.1 @@ -20,6 +20,12 @@ importers: commander: specifier: ^14.0.0 version: 14.0.0 + dotenv: + specifier: ^17.0.0 + version: 17.0.0 + playwright-core: + specifier: ^1.53.2 + version: 1.53.2 zod: specifier: ^3.25.67 version: 3.25.67 @@ -602,8 +608,8 @@ packages: resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} engines: {node: '>=0.10.0'} - dotenv@16.5.0: - resolution: {integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==} + dotenv@17.0.0: + resolution: {integrity: sha512-A0BJ5lrpJVSfnMMXjmeO0xUnoxqsBHWCoqqTnGwGYVdnctqXXUEhJOO7LxmgxJon9tEZFGpe0xPRX0h2v3AANQ==} engines: {node: '>=12'} dunder-proto@1.0.1: @@ -1419,6 +1425,11 @@ packages: engines: {node: '>=18'} hasBin: true + playwright-core@1.53.2: + resolution: {integrity: sha512-ox/OytMy+2w1jcYEYlOo1Hhp8hZkLCximMTUTMBXjGUA1KoFfiSZ+DU+3a739jsPY0yoKH2TFy9S2fsJas8yAw==} + engines: {node: '>=18'} + hasBin: true + playwright@1.53.1: resolution: {integrity: sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==} engines: {node: '>=18'} @@ -2011,7 +2022,7 @@ snapshots: transitivePeerDependencies: - encoding - '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.5.0)(react@19.1.0)(zod@3.25.67)': + '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@17.0.0)(react@19.1.0)(zod@3.25.67)': dependencies: '@anthropic-ai/sdk': 0.39.0 '@browserbasehq/sdk': 2.6.0 @@ -2019,7 +2030,7 @@ snapshots: ai: 4.3.16(react@19.1.0)(zod@3.25.67) deepmerge: 4.3.1 devtools-protocol: 0.0.1464554 - dotenv: 16.5.0 + dotenv: 17.0.0 fetch-cookie: 3.1.0 openai: 4.104.0(ws@8.18.2)(zod@3.25.67) pino: 9.7.0 @@ -2544,7 +2555,7 @@ snapshots: dependencies: esutils: 2.0.3 - dotenv@16.5.0: {} + dotenv@17.0.0: {} dunder-proto@1.0.1: dependencies: @@ -3528,6 +3539,8 @@ snapshots: playwright-core@1.53.1: {} + playwright-core@1.53.2: {} + playwright@1.53.1: dependencies: playwright-core: 1.53.1 From 95834abc67f1bf197e1f88a24208bf1ccdc37e47 Mon Sep 17 00:00:00 2001 From: Kyle Jeong <77771518+Kylejeong2@users.noreply.github.com> Date: Mon, 30 Jun 2025 16:47:16 -0700 Subject: [PATCH 16/32] [Fix]: add workflows to publish to npm + bug fixes (#93) * fix session url bugs * readme small updates + add github workflows to publish + ci --- .github/workflows/ci.yml | 25 + .github/workflows/publish.yml | 21 + LICENSE | 2 +- README.md | 12 +- package-lock.json | 5139 +++++++++++++++++++++++++++------ package.json | 10 +- src/tools/navigate.ts | 4 +- src/tools/session.ts | 2 +- 8 files changed, 4394 insertions(+), 821 deletions(-) create mode 100644 .github/workflows/ci.yml create mode 100644 .github/workflows/publish.yml diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 0000000..2bf6aa3 --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,25 @@ +name: CI + +on: + push: + branches: [ main ] + pull_request: + branches: [ main ] + +jobs: + lint: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - name: Use Node.js 22 + uses: actions/setup-node@v4 + with: + node-version: '22' + cache: 'npm' + - name: Install dependencies + run: npm ci + - run: npm run build + - name: Run ESLint + run: npm run lint + - name: Ensure no changes + run: git diff --exit-code \ No newline at end of file diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml new file mode 100644 index 0000000..199020a --- /dev/null +++ b/.github/workflows/publish.yml @@ -0,0 +1,21 @@ +name: Publish +on: + release: + types: [published] +jobs: + publish-npm: + runs-on: ubuntu-latest + permissions: + contents: read + id-token: write + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version: 22 + registry-url: https://registry.npmjs.org/ + - run: npm ci + - run: npm run build + - run: npm publish --provenance + env: + NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} \ No newline at end of file diff --git a/LICENSE b/LICENSE index 624e143..1c012e4 100644 --- a/LICENSE +++ b/LICENSE @@ -1,5 +1,5 @@ Apache License - Version 2.0, January 2004 + Version 2.0, June 2025 http://www.apache.org/licenses/ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION diff --git a/README.md b/README.md index 69a905b..ea97d0d 100644 --- a/README.md +++ b/README.md @@ -65,7 +65,7 @@ cd mcp-server-browserbase npm install && npm run build ``` -Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host over SSE. +Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host SHTTP. ### STDIO: @@ -100,7 +100,7 @@ Then in your MCP Config JSON file put the following: { "mcpServers": { "browserbase": { - "url": "http://localhost:8931/sse", + "url": "http://localhost:8931/mcp", "env": { "BROWSERBASE_API_KEY": "", "BROWSERBASE_PROJECT_ID": "" @@ -124,7 +124,7 @@ The Browserbase MCP server accepts the following command-line flags: | `--advancedStealth` | Enable Browserbase Advanced Stealth (Only for Scale Plan Users) | | `--contextId ` | Specify a Browserbase Context ID to use | | `--persist [boolean]` | Whether to persist the Browserbase context (default: true) | -| `--port ` | Port to listen on for HTTP/SSE transport | +| `--port ` | Port to listen on for HTTP/SHTTP transport | | `--host ` | Host to bind server to (default: localhost, use 0.0.0.0 for all interfaces) | | `--cookies [json]` | JSON array of cookies to inject into the browser | | `--browserWidth ` | Browser viewport width (default: 1024) | @@ -421,7 +421,7 @@ mcp-server-browserbase/ │ ├── sessionManager.ts # Browserbase session lifecycle management │ ├── stagehandStore.ts # Multi-session store for managing parallel browser sessions │ ├── program.ts # CLI program setup using Commander.js -│ ├── transport.ts # HTTP/SSE and STDIO transport handlers +│ ├── transport.ts # HTTP/SHTTP and STDIO transport handlers │ ├── server.ts # Server list management │ ├── utils.ts # Utility functions │ ├── mcp/ # MCP protocol implementations @@ -466,7 +466,7 @@ mcp-server-browserbase/ **program.ts** - CLI program setup using Commander.js with all command-line options, argument parsing, and transport initialization. -**transport.ts** - Transport layer implementations for STDIO and HTTP/SSE communication with session management across different connection types. +**transport.ts** - Transport layer implementations for STDIO and HTTP/SHTTP communication with session management across different connection types. **server.ts** - Server list management providing factory patterns for server creation and handling multiple concurrent connections. @@ -543,6 +543,6 @@ For more information about the Model Context Protocol, visit: ## License -Licensed under the MIT License. +Licensed under the Apache 2.0 License. Copyright 2025 Browserbase, Inc. diff --git a/package-lock.json b/package-lock.json index 76b4bc8..fa199e3 100644 --- a/package-lock.json +++ b/package-lock.json @@ -7,19 +7,30 @@ "": { "name": "@browserbasehq/mcp", "version": "2.0.0", - "license": "MIT", + "license": "Apache-2.0", "dependencies": { "@browserbasehq/stagehand": "^2.4.0", "@modelcontextprotocol/sdk": "^1.13.1", "@playwright/test": "^1.49.0", - "commander": "^14.0.0" + "commander": "^14.0.0", + "dotenv": "^16.4.6", + "playwright-core": "^1.53.2", + "zod": "^3.25.67" }, "bin": { "mcp-server-stagehand": "cli.js" }, "devDependencies": { + "@eslint/js": "^9.29.0", + "eslint": "^9.29.0", + "eslint-plugin-react": "^7.37.5", + "globals": "^16.2.0", + "husky": "^9.1.7", + "lint-staged": "^16.1.2", + "prettier": "^3.6.1", "shx": "^0.3.4", - "typescript": "^5.6.2" + "typescript": "^5.6.2", + "typescript-eslint": "^8.35.0" } }, "node_modules/@ai-sdk/anthropic": { @@ -400,6 +411,173 @@ "node": ">=18" } }, + "node_modules/@eslint-community/eslint-utils": { + "version": "4.7.0", + "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.7.0.tgz", + "integrity": "sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==", + "dev": true, + "license": "MIT", + "dependencies": { + "eslint-visitor-keys": "^3.4.3" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || >=8.0.0" + } + }, + "node_modules/@eslint-community/eslint-utils/node_modules/eslint-visitor-keys": { + "version": "3.4.3", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz", + "integrity": "sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/@eslint-community/regexpp": { + "version": "4.12.1", + "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.12.1.tgz", + "integrity": "sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": "^12.0.0 || ^14.0.0 || >=16.0.0" + } + }, + "node_modules/@eslint/config-array": { + "version": "0.21.0", + "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.0.tgz", + "integrity": "sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@eslint/object-schema": "^2.1.6", + "debug": "^4.3.1", + "minimatch": "^3.1.2" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, + "node_modules/@eslint/config-helpers": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.0.tgz", + "integrity": "sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, + "node_modules/@eslint/core": { + "version": "0.14.0", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.14.0.tgz", + "integrity": "sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@types/json-schema": "^7.0.15" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, + "node_modules/@eslint/eslintrc": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-3.3.1.tgz", + "integrity": "sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^10.0.1", + "globals": "^14.0.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.1.2", + "strip-json-comments": "^3.1.1" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/@eslint/eslintrc/node_modules/globals": { + "version": "14.0.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-14.0.0.tgz", + "integrity": "sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@eslint/js": { + "version": "9.30.0", + "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.30.0.tgz", + "integrity": "sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==", + "dev": true, + "license": "MIT", + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://eslint.org/donate" + } + }, + "node_modules/@eslint/object-schema": { + "version": "2.1.6", + "resolved": "https://registry.npmjs.org/@eslint/object-schema/-/object-schema-2.1.6.tgz", + "integrity": "sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, + "node_modules/@eslint/plugin-kit": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.3.tgz", + "integrity": "sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@eslint/core": "^0.15.1", + "levn": "^0.4.1" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, + "node_modules/@eslint/plugin-kit/node_modules/@eslint/core": { + "version": "0.15.1", + "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.15.1.tgz", + "integrity": "sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@types/json-schema": "^7.0.15" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + } + }, "node_modules/@google/genai": { "version": "0.8.0", "resolved": "https://registry.npmjs.org/@google/genai/-/genai-0.8.0.tgz", @@ -413,6 +591,72 @@ "node": ">=18.0.0" } }, + "node_modules/@humanfs/core": { + "version": "0.19.1", + "resolved": "https://registry.npmjs.org/@humanfs/core/-/core-0.19.1.tgz", + "integrity": "sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=18.18.0" + } + }, + "node_modules/@humanfs/node": { + "version": "0.16.6", + "resolved": "https://registry.npmjs.org/@humanfs/node/-/node-0.16.6.tgz", + "integrity": "sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@humanfs/core": "^0.19.1", + "@humanwhocodes/retry": "^0.3.0" + }, + "engines": { + "node": ">=18.18.0" + } + }, + "node_modules/@humanfs/node/node_modules/@humanwhocodes/retry": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.3.1.tgz", + "integrity": "sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=18.18" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, + "node_modules/@humanwhocodes/module-importer": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", + "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=12.22" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, + "node_modules/@humanwhocodes/retry": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.4.3.tgz", + "integrity": "sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=18.18" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, "node_modules/@modelcontextprotocol/sdk": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.13.1.tgz", @@ -435,6 +679,44 @@ "node": ">=18" } }, + "node_modules/@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + }, + "engines": { + "node": ">= 8" + } + }, "node_modules/@opentelemetry/api": { "version": "1.9.0", "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.0.tgz", @@ -465,6 +747,20 @@ "integrity": "sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==", "license": "MIT" }, + "node_modules/@types/estree": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", + "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/json-schema": { + "version": "7.0.15", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", + "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", + "dev": true, + "license": "MIT" + }, "node_modules/@types/node": { "version": "18.19.80", "resolved": "https://registry.npmjs.org/@types/node/-/node-18.19.80.tgz", @@ -484,730 +780,672 @@ "form-data": "^4.0.0" } }, - "node_modules/abort-controller": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", - "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", + "node_modules/@typescript-eslint/eslint-plugin": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.35.1.tgz", + "integrity": "sha512-9XNTlo7P7RJxbVeICaIIIEipqxLKguyh+3UbXuT2XQuFp6d8VOeDEGuz5IiX0dgZo8CiI6aOFLg4e8cF71SFVg==", + "dev": true, "license": "MIT", "dependencies": { - "event-target-shim": "^5.0.0" + "@eslint-community/regexpp": "^4.10.0", + "@typescript-eslint/scope-manager": "8.35.1", + "@typescript-eslint/type-utils": "8.35.1", + "@typescript-eslint/utils": "8.35.1", + "@typescript-eslint/visitor-keys": "8.35.1", + "graphemer": "^1.4.0", + "ignore": "^7.0.0", + "natural-compare": "^1.4.0", + "ts-api-utils": "^2.1.0" }, "engines": { - "node": ">=6.5" - } - }, - "node_modules/accepts": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-2.0.0.tgz", - "integrity": "sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==", - "license": "MIT", - "dependencies": { - "mime-types": "^3.0.0", - "negotiator": "^1.0.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, - "engines": { - "node": ">= 0.6" + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "@typescript-eslint/parser": "^8.35.1", + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/agent-base": { - "version": "7.1.3", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.3.tgz", - "integrity": "sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==", + "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { + "version": "7.0.5", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.5.tgz", + "integrity": "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==", + "dev": true, "license": "MIT", "engines": { - "node": ">= 14" + "node": ">= 4" } }, - "node_modules/agentkeepalive": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.6.0.tgz", - "integrity": "sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==", + "node_modules/@typescript-eslint/parser": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.35.1.tgz", + "integrity": "sha512-3MyiDfrfLeK06bi/g9DqJxP5pV74LNv4rFTyvGDmT3x2p1yp1lOd+qYZfiRPIOf/oON+WRZR5wxxuF85qOar+w==", + "dev": true, "license": "MIT", "dependencies": { - "humanize-ms": "^1.2.1" + "@typescript-eslint/scope-manager": "8.35.1", + "@typescript-eslint/types": "8.35.1", + "@typescript-eslint/typescript-estree": "8.35.1", + "@typescript-eslint/visitor-keys": "8.35.1", + "debug": "^4.3.4" }, "engines": { - "node": ">= 8.0.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/ai": { - "version": "4.3.16", - "resolved": "https://registry.npmjs.org/ai/-/ai-4.3.16.tgz", - "integrity": "sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==", - "license": "Apache-2.0", + "node_modules/@typescript-eslint/project-service": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.35.1.tgz", + "integrity": "sha512-VYxn/5LOpVxADAuP3NrnxxHYfzVtQzLKeldIhDhzC8UHaiQvYlXvKuVho1qLduFbJjjy5U5bkGwa3rUGUb1Q6Q==", + "dev": true, + "license": "MIT", "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8", - "@ai-sdk/react": "1.2.12", - "@ai-sdk/ui-utils": "1.2.11", - "@opentelemetry/api": "1.9.0", - "jsondiffpatch": "0.6.0" + "@typescript-eslint/tsconfig-utils": "^8.35.1", + "@typescript-eslint/types": "^8.35.1", + "debug": "^4.3.4" }, "engines": { - "node": ">=18" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, - "peerDependencies": { - "react": "^18 || ^19 || ^19.0.0-rc", - "zod": "^3.23.8" + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" }, - "peerDependenciesMeta": { - "react": { - "optional": true - } + "peerDependencies": { + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "node_modules/@typescript-eslint/scope-manager": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.35.1.tgz", + "integrity": "sha512-s/Bpd4i7ht2934nG+UoSPlYXd08KYz3bmjLEb7Ye1UVob0d1ENiT3lY8bsCmik4RqfSbPw9xJJHbugpPpP5JUg==", + "dev": true, "license": "MIT", "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" + "@typescript-eslint/types": "8.35.1", + "@typescript-eslint/visitor-keys": "8.35.1" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" } }, - "node_modules/asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", - "license": "MIT" - }, - "node_modules/atomic-sleep": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/atomic-sleep/-/atomic-sleep-1.0.0.tgz", - "integrity": "sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==", + "node_modules/@typescript-eslint/tsconfig-utils": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.35.1.tgz", + "integrity": "sha512-K5/U9VmT9dTHoNowWZpz+/TObS3xqC5h0xAIjXPw+MNcKV9qg6eSatEnmeAwkjHijhACH0/N7bkhKvbt1+DXWQ==", + "dev": true, "license": "MIT", "engines": { - "node": ">=8.0.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/balanced-match": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "node_modules/@typescript-eslint/type-utils": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.35.1.tgz", + "integrity": "sha512-HOrUBlfVRz5W2LIKpXzZoy6VTZzMu2n8q9C2V/cFngIC5U1nStJgv0tMV4sZPzdf4wQm9/ToWUFPMN9Vq9VJQQ==", "dev": true, - "license": "MIT" - }, - "node_modules/base64-js": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", - "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/bignumber.js": { - "version": "9.3.0", - "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.3.0.tgz", - "integrity": "sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==", - "license": "MIT", - "engines": { - "node": "*" - } - }, - "node_modules/body-parser": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.1.0.tgz", - "integrity": "sha512-/hPxh61E+ll0Ujp24Ilm64cykicul1ypfwjVttduAiEdtnJFvLePSrIPk+HMImtNv5270wOGCb1Tns2rybMkoQ==", "license": "MIT", "dependencies": { - "bytes": "^3.1.2", - "content-type": "^1.0.5", - "debug": "^4.4.0", - "http-errors": "^2.0.0", - "iconv-lite": "^0.5.2", - "on-finished": "^2.4.1", - "qs": "^6.14.0", - "raw-body": "^3.0.0", - "type-is": "^2.0.0" + "@typescript-eslint/typescript-estree": "8.35.1", + "@typescript-eslint/utils": "8.35.1", + "debug": "^4.3.4", + "ts-api-utils": "^2.1.0" }, "engines": { - "node": ">=18" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/body-parser/node_modules/debug": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", - "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", + "node_modules/@typescript-eslint/types": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.35.1.tgz", + "integrity": "sha512-q/O04vVnKHfrrhNAscndAn1tuQhIkwqnaW+eu5waD5IPts2eX1dgJxgqcPx5BX109/qAz7IG6VrEPTOYKCNfRQ==", + "dev": true, "license": "MIT", - "dependencies": { - "ms": "^2.1.3" - }, "engines": { - "node": ">=6.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" } }, - "node_modules/body-parser/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" - }, - "node_modules/body-parser/node_modules/qs": { - "version": "6.14.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.14.0.tgz", - "integrity": "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==", - "license": "BSD-3-Clause", + "node_modules/@typescript-eslint/typescript-estree": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.35.1.tgz", + "integrity": "sha512-Vvpuvj4tBxIka7cPs6Y1uvM7gJgdF5Uu9F+mBJBPY4MhvjrjWGK4H0lVgLJd/8PWZ23FTqsaJaLEkBCFUk8Y9g==", + "dev": true, + "license": "MIT", "dependencies": { - "side-channel": "^1.1.0" + "@typescript-eslint/project-service": "8.35.1", + "@typescript-eslint/tsconfig-utils": "8.35.1", + "@typescript-eslint/types": "8.35.1", + "@typescript-eslint/visitor-keys": "8.35.1", + "debug": "^4.3.4", + "fast-glob": "^3.3.2", + "is-glob": "^4.0.3", + "minimatch": "^9.0.4", + "semver": "^7.6.0", + "ts-api-utils": "^2.1.0" }, "engines": { - "node": ">=0.6" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, "funding": { - "url": "https://github.com/sponsors/ljharb" + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "node_modules/@typescript-eslint/typescript-estree/node_modules/brace-expansion": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", + "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", "dev": true, "license": "MIT", "dependencies": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" + "balanced-match": "^1.0.0" } }, - "node_modules/buffer-equal-constant-time": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", - "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==", - "license": "BSD-3-Clause" - }, - "node_modules/bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "license": "MIT", + "node_modules/@typescript-eslint/typescript-estree/node_modules/minimatch": { + "version": "9.0.5", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", + "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", + "dev": true, + "license": "ISC", + "dependencies": { + "brace-expansion": "^2.0.1" + }, "engines": { - "node": ">= 0.8" + "node": ">=16 || 14 >=14.17" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/call-bind-apply-helpers": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", - "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "function-bind": "^1.1.2" + "node_modules/@typescript-eslint/typescript-estree/node_modules/semver": { + "version": "7.7.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", + "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" }, "engines": { - "node": ">= 0.4" + "node": ">=10" } }, - "node_modules/call-bound": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.4.tgz", - "integrity": "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==", + "node_modules/@typescript-eslint/utils": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.35.1.tgz", + "integrity": "sha512-lhnwatFmOFcazAsUm3ZnZFpXSxiwoa1Lj50HphnDe1Et01NF4+hrdXONSUHIcbVu2eFb1bAf+5yjXkGVkXBKAQ==", + "dev": true, "license": "MIT", "dependencies": { - "call-bind-apply-helpers": "^1.0.2", - "get-intrinsic": "^1.3.0" + "@eslint-community/eslint-utils": "^4.7.0", + "@typescript-eslint/scope-manager": "8.35.1", + "@typescript-eslint/types": "8.35.1", + "@typescript-eslint/typescript-estree": "8.35.1" }, "engines": { - "node": ">= 0.4" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, "funding": { - "url": "https://github.com/sponsors/ljharb" + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <5.9.0" } }, - "node_modules/chalk": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", - "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", + "node_modules/@typescript-eslint/visitor-keys": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.35.1.tgz", + "integrity": "sha512-VRwixir4zBWCSTP/ljEo091lbpypz57PoeAQ9imjG+vbeof9LplljsL1mos4ccG6H9IjfrVGM359RozUnuFhpw==", + "dev": true, "license": "MIT", + "dependencies": { + "@typescript-eslint/types": "8.35.1", + "eslint-visitor-keys": "^4.2.1" + }, "engines": { - "node": "^12.17.0 || ^14.13 || >=16.0.0" + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" }, "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" } }, - "node_modules/colorette": { - "version": "2.0.20", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", - "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", - "license": "MIT" - }, - "node_modules/combined-stream": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", - "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "node_modules/abort-controller": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", + "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", "license": "MIT", "dependencies": { - "delayed-stream": "~1.0.0" + "event-target-shim": "^5.0.0" }, "engines": { - "node": ">= 0.8" - } - }, - "node_modules/commander": { - "version": "14.0.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-14.0.0.tgz", - "integrity": "sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==", - "license": "MIT", - "engines": { - "node": ">=20" + "node": ">=6.5" } }, - "node_modules/concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", - "dev": true, - "license": "MIT" - }, - "node_modules/content-disposition": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.0.0.tgz", - "integrity": "sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==", + "node_modules/accepts": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-2.0.0.tgz", + "integrity": "sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==", "license": "MIT", "dependencies": { - "safe-buffer": "5.2.1" + "mime-types": "^3.0.0", + "negotiator": "^1.0.0" }, "engines": { "node": ">= 0.6" } }, - "node_modules/content-type": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", - "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", + "node_modules/acorn": { + "version": "8.15.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", + "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", + "dev": true, "license": "MIT", + "bin": { + "acorn": "bin/acorn" + }, "engines": { - "node": ">= 0.6" + "node": ">=0.4.0" } }, - "node_modules/cookie": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.1.tgz", - "integrity": "sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==", + "node_modules/acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, "license": "MIT", - "engines": { - "node": ">= 0.6" + "peerDependencies": { + "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" } }, - "node_modules/cookie-signature": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.2.2.tgz", - "integrity": "sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==", + "node_modules/agent-base": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.3.tgz", + "integrity": "sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==", "license": "MIT", "engines": { - "node": ">=6.6.0" + "node": ">= 14" } }, - "node_modules/cors": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "node_modules/agentkeepalive": { + "version": "4.6.0", + "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.6.0.tgz", + "integrity": "sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==", "license": "MIT", "dependencies": { - "object-assign": "^4", - "vary": "^1" + "humanize-ms": "^1.2.1" }, "engines": { - "node": ">= 0.10" + "node": ">= 8.0.0" } }, - "node_modules/cross-spawn": { - "version": "7.0.6", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", - "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", - "license": "MIT", + "node_modules/ai": { + "version": "4.3.16", + "resolved": "https://registry.npmjs.org/ai/-/ai-4.3.16.tgz", + "integrity": "sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==", + "license": "Apache-2.0", "dependencies": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" + "@ai-sdk/provider": "1.1.3", + "@ai-sdk/provider-utils": "2.2.8", + "@ai-sdk/react": "1.2.12", + "@ai-sdk/ui-utils": "1.2.11", + "@opentelemetry/api": "1.9.0", + "jsondiffpatch": "0.6.0" }, "engines": { - "node": ">= 8" + "node": ">=18" + }, + "peerDependencies": { + "react": "^18 || ^19 || ^19.0.0-rc", + "zod": "^3.23.8" + }, + "peerDependenciesMeta": { + "react": { + "optional": true + } } }, - "node_modules/dateformat": { - "version": "4.6.3", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-4.6.3.tgz", - "integrity": "sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==", - "license": "MIT", - "engines": { - "node": "*" + "node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "license": "MIT", + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" } }, - "node_modules/debug": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.6.tgz", - "integrity": "sha512-O/09Bd4Z1fBrU4VzkhFqVgpPzaGbw6Sm9FEkBT1A/YBXQFGuuSxa1dN2nxgxS34JmKXqYx8CZAwEVoJFImUXIg==", + "node_modules/ansi-escapes": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-7.0.0.tgz", + "integrity": "sha512-GdYO7a61mR0fOlAsvC9/rIHf7L96sBc6dEWzeOu+KAea5bZyQRPIpojrVoI4AXGJS/ycu/fBTdLrUkA4ODrvjw==", + "dev": true, "license": "MIT", "dependencies": { - "ms": "2.1.2" + "environment": "^1.0.0" }, "engines": { - "node": ">=6.0" + "node": ">=18" }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/deepmerge": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", - "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", + "node_modules/ansi-regex": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", + "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", + "dev": true, "license": "MIT", - "peer": true, "engines": { - "node": ">=0.10.0" + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-regex?sponsor=1" } }, - "node_modules/delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "node_modules/ansi-styles": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.1.tgz", + "integrity": "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==", + "dev": true, "license": "MIT", "engines": { - "node": ">=0.4.0" + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } + "node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", + "dev": true, + "license": "Python-2.0" }, - "node_modules/dequal": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", - "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "node_modules/array-buffer-byte-length": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.2.tgz", + "integrity": "sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==", + "dev": true, "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "is-array-buffer": "^3.0.5" + }, "engines": { - "node": ">=6" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/destroy": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", - "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", + "node_modules/array-includes": { + "version": "3.1.9", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.9.tgz", + "integrity": "sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==", + "dev": true, "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.4", + "define-properties": "^1.2.1", + "es-abstract": "^1.24.0", + "es-object-atoms": "^1.1.1", + "get-intrinsic": "^1.3.0", + "is-string": "^1.1.1", + "math-intrinsics": "^1.1.0" + }, "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, - "node_modules/devtools-protocol": { - "version": "0.0.1464554", - "resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1464554.tgz", - "integrity": "sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==", - "license": "BSD-3-Clause" - }, - "node_modules/diff-match-patch": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/diff-match-patch/-/diff-match-patch-1.0.5.tgz", - "integrity": "sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==", - "license": "Apache-2.0" - }, - "node_modules/dotenv": { - "version": "16.4.7", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.4.7.tgz", - "integrity": "sha512-47qPchRCykZC03FhkYAhrvwU4xDBFIj1QPqaarj6mdM/hgUzfPHcpkHJOn3mJAufFeeAxAzeGsr5X0M4k6fLZQ==", - "license": "BSD-2-Clause", - "peer": true, - "engines": { - "node": ">=12" + "node": ">= 0.4" }, "funding": { - "url": "https://dotenvx.com" + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/dunder-proto": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", - "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", + "node_modules/array.prototype.findlast": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/array.prototype.findlast/-/array.prototype.findlast-1.2.5.tgz", + "integrity": "sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==", + "dev": true, "license": "MIT", "dependencies": { - "call-bind-apply-helpers": "^1.0.1", + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", "es-errors": "^1.3.0", - "gopd": "^1.2.0" + "es-object-atoms": "^1.0.0", + "es-shim-unscopables": "^1.0.2" }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/ecdsa-sig-formatter": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", - "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", - "license": "Apache-2.0", - "dependencies": { - "safe-buffer": "^5.0.1" - } - }, - "node_modules/ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", - "license": "MIT" - }, - "node_modules/encodeurl": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-2.0.0.tgz", - "integrity": "sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/end-of-stream": { - "version": "1.4.4", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", - "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "node_modules/array.prototype.flat": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.3.tgz", + "integrity": "sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==", + "dev": true, "license": "MIT", "dependencies": { - "once": "^1.4.0" - } - }, - "node_modules/es-define-property": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", - "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", - "license": "MIT", + "call-bind": "^1.0.8", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.5", + "es-shim-unscopables": "^1.0.2" + }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/es-errors": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", - "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "node_modules/array.prototype.flatmap": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.3.tgz", + "integrity": "sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==", + "dev": true, "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.5", + "es-shim-unscopables": "^1.0.2" + }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/es-object-atoms": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", - "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", + "node_modules/array.prototype.tosorted": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/array.prototype.tosorted/-/array.prototype.tosorted-1.1.4.tgz", + "integrity": "sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==", + "dev": true, "license": "MIT", "dependencies": { - "es-errors": "^1.3.0" + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.3", + "es-errors": "^1.3.0", + "es-shim-unscopables": "^1.0.2" }, "engines": { "node": ">= 0.4" } }, - "node_modules/es-set-tostringtag": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", - "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", + "node_modules/arraybuffer.prototype.slice": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.4.tgz", + "integrity": "sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==", + "dev": true, "license": "MIT", "dependencies": { + "array-buffer-byte-length": "^1.0.1", + "call-bind": "^1.0.8", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.5", "es-errors": "^1.3.0", "get-intrinsic": "^1.2.6", - "has-tostringtag": "^1.0.2", - "hasown": "^2.0.2" + "is-array-buffer": "^3.0.4" }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "license": "MIT" - }, - "node_modules/etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", + "node_modules/async-function": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/async-function/-/async-function-1.0.0.tgz", + "integrity": "sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==", + "dev": true, "license": "MIT", "engines": { - "node": ">= 0.6" + "node": ">= 0.4" } }, - "node_modules/event-target-shim": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", - "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", + "license": "MIT" + }, + "node_modules/atomic-sleep": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/atomic-sleep/-/atomic-sleep-1.0.0.tgz", + "integrity": "sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==", "license": "MIT", "engines": { - "node": ">=6" + "node": ">=8.0.0" } }, - "node_modules/eventsource": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/eventsource/-/eventsource-3.0.5.tgz", - "integrity": "sha512-LT/5J605bx5SNyE+ITBDiM3FxffBiq9un7Vx0EwMDM3vg8sWKx/tO2zC+LMqZ+smAM0F2hblaDZUVZF0te2pSw==", + "node_modules/available-typed-arrays": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", + "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", + "dev": true, "license": "MIT", "dependencies": { - "eventsource-parser": "^3.0.0" + "possible-typed-array-names": "^1.0.0" }, "engines": { - "node": ">=18.0.0" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/eventsource-parser": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.0.tgz", - "integrity": "sha512-T1C0XCUimhxVQzW4zFipdx0SficT651NnkR0ZSH3yQwh+mFMdLfgjABVi4YtMTtaL4s168593DaoaRLMqryavA==", - "license": "MIT", - "engines": { - "node": ">=18.0.0" - } + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true, + "license": "MIT" }, - "node_modules/express": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/express/-/express-5.0.1.tgz", - "integrity": "sha512-ORF7g6qGnD+YtUG9yx4DFoqCShNMmUKiXuT5oWMHiOvt/4WFbHC6yCwQMTSBMno7AqntNCAzzcnnjowRkTL9eQ==", - "license": "MIT", - "dependencies": { - "accepts": "^2.0.0", - "body-parser": "^2.0.1", - "content-disposition": "^1.0.0", - "content-type": "~1.0.4", - "cookie": "0.7.1", - "cookie-signature": "^1.2.1", - "debug": "4.3.6", - "depd": "2.0.0", - "encodeurl": "~2.0.0", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "^2.0.0", - "fresh": "2.0.0", - "http-errors": "2.0.0", - "merge-descriptors": "^2.0.0", - "methods": "~1.1.2", - "mime-types": "^3.0.0", - "on-finished": "2.4.1", - "once": "1.4.0", - "parseurl": "~1.3.3", - "proxy-addr": "~2.0.7", - "qs": "6.13.0", - "range-parser": "~1.2.1", - "router": "^2.0.0", - "safe-buffer": "5.2.1", - "send": "^1.1.0", - "serve-static": "^2.1.0", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "type-is": "^2.0.0", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/express-rate-limit": { - "version": "7.5.0", - "resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-7.5.0.tgz", - "integrity": "sha512-eB5zbQh5h+VenMPM3fh+nw1YExi5nMr6HUCR62ELSP11huvxm/Uir1H1QEyTkk5QX6A58pX6NmaTMceKZ0Eodg==", - "license": "MIT", - "engines": { - "node": ">= 16" - }, - "funding": { - "url": "https://github.com/sponsors/express-rate-limit" - }, - "peerDependencies": { - "express": "^4.11 || 5 || ^5.0.0-beta.1" - } - }, - "node_modules/extend": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", - "license": "MIT" - }, - "node_modules/fast-copy": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/fast-copy/-/fast-copy-3.0.2.tgz", - "integrity": "sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==", - "license": "MIT" - }, - "node_modules/fast-deep-equal": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "license": "MIT" - }, - "node_modules/fast-json-stable-stringify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "node_modules/base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], "license": "MIT" }, - "node_modules/fast-redact": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/fast-redact/-/fast-redact-3.5.0.tgz", - "integrity": "sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==", + "node_modules/bignumber.js": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.3.0.tgz", + "integrity": "sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==", "license": "MIT", "engines": { - "node": ">=6" - } - }, - "node_modules/fast-safe-stringify": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", - "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==", - "license": "MIT" - }, - "node_modules/fetch-cookie": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/fetch-cookie/-/fetch-cookie-3.1.0.tgz", - "integrity": "sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==", - "license": "Unlicense", - "dependencies": { - "set-cookie-parser": "^2.4.8", - "tough-cookie": "^5.0.0" + "node": "*" } }, - "node_modules/finalhandler": { + "node_modules/body-parser": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-2.1.0.tgz", - "integrity": "sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.1.0.tgz", + "integrity": "sha512-/hPxh61E+ll0Ujp24Ilm64cykicul1ypfwjVttduAiEdtnJFvLePSrIPk+HMImtNv5270wOGCb1Tns2rybMkoQ==", "license": "MIT", "dependencies": { + "bytes": "^3.1.2", + "content-type": "^1.0.5", "debug": "^4.4.0", - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", + "http-errors": "^2.0.0", + "iconv-lite": "^0.5.2", "on-finished": "^2.4.1", - "parseurl": "^1.3.3", - "statuses": "^2.0.1" + "qs": "^6.14.0", + "raw-body": "^3.0.0", + "type-is": "^2.0.0" }, "engines": { - "node": ">= 0.8" + "node": ">=18" } }, - "node_modules/finalhandler/node_modules/debug": { + "node_modules/body-parser/node_modules/debug": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", @@ -1224,161 +1462,2013 @@ } } }, - "node_modules/finalhandler/node_modules/ms": { + "node_modules/body-parser/node_modules/ms": { "version": "2.1.3", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", "license": "MIT" }, - "node_modules/form-data": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.2.tgz", - "integrity": "sha512-hGfm/slu0ZabnNt4oaRZ6uREyfCj6P4fT/n6A1rGV+Z0VdGXjfOhVUpkn6qVQONHGIFwmveGXyDs75+nr6FM8w==", + "node_modules/body-parser/node_modules/qs": { + "version": "6.14.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.14.0.tgz", + "integrity": "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==", + "license": "BSD-3-Clause", + "dependencies": { + "side-channel": "^1.1.0" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, "license": "MIT", "dependencies": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "es-set-tostringtag": "^2.1.0", - "mime-types": "^2.1.12" + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/braces": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", + "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", + "dev": true, + "license": "MIT", + "dependencies": { + "fill-range": "^7.1.1" }, "engines": { - "node": ">= 6" + "node": ">=8" } }, - "node_modules/form-data-encoder": { - "version": "1.7.2", - "resolved": "https://registry.npmjs.org/form-data-encoder/-/form-data-encoder-1.7.2.tgz", - "integrity": "sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==", - "license": "MIT" + "node_modules/buffer-equal-constant-time": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", + "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==", + "license": "BSD-3-Clause" }, - "node_modules/form-data/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", "license": "MIT", "engines": { - "node": ">= 0.6" + "node": ">= 0.8" } }, - "node_modules/form-data/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "node_modules/call-bind": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.8.tgz", + "integrity": "sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==", + "dev": true, "license": "MIT", "dependencies": { - "mime-db": "1.52.0" + "call-bind-apply-helpers": "^1.0.0", + "es-define-property": "^1.0.0", + "get-intrinsic": "^1.2.4", + "set-function-length": "^1.2.2" }, "engines": { - "node": ">= 0.6" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/formdata-node": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/formdata-node/-/formdata-node-4.4.1.tgz", - "integrity": "sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==", + "node_modules/call-bind-apply-helpers": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", + "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", "license": "MIT", "dependencies": { - "node-domexception": "1.0.0", - "web-streams-polyfill": "4.0.0-beta.3" + "es-errors": "^1.3.0", + "function-bind": "^1.1.2" }, "engines": { - "node": ">= 12.20" + "node": ">= 0.4" } }, - "node_modules/forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "node_modules/call-bound": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.4.tgz", + "integrity": "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==", "license": "MIT", + "dependencies": { + "call-bind-apply-helpers": "^1.0.2", + "get-intrinsic": "^1.3.0" + }, "engines": { - "node": ">= 0.6" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/fresh": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-2.0.0.tgz", - "integrity": "sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==", + "node_modules/callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true, "license": "MIT", "engines": { - "node": ">= 0.8" + "node": ">=6" } }, - "node_modules/fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", - "dev": true, - "license": "ISC" - }, - "node_modules/fsevents": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", - "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", - "hasInstallScript": true, - "license": "MIT", - "optional": true, + "node_modules/chalk": { + "version": "5.4.1", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", + "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", + "license": "MIT", + "engines": { + "node": "^12.17.0 || ^14.13 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/cli-cursor": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-5.0.0.tgz", + "integrity": "sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==", + "dev": true, + "license": "MIT", + "dependencies": { + "restore-cursor": "^5.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/cli-truncate": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-4.0.0.tgz", + "integrity": "sha512-nPdaFdQ0h/GEigbPClz11D0v/ZJEwxmeVZGeMo3Z5StPtUTkA9o1lD6QwoirYiSDzbcwn2XcjwmCp68W1IS4TA==", + "dev": true, + "license": "MIT", + "dependencies": { + "slice-ansi": "^5.0.0", + "string-width": "^7.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true, + "license": "MIT" + }, + "node_modules/colorette": { + "version": "2.0.20", + "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", + "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", + "license": "MIT" + }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "license": "MIT", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/commander": { + "version": "14.0.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-14.0.0.tgz", + "integrity": "sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==", + "license": "MIT", + "engines": { + "node": ">=20" + } + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true, + "license": "MIT" + }, + "node_modules/content-disposition": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.0.0.tgz", + "integrity": "sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==", + "license": "MIT", + "dependencies": { + "safe-buffer": "5.2.1" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/content-type": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", + "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie": { + "version": "0.7.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.1.tgz", + "integrity": "sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie-signature": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.2.2.tgz", + "integrity": "sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==", + "license": "MIT", + "engines": { + "node": ">=6.6.0" + } + }, + "node_modules/cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "license": "MIT", + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/cross-spawn": { + "version": "7.0.6", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", + "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", + "license": "MIT", + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/data-view-buffer": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.2.tgz", + "integrity": "sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "es-errors": "^1.3.0", + "is-data-view": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/data-view-byte-length": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.2.tgz", + "integrity": "sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "es-errors": "^1.3.0", + "is-data-view": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/inspect-js" + } + }, + "node_modules/data-view-byte-offset": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.1.tgz", + "integrity": "sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.2", + "es-errors": "^1.3.0", + "is-data-view": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/dateformat": { + "version": "4.6.3", + "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-4.6.3.tgz", + "integrity": "sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==", + "license": "MIT", + "engines": { + "node": "*" + } + }, + "node_modules/debug": { + "version": "4.3.6", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.6.tgz", + "integrity": "sha512-O/09Bd4Z1fBrU4VzkhFqVgpPzaGbw6Sm9FEkBT1A/YBXQFGuuSxa1dN2nxgxS34JmKXqYx8CZAwEVoJFImUXIg==", + "license": "MIT", + "dependencies": { + "ms": "2.1.2" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/deep-is": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", + "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/deepmerge": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", + "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", + "license": "MIT", + "peer": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/define-data-property": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", + "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", + "gopd": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/define-properties": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", + "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-data-property": "^1.0.1", + "has-property-descriptors": "^1.0.0", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "license": "MIT", + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/depd": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", + "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/destroy": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", + "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", + "license": "MIT", + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/devtools-protocol": { + "version": "0.0.1464554", + "resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1464554.tgz", + "integrity": "sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==", + "license": "BSD-3-Clause" + }, + "node_modules/diff-match-patch": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/diff-match-patch/-/diff-match-patch-1.0.5.tgz", + "integrity": "sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==", + "license": "Apache-2.0" + }, + "node_modules/doctrine": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/dotenv": { + "version": "16.6.1", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.6.1.tgz", + "integrity": "sha512-uBq4egWHTcTt33a72vpSG0z3HnPuIl6NqYcTrKEg2azoEyl2hpW0zqlxysq2pK9HlDIHyHyakeYaYnSAwd8bow==", + "license": "BSD-2-Clause", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://dotenvx.com" + } + }, + "node_modules/dunder-proto": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", + "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", + "license": "MIT", + "dependencies": { + "call-bind-apply-helpers": "^1.0.1", + "es-errors": "^1.3.0", + "gopd": "^1.2.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/ecdsa-sig-formatter": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", + "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", + "license": "Apache-2.0", + "dependencies": { + "safe-buffer": "^5.0.1" + } + }, + "node_modules/ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", + "license": "MIT" + }, + "node_modules/emoji-regex": { + "version": "10.4.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.4.0.tgz", + "integrity": "sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw==", + "dev": true, + "license": "MIT" + }, + "node_modules/encodeurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-2.0.0.tgz", + "integrity": "sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "license": "MIT", + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/environment": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/environment/-/environment-1.1.0.tgz", + "integrity": "sha512-xUtoPkMggbz0MPyPiIWr1Kp4aeWJjDZ6SMvURhimjdZgsRuDplF5/s9hcgGhyXMhs+6vpnuoiZ2kFiu3FMnS8Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/es-abstract": { + "version": "1.24.0", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.0.tgz", + "integrity": "sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-buffer-byte-length": "^1.0.2", + "arraybuffer.prototype.slice": "^1.0.4", + "available-typed-arrays": "^1.0.7", + "call-bind": "^1.0.8", + "call-bound": "^1.0.4", + "data-view-buffer": "^1.0.2", + "data-view-byte-length": "^1.0.2", + "data-view-byte-offset": "^1.0.1", + "es-define-property": "^1.0.1", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.1.1", + "es-set-tostringtag": "^2.1.0", + "es-to-primitive": "^1.3.0", + "function.prototype.name": "^1.1.8", + "get-intrinsic": "^1.3.0", + "get-proto": "^1.0.1", + "get-symbol-description": "^1.1.0", + "globalthis": "^1.0.4", + "gopd": "^1.2.0", + "has-property-descriptors": "^1.0.2", + "has-proto": "^1.2.0", + "has-symbols": "^1.1.0", + "hasown": "^2.0.2", + "internal-slot": "^1.1.0", + "is-array-buffer": "^3.0.5", + "is-callable": "^1.2.7", + "is-data-view": "^1.0.2", + "is-negative-zero": "^2.0.3", + "is-regex": "^1.2.1", + "is-set": "^2.0.3", + "is-shared-array-buffer": "^1.0.4", + "is-string": "^1.1.1", + "is-typed-array": "^1.1.15", + "is-weakref": "^1.1.1", + "math-intrinsics": "^1.1.0", + "object-inspect": "^1.13.4", + "object-keys": "^1.1.1", + "object.assign": "^4.1.7", + "own-keys": "^1.0.1", + "regexp.prototype.flags": "^1.5.4", + "safe-array-concat": "^1.1.3", + "safe-push-apply": "^1.0.0", + "safe-regex-test": "^1.1.0", + "set-proto": "^1.0.0", + "stop-iteration-iterator": "^1.1.0", + "string.prototype.trim": "^1.2.10", + "string.prototype.trimend": "^1.0.9", + "string.prototype.trimstart": "^1.0.8", + "typed-array-buffer": "^1.0.3", + "typed-array-byte-length": "^1.0.3", + "typed-array-byte-offset": "^1.0.4", + "typed-array-length": "^1.0.7", + "unbox-primitive": "^1.1.0", + "which-typed-array": "^1.1.19" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/es-define-property": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", + "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-errors": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", + "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-iterator-helpers": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.2.1.tgz", + "integrity": "sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.3", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.6", + "es-errors": "^1.3.0", + "es-set-tostringtag": "^2.0.3", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.6", + "globalthis": "^1.0.4", + "gopd": "^1.2.0", + "has-property-descriptors": "^1.0.2", + "has-proto": "^1.2.0", + "has-symbols": "^1.1.0", + "internal-slot": "^1.1.0", + "iterator.prototype": "^1.1.4", + "safe-array-concat": "^1.1.3" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-object-atoms": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", + "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-set-tostringtag": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", + "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.6", + "has-tostringtag": "^1.0.2", + "hasown": "^2.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-shim-unscopables": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.1.0.tgz", + "integrity": "sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==", + "dev": true, + "license": "MIT", + "dependencies": { + "hasown": "^2.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-to-primitive": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.3.0.tgz", + "integrity": "sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-callable": "^1.2.7", + "is-date-object": "^1.0.5", + "is-symbol": "^1.0.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", + "license": "MIT" + }, + "node_modules/escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/eslint": { + "version": "9.30.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.30.0.tgz", + "integrity": "sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@eslint-community/eslint-utils": "^4.2.0", + "@eslint-community/regexpp": "^4.12.1", + "@eslint/config-array": "^0.21.0", + "@eslint/config-helpers": "^0.3.0", + "@eslint/core": "^0.14.0", + "@eslint/eslintrc": "^3.3.1", + "@eslint/js": "9.30.0", + "@eslint/plugin-kit": "^0.3.1", + "@humanfs/node": "^0.16.6", + "@humanwhocodes/module-importer": "^1.0.1", + "@humanwhocodes/retry": "^0.4.2", + "@types/estree": "^1.0.6", + "@types/json-schema": "^7.0.15", + "ajv": "^6.12.4", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.6", + "debug": "^4.3.2", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^8.4.0", + "eslint-visitor-keys": "^4.2.1", + "espree": "^10.4.0", + "esquery": "^1.5.0", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^8.0.0", + "find-up": "^5.0.0", + "glob-parent": "^6.0.2", + "ignore": "^5.2.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.1.2", + "natural-compare": "^1.4.0", + "optionator": "^0.9.3" + }, + "bin": { + "eslint": "bin/eslint.js" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://eslint.org/donate" + }, + "peerDependencies": { + "jiti": "*" + }, + "peerDependenciesMeta": { + "jiti": { + "optional": true + } + } + }, + "node_modules/eslint-plugin-react": { + "version": "7.37.5", + "resolved": "https://registry.npmjs.org/eslint-plugin-react/-/eslint-plugin-react-7.37.5.tgz", + "integrity": "sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-includes": "^3.1.8", + "array.prototype.findlast": "^1.2.5", + "array.prototype.flatmap": "^1.3.3", + "array.prototype.tosorted": "^1.1.4", + "doctrine": "^2.1.0", + "es-iterator-helpers": "^1.2.1", + "estraverse": "^5.3.0", + "hasown": "^2.0.2", + "jsx-ast-utils": "^2.4.1 || ^3.0.0", + "minimatch": "^3.1.2", + "object.entries": "^1.1.9", + "object.fromentries": "^2.0.8", + "object.values": "^1.2.1", + "prop-types": "^15.8.1", + "resolve": "^2.0.0-next.5", + "semver": "^6.3.1", + "string.prototype.matchall": "^4.0.12", + "string.prototype.repeat": "^1.0.0" + }, + "engines": { + "node": ">=4" + }, + "peerDependencies": { + "eslint": "^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7" + } + }, + "node_modules/eslint-plugin-react/node_modules/resolve": { + "version": "2.0.0-next.5", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", + "integrity": "sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-core-module": "^2.13.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/eslint-scope": { + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-8.4.0.tgz", + "integrity": "sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint-visitor-keys": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", + "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "license": "MIT", + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/eslint/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/espree": { + "version": "10.4.0", + "resolved": "https://registry.npmjs.org/espree/-/espree-10.4.0.tgz", + "integrity": "sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "acorn": "^8.15.0", + "acorn-jsx": "^5.3.2", + "eslint-visitor-keys": "^4.2.1" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/esquery": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.6.0.tgz", + "integrity": "sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "estraverse": "^5.1.0" + }, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "estraverse": "^5.2.0" + }, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/event-target-shim": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", + "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/eventemitter3": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.1.tgz", + "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==", + "dev": true, + "license": "MIT" + }, + "node_modules/eventsource": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/eventsource/-/eventsource-3.0.5.tgz", + "integrity": "sha512-LT/5J605bx5SNyE+ITBDiM3FxffBiq9un7Vx0EwMDM3vg8sWKx/tO2zC+LMqZ+smAM0F2hblaDZUVZF0te2pSw==", + "license": "MIT", + "dependencies": { + "eventsource-parser": "^3.0.0" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/eventsource-parser": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.0.tgz", + "integrity": "sha512-T1C0XCUimhxVQzW4zFipdx0SficT651NnkR0ZSH3yQwh+mFMdLfgjABVi4YtMTtaL4s168593DaoaRLMqryavA==", + "license": "MIT", + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/express": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/express/-/express-5.0.1.tgz", + "integrity": "sha512-ORF7g6qGnD+YtUG9yx4DFoqCShNMmUKiXuT5oWMHiOvt/4WFbHC6yCwQMTSBMno7AqntNCAzzcnnjowRkTL9eQ==", + "license": "MIT", + "dependencies": { + "accepts": "^2.0.0", + "body-parser": "^2.0.1", + "content-disposition": "^1.0.0", + "content-type": "~1.0.4", + "cookie": "0.7.1", + "cookie-signature": "^1.2.1", + "debug": "4.3.6", + "depd": "2.0.0", + "encodeurl": "~2.0.0", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "^2.0.0", + "fresh": "2.0.0", + "http-errors": "2.0.0", + "merge-descriptors": "^2.0.0", + "methods": "~1.1.2", + "mime-types": "^3.0.0", + "on-finished": "2.4.1", + "once": "1.4.0", + "parseurl": "~1.3.3", + "proxy-addr": "~2.0.7", + "qs": "6.13.0", + "range-parser": "~1.2.1", + "router": "^2.0.0", + "safe-buffer": "5.2.1", + "send": "^1.1.0", + "serve-static": "^2.1.0", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "type-is": "^2.0.0", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 18" + } + }, + "node_modules/express-rate-limit": { + "version": "7.5.0", + "resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-7.5.0.tgz", + "integrity": "sha512-eB5zbQh5h+VenMPM3fh+nw1YExi5nMr6HUCR62ELSP11huvxm/Uir1H1QEyTkk5QX6A58pX6NmaTMceKZ0Eodg==", + "license": "MIT", + "engines": { + "node": ">= 16" + }, + "funding": { + "url": "https://github.com/sponsors/express-rate-limit" + }, + "peerDependencies": { + "express": "^4.11 || 5 || ^5.0.0-beta.1" + } + }, + "node_modules/extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "license": "MIT" + }, + "node_modules/fast-copy": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/fast-copy/-/fast-copy-3.0.2.tgz", + "integrity": "sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==", + "license": "MIT" + }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "license": "MIT" + }, + "node_modules/fast-glob": { + "version": "3.3.3", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.3.tgz", + "integrity": "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.8" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/fast-glob/node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "license": "ISC", + "dependencies": { + "is-glob": "^4.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "license": "MIT" + }, + "node_modules/fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", + "dev": true, + "license": "MIT" + }, + "node_modules/fast-redact": { + "version": "3.5.0", + "resolved": "https://registry.npmjs.org/fast-redact/-/fast-redact-3.5.0.tgz", + "integrity": "sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/fast-safe-stringify": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", + "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==", + "license": "MIT" + }, + "node_modules/fastq": { + "version": "1.19.1", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.19.1.tgz", + "integrity": "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==", + "dev": true, + "license": "ISC", + "dependencies": { + "reusify": "^1.0.4" + } + }, + "node_modules/fetch-cookie": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/fetch-cookie/-/fetch-cookie-3.1.0.tgz", + "integrity": "sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==", + "license": "Unlicense", + "dependencies": { + "set-cookie-parser": "^2.4.8", + "tough-cookie": "^5.0.0" + } + }, + "node_modules/file-entry-cache": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-8.0.0.tgz", + "integrity": "sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "flat-cache": "^4.0.0" + }, + "engines": { + "node": ">=16.0.0" + } + }, + "node_modules/fill-range": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", + "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", + "dev": true, + "license": "MIT", + "dependencies": { + "to-regex-range": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/finalhandler": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-2.1.0.tgz", + "integrity": "sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==", + "license": "MIT", + "dependencies": { + "debug": "^4.4.0", + "encodeurl": "^2.0.0", + "escape-html": "^1.0.3", + "on-finished": "^2.4.1", + "parseurl": "^1.3.3", + "statuses": "^2.0.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/finalhandler/node_modules/debug": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", + "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/finalhandler/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "license": "MIT" + }, + "node_modules/find-up": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", + "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", + "dev": true, + "license": "MIT", + "dependencies": { + "locate-path": "^6.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/flat-cache": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-4.0.1.tgz", + "integrity": "sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==", + "dev": true, + "license": "MIT", + "dependencies": { + "flatted": "^3.2.9", + "keyv": "^4.5.4" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/flatted": { + "version": "3.3.3", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.3.3.tgz", + "integrity": "sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==", + "dev": true, + "license": "ISC" + }, + "node_modules/for-each": { + "version": "0.3.5", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.5.tgz", + "integrity": "sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-callable": "^1.2.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/form-data": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.2.tgz", + "integrity": "sha512-hGfm/slu0ZabnNt4oaRZ6uREyfCj6P4fT/n6A1rGV+Z0VdGXjfOhVUpkn6qVQONHGIFwmveGXyDs75+nr6FM8w==", + "license": "MIT", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "es-set-tostringtag": "^2.1.0", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/form-data-encoder": { + "version": "1.7.2", + "resolved": "https://registry.npmjs.org/form-data-encoder/-/form-data-encoder-1.7.2.tgz", + "integrity": "sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==", + "license": "MIT" + }, + "node_modules/form-data/node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/form-data/node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/formdata-node": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/formdata-node/-/formdata-node-4.4.1.tgz", + "integrity": "sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==", + "license": "MIT", + "dependencies": { + "node-domexception": "1.0.0", + "web-streams-polyfill": "4.0.0-beta.3" + }, + "engines": { + "node": ">= 12.20" + } + }, + "node_modules/forwarded": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fresh": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-2.0.0.tgz", + "integrity": "sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", + "dev": true, + "license": "ISC" + }, + "node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "hasInstallScript": true, + "license": "MIT", + "optional": true, "os": [ "darwin" ], "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", + "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/function.prototype.name": { + "version": "1.1.8", + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.8.tgz", + "integrity": "sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.3", + "define-properties": "^1.2.1", + "functions-have-names": "^1.2.3", + "hasown": "^2.0.2", + "is-callable": "^1.2.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/functions-have-names": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", + "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/gaxios": { + "version": "6.7.1", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-6.7.1.tgz", + "integrity": "sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==", + "license": "Apache-2.0", + "dependencies": { + "extend": "^3.0.2", + "https-proxy-agent": "^7.0.1", + "is-stream": "^2.0.0", + "node-fetch": "^2.6.9", + "uuid": "^9.0.1" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/gcp-metadata": { + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-6.1.1.tgz", + "integrity": "sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==", + "license": "Apache-2.0", + "dependencies": { + "gaxios": "^6.1.1", + "google-logging-utils": "^0.0.2", + "json-bigint": "^1.0.0" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/get-east-asian-width": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/get-east-asian-width/-/get-east-asian-width-1.3.0.tgz", + "integrity": "sha512-vpeMIQKxczTD/0s2CdEWHcb0eeJe6TFjxb+J5xgX7hScxqrGuyjmv4c1D4A/gelKfyox0gJJwIHF+fLjeaM8kQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/get-intrinsic": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", + "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", + "license": "MIT", + "dependencies": { + "call-bind-apply-helpers": "^1.0.2", + "es-define-property": "^1.0.1", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.1.1", + "function-bind": "^1.1.2", + "get-proto": "^1.0.1", + "gopd": "^1.2.0", + "has-symbols": "^1.1.0", + "hasown": "^2.0.2", + "math-intrinsics": "^1.1.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-proto": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", + "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", + "license": "MIT", + "dependencies": { + "dunder-proto": "^1.0.1", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/get-symbol-description": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.1.0.tgz", + "integrity": "sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.6" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "deprecated": "Glob versions prior to v9 are no longer supported", + "dev": true, + "license": "ISC", + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", + "dev": true, + "license": "ISC", + "dependencies": { + "is-glob": "^4.0.3" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/globals": { + "version": "16.2.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-16.2.0.tgz", + "integrity": "sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/globalthis": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.4.tgz", + "integrity": "sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-properties": "^1.2.1", + "gopd": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/google-auth-library": { + "version": "9.15.1", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-9.15.1.tgz", + "integrity": "sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==", + "license": "Apache-2.0", + "dependencies": { + "base64-js": "^1.3.0", + "ecdsa-sig-formatter": "^1.0.11", + "gaxios": "^6.1.1", + "gcp-metadata": "^6.1.0", + "gtoken": "^7.0.0", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/google-logging-utils": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-0.0.2.tgz", + "integrity": "sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==", + "license": "Apache-2.0", + "engines": { + "node": ">=14" + } + }, + "node_modules/gopd": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", + "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/graphemer": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/graphemer/-/graphemer-1.4.0.tgz", + "integrity": "sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==", + "dev": true, + "license": "MIT" + }, + "node_modules/gtoken": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-7.1.0.tgz", + "integrity": "sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==", + "license": "MIT", + "dependencies": { + "gaxios": "^6.0.0", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=14.0.0" } }, - "node_modules/function-bind": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", - "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "node_modules/has-bigints": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz", + "integrity": "sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, + "node_modules/has-property-descriptors": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", + "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-define-property": "^1.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-proto": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.2.0.tgz", + "integrity": "sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "dunder-proto": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-symbols": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", + "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-tostringtag": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", + "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", + "license": "MIT", + "dependencies": { + "has-symbols": "^1.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/hasown": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", + "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", + "license": "MIT", + "dependencies": { + "function-bind": "^1.1.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/help-me": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/help-me/-/help-me-5.0.0.tgz", + "integrity": "sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==", + "license": "MIT" + }, + "node_modules/http-errors": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", + "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", + "license": "MIT", + "dependencies": { + "depd": "2.0.0", + "inherits": "2.0.4", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "toidentifier": "1.0.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/https-proxy-agent": { + "version": "7.0.6", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", + "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", + "license": "MIT", + "dependencies": { + "agent-base": "^7.1.2", + "debug": "4" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/humanize-ms": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", + "integrity": "sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==", + "license": "MIT", + "dependencies": { + "ms": "^2.0.0" + } + }, + "node_modules/husky": { + "version": "9.1.7", + "resolved": "https://registry.npmjs.org/husky/-/husky-9.1.7.tgz", + "integrity": "sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==", + "dev": true, + "license": "MIT", + "bin": { + "husky": "bin.js" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/typicode" + } + }, + "node_modules/iconv-lite": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.5.2.tgz", + "integrity": "sha512-kERHXvpSaB4aU3eANwidg79K8FlrN77m8G9V+0vOR3HYaRifrlwMEpT7ZBJqLSEIHnEgJTHcWK82wwLwwKwtag==", + "license": "MIT", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/ignore": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz", + "integrity": "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 4" + } + }, + "node_modules/import-fresh": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.1.tgz", + "integrity": "sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.8.19" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", + "deprecated": "This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.", + "dev": true, + "license": "ISC", + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "license": "ISC" + }, + "node_modules/internal-slot": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz", + "integrity": "sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "hasown": "^2.0.2", + "side-channel": "^1.1.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/interpret": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", + "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/ipaddr.js": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", + "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", + "license": "MIT", + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/is-array-buffer": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.5.tgz", + "integrity": "sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.3", + "get-intrinsic": "^1.2.6" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-async-function": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-async-function/-/is-async-function-2.1.1.tgz", + "integrity": "sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==", + "dev": true, "license": "MIT", + "dependencies": { + "async-function": "^1.0.0", + "call-bound": "^1.0.3", + "get-proto": "^1.0.1", + "has-tostringtag": "^1.0.2", + "safe-regex-test": "^1.1.0" + }, + "engines": { + "node": ">= 0.4" + }, "funding": { "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/gaxios": { - "version": "6.7.1", - "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-6.7.1.tgz", - "integrity": "sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==", - "license": "Apache-2.0", + "node_modules/is-bigint": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.1.0.tgz", + "integrity": "sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==", + "dev": true, + "license": "MIT", "dependencies": { - "extend": "^3.0.2", - "https-proxy-agent": "^7.0.1", - "is-stream": "^2.0.0", - "node-fetch": "^2.6.9", - "uuid": "^9.0.1" + "has-bigints": "^1.0.2" }, "engines": { - "node": ">=14" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/gcp-metadata": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-6.1.1.tgz", - "integrity": "sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==", - "license": "Apache-2.0", + "node_modules/is-boolean-object": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.2.2.tgz", + "integrity": "sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==", + "dev": true, + "license": "MIT", "dependencies": { - "gaxios": "^6.1.1", - "google-logging-utils": "^0.0.2", - "json-bigint": "^1.0.0" + "call-bound": "^1.0.3", + "has-tostringtag": "^1.0.2" }, "engines": { - "node": ">=14" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/get-intrinsic": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", - "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", + "node_modules/is-callable": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", + "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-core-module": { + "version": "2.16.1", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.1.tgz", + "integrity": "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==", + "dev": true, "license": "MIT", "dependencies": { - "call-bind-apply-helpers": "^1.0.2", - "es-define-property": "^1.0.1", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.1.1", - "function-bind": "^1.1.2", - "get-proto": "^1.0.1", - "gopd": "^1.2.0", - "has-symbols": "^1.1.0", - "hasown": "^2.0.2", - "math-intrinsics": "^1.1.0" + "hasown": "^2.0.2" }, "engines": { "node": ">= 0.4" @@ -1387,72 +3477,92 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/get-proto": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", - "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", + "node_modules/is-data-view": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-data-view/-/is-data-view-1.0.2.tgz", + "integrity": "sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==", + "dev": true, "license": "MIT", "dependencies": { - "dunder-proto": "^1.0.1", - "es-object-atoms": "^1.0.0" + "call-bound": "^1.0.2", + "get-intrinsic": "^1.2.6", + "is-typed-array": "^1.1.13" }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/glob": { - "version": "7.2.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", - "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "deprecated": "Glob versions prior to v9 are no longer supported", + "node_modules/is-date-object": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.1.0.tgz", + "integrity": "sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==", "dev": true, - "license": "ISC", + "license": "MIT", "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.1.1", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "call-bound": "^1.0.2", + "has-tostringtag": "^1.0.2" }, "engines": { - "node": "*" + "node": ">= 0.4" }, "funding": { - "url": "https://github.com/sponsors/isaacs" + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/google-auth-library": { - "version": "9.15.1", - "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-9.15.1.tgz", - "integrity": "sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==", - "license": "Apache-2.0", + "node_modules/is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-finalizationregistry": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/is-finalizationregistry/-/is-finalizationregistry-1.1.1.tgz", + "integrity": "sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==", + "dev": true, + "license": "MIT", "dependencies": { - "base64-js": "^1.3.0", - "ecdsa-sig-formatter": "^1.0.11", - "gaxios": "^6.1.1", - "gcp-metadata": "^6.1.0", - "gtoken": "^7.0.0", - "jws": "^4.0.0" + "call-bound": "^1.0.3" }, "engines": { - "node": ">=14" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/google-logging-utils": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-0.0.2.tgz", - "integrity": "sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==", - "license": "Apache-2.0", + "node_modules/is-fullwidth-code-point": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-4.0.0.tgz", + "integrity": "sha512-O4L094N2/dZ7xqVdrXhh9r1KODPJpFms8B5sGdJLPy664AgvXsreZUyCQQNItZRDlYug4xStLjNp/sz3HvBowQ==", + "dev": true, + "license": "MIT", "engines": { - "node": ">=14" + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/gopd": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", - "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", + "node_modules/is-generator-function": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.1.0.tgz", + "integrity": "sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==", + "dev": true, "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "get-proto": "^1.0.0", + "has-tostringtag": "^1.0.2", + "safe-regex-test": "^1.1.0" + }, "engines": { "node": ">= 0.4" }, @@ -1460,23 +3570,24 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/gtoken": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-7.1.0.tgz", - "integrity": "sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==", + "node_modules/is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, "license": "MIT", "dependencies": { - "gaxios": "^6.0.0", - "jws": "^4.0.0" + "is-extglob": "^2.1.1" }, "engines": { - "node": ">=14.0.0" + "node": ">=0.10.0" } }, - "node_modules/has-symbols": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", - "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", + "node_modules/is-map": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.3.tgz", + "integrity": "sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==", + "dev": true, "license": "MIT", "engines": { "node": ">= 0.4" @@ -1485,14 +3596,12 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/has-tostringtag": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", - "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", + "node_modules/is-negative-zero": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz", + "integrity": "sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==", + "dev": true, "license": "MIT", - "dependencies": { - "has-symbols": "^1.0.3" - }, "engines": { "node": ">= 0.4" }, @@ -1500,119 +3609,171 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/hasown": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", - "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", + "node_modules/is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.12.0" + } + }, + "node_modules/is-number-object": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.1.1.tgz", + "integrity": "sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==", + "dev": true, "license": "MIT", "dependencies": { - "function-bind": "^1.1.2" + "call-bound": "^1.0.3", + "has-tostringtag": "^1.0.2" }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/help-me": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/help-me/-/help-me-5.0.0.tgz", - "integrity": "sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==", + "node_modules/is-promise": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-4.0.0.tgz", + "integrity": "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==", "license": "MIT" }, - "node_modules/http-errors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", - "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", + "node_modules/is-regex": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.2.1.tgz", + "integrity": "sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==", + "dev": true, "license": "MIT", "dependencies": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" + "call-bound": "^1.0.2", + "gopd": "^1.2.0", + "has-tostringtag": "^1.0.2", + "hasown": "^2.0.2" }, "engines": { - "node": ">= 0.8" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/https-proxy-agent": { - "version": "7.0.6", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", - "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", + "node_modules/is-set": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/is-set/-/is-set-2.0.3.tgz", + "integrity": "sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==", + "dev": true, "license": "MIT", - "dependencies": { - "agent-base": "^7.1.2", - "debug": "4" - }, "engines": { - "node": ">= 14" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/humanize-ms": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", - "integrity": "sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==", + "node_modules/is-shared-array-buffer": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.4.tgz", + "integrity": "sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==", + "dev": true, "license": "MIT", "dependencies": { - "ms": "^2.0.0" + "call-bound": "^1.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/iconv-lite": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.5.2.tgz", - "integrity": "sha512-kERHXvpSaB4aU3eANwidg79K8FlrN77m8G9V+0vOR3HYaRifrlwMEpT7ZBJqLSEIHnEgJTHcWK82wwLwwKwtag==", + "node_modules/is-stream": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "license": "MIT", + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-string": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.1.1.tgz", + "integrity": "sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==", + "dev": true, "license": "MIT", "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" + "call-bound": "^1.0.3", + "has-tostringtag": "^1.0.2" }, "engines": { - "node": ">=0.10.0" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", - "deprecated": "This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.", + "node_modules/is-symbol": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.1.1.tgz", + "integrity": "sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==", "dev": true, - "license": "ISC", + "license": "MIT", "dependencies": { - "once": "^1.3.0", - "wrappy": "1" + "call-bound": "^1.0.2", + "has-symbols": "^1.1.0", + "safe-regex-test": "^1.1.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "license": "ISC" - }, - "node_modules/interpret": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", - "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", + "node_modules/is-typed-array": { + "version": "1.1.15", + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.15.tgz", + "integrity": "sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==", "dev": true, "license": "MIT", + "dependencies": { + "which-typed-array": "^1.1.16" + }, "engines": { - "node": ">= 0.10" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/ipaddr.js": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", - "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", + "node_modules/is-weakmap": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.2.tgz", + "integrity": "sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==", + "dev": true, "license": "MIT", "engines": { - "node": ">= 0.10" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/is-core-module": { - "version": "2.16.1", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.1.tgz", - "integrity": "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==", + "node_modules/is-weakref": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.1.1.tgz", + "integrity": "sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==", "dev": true, "license": "MIT", "dependencies": { - "hasown": "^2.0.2" + "call-bound": "^1.0.3" }, "engines": { "node": ">= 0.4" @@ -1621,30 +3782,54 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/is-promise": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-4.0.0.tgz", - "integrity": "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==", - "license": "MIT" - }, - "node_modules/is-stream": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", - "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "node_modules/is-weakset": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.4.tgz", + "integrity": "sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==", + "dev": true, "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "get-intrinsic": "^1.2.6" + }, "engines": { - "node": ">=8" + "node": ">= 0.4" }, "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/isarray": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", + "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", + "dev": true, + "license": "MIT" + }, "node_modules/isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", "license": "ISC" }, + "node_modules/iterator.prototype": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/iterator.prototype/-/iterator.prototype-1.1.5.tgz", + "integrity": "sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-data-property": "^1.1.4", + "es-object-atoms": "^1.0.0", + "get-intrinsic": "^1.2.6", + "get-proto": "^1.0.0", + "has-symbols": "^1.1.0", + "set-function-name": "^2.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, "node_modules/joycon": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/joycon/-/joycon-3.1.1.tgz", @@ -1654,6 +3839,26 @@ "node": ">=10" } }, + "node_modules/js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dev": true, + "license": "MIT", + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, "node_modules/json-bigint": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", @@ -1663,6 +3868,13 @@ "bignumber.js": "^9.0.0" } }, + "node_modules/json-buffer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", + "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", + "dev": true, + "license": "MIT" + }, "node_modules/json-schema": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", @@ -1675,6 +3887,13 @@ "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", "license": "MIT" }, + "node_modules/json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==", + "dev": true, + "license": "MIT" + }, "node_modules/jsondiffpatch": { "version": "0.6.0", "resolved": "https://registry.npmjs.org/jsondiffpatch/-/jsondiffpatch-0.6.0.tgz", @@ -1692,6 +3911,22 @@ "node": "^18.0.0 || >=20.0.0" } }, + "node_modules/jsx-ast-utils": { + "version": "3.3.5", + "resolved": "https://registry.npmjs.org/jsx-ast-utils/-/jsx-ast-utils-3.3.5.tgz", + "integrity": "sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "array-includes": "^3.1.6", + "array.prototype.flat": "^1.3.1", + "object.assign": "^4.1.4", + "object.values": "^1.1.6" + }, + "engines": { + "node": ">=4.0" + } + }, "node_modules/jwa": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.1.tgz", @@ -1713,6 +3948,203 @@ "safe-buffer": "^5.0.1" } }, + "node_modules/keyv": { + "version": "4.5.4", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", + "integrity": "sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==", + "dev": true, + "license": "MIT", + "dependencies": { + "json-buffer": "3.0.1" + } + }, + "node_modules/levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/lilconfig": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.3.tgz", + "integrity": "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/sponsors/antonk52" + } + }, + "node_modules/lint-staged": { + "version": "16.1.2", + "resolved": "https://registry.npmjs.org/lint-staged/-/lint-staged-16.1.2.tgz", + "integrity": "sha512-sQKw2Si2g9KUZNY3XNvRuDq4UJqpHwF0/FQzZR2M7I5MvtpWvibikCjUVJzZdGE0ByurEl3KQNvsGetd1ty1/Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "chalk": "^5.4.1", + "commander": "^14.0.0", + "debug": "^4.4.1", + "lilconfig": "^3.1.3", + "listr2": "^8.3.3", + "micromatch": "^4.0.8", + "nano-spawn": "^1.0.2", + "pidtree": "^0.6.0", + "string-argv": "^0.3.2", + "yaml": "^2.8.0" + }, + "bin": { + "lint-staged": "bin/lint-staged.js" + }, + "engines": { + "node": ">=20.17" + }, + "funding": { + "url": "https://opencollective.com/lint-staged" + } + }, + "node_modules/lint-staged/node_modules/debug": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.1.tgz", + "integrity": "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/lint-staged/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "dev": true, + "license": "MIT" + }, + "node_modules/listr2": { + "version": "8.3.3", + "resolved": "https://registry.npmjs.org/listr2/-/listr2-8.3.3.tgz", + "integrity": "sha512-LWzX2KsqcB1wqQ4AHgYb4RsDXauQiqhjLk+6hjbaeHG4zpjjVAB6wC/gz6X0l+Du1cN3pUB5ZlrvTbhGSNnUQQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "cli-truncate": "^4.0.0", + "colorette": "^2.0.20", + "eventemitter3": "^5.0.1", + "log-update": "^6.1.0", + "rfdc": "^1.4.1", + "wrap-ansi": "^9.0.0" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/locate-path": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", + "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", + "dev": true, + "license": "MIT", + "dependencies": { + "p-locate": "^5.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/log-update": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/log-update/-/log-update-6.1.0.tgz", + "integrity": "sha512-9ie8ItPR6tjY5uYJh8K/Zrv/RMZ5VOlOWvtZdEHYSTFKZfIBPQa9tOAEeAWhd+AnIneLJ22w5fjOYtoutpWq5w==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-escapes": "^7.0.0", + "cli-cursor": "^5.0.0", + "slice-ansi": "^7.1.0", + "strip-ansi": "^7.1.0", + "wrap-ansi": "^9.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/log-update/node_modules/is-fullwidth-code-point": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-5.0.0.tgz", + "integrity": "sha512-OVa3u9kkBbw7b8Xw5F9P+D/T9X+Z4+JruYVNapTjPYZYUznQ5YfWeFkOj606XYYW8yugTfC8Pj0hYqvi4ryAhA==", + "dev": true, + "license": "MIT", + "dependencies": { + "get-east-asian-width": "^1.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/log-update/node_modules/slice-ansi": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-7.1.0.tgz", + "integrity": "sha512-bSiSngZ/jWeX93BqeIAbImyTbEihizcwNjFoRUIY/T1wWQsfsm2Vw1agPKylXvQTU7iASGdHhyqRlqQzfz+Htg==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-styles": "^6.2.1", + "is-fullwidth-code-point": "^5.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/chalk/slice-ansi?sponsor=1" + } + }, + "node_modules/loose-envify": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", + "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "js-tokens": "^3.0.0 || ^4.0.0" + }, + "bin": { + "loose-envify": "cli.js" + } + }, "node_modules/math-intrinsics": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", @@ -1743,6 +4175,16 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 8" + } + }, "node_modules/methods": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", @@ -1752,6 +4194,20 @@ "node": ">= 0.6" } }, + "node_modules/micromatch": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", + "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", + "dev": true, + "license": "MIT", + "dependencies": { + "braces": "^3.0.3", + "picomatch": "^2.3.1" + }, + "engines": { + "node": ">=8.6" + } + }, "node_modules/mime-db": { "version": "1.53.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.53.0.tgz", @@ -1773,6 +4229,19 @@ "node": ">= 0.6" } }, + "node_modules/mimic-function": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/mimic-function/-/mimic-function-5.0.1.tgz", + "integrity": "sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/minimatch": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", @@ -1801,6 +4270,19 @@ "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", "license": "MIT" }, + "node_modules/nano-spawn": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/nano-spawn/-/nano-spawn-1.0.2.tgz", + "integrity": "sha512-21t+ozMQDAL/UGgQVBbZ/xXvNO10++ZPuTmKRO8k9V3AClVRht49ahtDjfY8l1q6nSHOrE5ASfthzH3ol6R/hg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=20.17" + }, + "funding": { + "url": "https://github.com/sindresorhus/nano-spawn?sponsor=1" + } + }, "node_modules/nanoid": { "version": "3.3.11", "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.11.tgz", @@ -1819,6 +4301,13 @@ "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" } }, + "node_modules/natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", + "dev": true, + "license": "MIT" + }, "node_modules/negotiator": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-1.0.0.tgz", @@ -1888,6 +4377,91 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.assign": { + "version": "4.1.7", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.7.tgz", + "integrity": "sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.3", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0", + "has-symbols": "^1.1.0", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object.entries": { + "version": "1.1.9", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.9.tgz", + "integrity": "sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.4", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.fromentries": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/object.fromentries/-/object.fromentries-2.0.8.tgz", + "integrity": "sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.2", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object.values": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.2.1.tgz", + "integrity": "sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.3", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/ollama-ai-provider": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/ollama-ai-provider/-/ollama-ai-provider-1.2.0.tgz", @@ -1941,6 +4515,22 @@ "wrappy": "1" } }, + "node_modules/onetime": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-7.0.0.tgz", + "integrity": "sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "mimic-function": "^5.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/openai": { "version": "4.92.0", "resolved": "https://registry.npmjs.org/openai/-/openai-4.92.0.tgz", @@ -1971,6 +4561,87 @@ } } }, + "node_modules/optionator": { + "version": "0.9.4", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.4.tgz", + "integrity": "sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==", + "dev": true, + "license": "MIT", + "dependencies": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.5" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/own-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/own-keys/-/own-keys-1.0.1.tgz", + "integrity": "sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==", + "dev": true, + "license": "MIT", + "dependencies": { + "get-intrinsic": "^1.2.6", + "object-keys": "^1.1.1", + "safe-push-apply": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/p-limit": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", + "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "yocto-queue": "^0.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-locate": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", + "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", + "dev": true, + "license": "MIT", + "dependencies": { + "p-limit": "^3.0.2" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "license": "MIT", + "dependencies": { + "callsites": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, "node_modules/parseurl": { "version": "1.3.3", "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", @@ -1987,6 +4658,16 @@ "license": "MIT", "optional": true }, + "node_modules/path-exists": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", + "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, "node_modules/path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", @@ -2022,6 +4703,32 @@ "node": ">=16" } }, + "node_modules/picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8.6" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/pidtree": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/pidtree/-/pidtree-0.6.0.tgz", + "integrity": "sha512-eG2dWTVw5bzqGRztnHExczNxt5VGsE6OwTeCG3fdUf9KBsZzO3R5OIIIzWR+iZA0NtZ+RDVdaoE2dK1cn6jH4g==", + "dev": true, + "license": "MIT", + "bin": { + "pidtree": "bin/pidtree.js" + }, + "engines": { + "node": ">=0.10" + } + }, "node_modules/pino": { "version": "9.6.0", "resolved": "https://registry.npmjs.org/pino/-/pino-9.6.0.tgz", @@ -2111,6 +4818,18 @@ } }, "node_modules/playwright-core": { + "version": "1.53.2", + "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.53.2.tgz", + "integrity": "sha512-ox/OytMy+2w1jcYEYlOo1Hhp8hZkLCximMTUTMBXjGUA1KoFfiSZ+DU+3a739jsPY0yoKH2TFy9S2fsJas8yAw==", + "license": "Apache-2.0", + "bin": { + "playwright-core": "cli.js" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/playwright/node_modules/playwright-core": { "version": "1.51.0", "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.51.0.tgz", "integrity": "sha512-x47yPE3Zwhlil7wlNU/iktF7t2r/URR3VLbH6EknJd/04Qc/PSJ0EY3CMXipmglLG+zyRxW6HNo2EGbKLHPWMg==", @@ -2122,6 +4841,42 @@ "node": ">=18" } }, + "node_modules/possible-typed-array-names": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.1.0.tgz", + "integrity": "sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/prettier": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.6.2.tgz", + "integrity": "sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ==", + "dev": true, + "license": "MIT", + "bin": { + "prettier": "bin/prettier.cjs" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/prettier/prettier?sponsor=1" + } + }, "node_modules/process-warning": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/process-warning/-/process-warning-4.0.1.tgz", @@ -2138,6 +4893,18 @@ ], "license": "MIT" }, + "node_modules/prop-types": { + "version": "15.8.1", + "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", + "integrity": "sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==", + "dev": true, + "license": "MIT", + "dependencies": { + "loose-envify": "^1.4.0", + "object-assign": "^4.1.1", + "react-is": "^16.13.1" + } + }, "node_modules/proxy-addr": { "version": "2.0.7", "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", @@ -2185,6 +4952,27 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, "node_modules/quick-format-unescaped": { "version": "4.0.4", "resolved": "https://registry.npmjs.org/quick-format-unescaped/-/quick-format-unescaped-4.0.4.tgz", @@ -2237,6 +5025,13 @@ "node": ">=0.10.0" } }, + "node_modules/react-is": { + "version": "16.13.1", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", + "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==", + "dev": true, + "license": "MIT" + }, "node_modules/real-require": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/real-require/-/real-require-0.2.0.tgz", @@ -2258,6 +5053,50 @@ "node": ">= 0.10" } }, + "node_modules/reflect.getprototypeof": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/reflect.getprototypeof/-/reflect.getprototypeof-1.0.10.tgz", + "integrity": "sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.9", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0", + "get-intrinsic": "^1.2.7", + "get-proto": "^1.0.1", + "which-builtin-type": "^1.2.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/regexp.prototype.flags": { + "version": "1.5.4", + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.4.tgz", + "integrity": "sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "define-properties": "^1.2.1", + "es-errors": "^1.3.0", + "get-proto": "^1.0.1", + "gopd": "^1.2.0", + "set-function-name": "^2.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/resolve": { "version": "1.22.10", "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.10.tgz", @@ -2273,12 +5112,57 @@ "resolve": "bin/resolve" }, "engines": { - "node": ">= 0.4" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=4" + } + }, + "node_modules/restore-cursor": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz", + "integrity": "sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==", + "dev": true, + "license": "MIT", + "dependencies": { + "onetime": "^7.0.0", + "signal-exit": "^4.1.0" + }, + "engines": { + "node": ">=18" }, "funding": { - "url": "https://github.com/sponsors/ljharb" + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/reusify": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.1.0.tgz", + "integrity": "sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==", + "dev": true, + "license": "MIT", + "engines": { + "iojs": ">=1.0.0", + "node": ">=0.10.0" } }, + "node_modules/rfdc": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.4.1.tgz", + "integrity": "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==", + "dev": true, + "license": "MIT" + }, "node_modules/router": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/router/-/router-2.1.0.tgz", @@ -2293,6 +5177,50 @@ "node": ">= 18" } }, + "node_modules/run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT", + "dependencies": { + "queue-microtask": "^1.2.2" + } + }, + "node_modules/safe-array-concat": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.1.3.tgz", + "integrity": "sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.2", + "get-intrinsic": "^1.2.6", + "has-symbols": "^1.1.0", + "isarray": "^2.0.5" + }, + "engines": { + "node": ">=0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/safe-buffer": { "version": "5.2.1", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", @@ -2313,6 +5241,41 @@ ], "license": "MIT" }, + "node_modules/safe-push-apply": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/safe-push-apply/-/safe-push-apply-1.0.0.tgz", + "integrity": "sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "isarray": "^2.0.5" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/safe-regex-test": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.1.0.tgz", + "integrity": "sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.2", + "es-errors": "^1.3.0", + "is-regex": "^1.2.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/safe-stable-stringify": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/safe-stable-stringify/-/safe-stable-stringify-2.5.0.tgz", @@ -2334,6 +5297,16 @@ "integrity": "sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==", "license": "BSD-3-Clause" }, + "node_modules/semver": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", + "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + } + }, "node_modules/send": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/send/-/send-1.1.0.tgz", @@ -2414,6 +5387,55 @@ "integrity": "sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==", "license": "MIT" }, + "node_modules/set-function-length": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", + "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-data-property": "^1.1.4", + "es-errors": "^1.3.0", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.4", + "gopd": "^1.0.1", + "has-property-descriptors": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/set-function-name": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/set-function-name/-/set-function-name-2.0.2.tgz", + "integrity": "sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "define-data-property": "^1.1.4", + "es-errors": "^1.3.0", + "functions-have-names": "^1.2.3", + "has-property-descriptors": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/set-proto": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/set-proto/-/set-proto-1.0.0.tgz", + "integrity": "sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==", + "dev": true, + "license": "MIT", + "dependencies": { + "dunder-proto": "^1.0.1", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, "node_modules/setprototypeof": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", @@ -2483,10 +5505,190 @@ "license": "MIT", "dependencies": { "es-errors": "^1.3.0", - "object-inspect": "^1.13.3", - "side-channel-list": "^1.0.0", - "side-channel-map": "^1.0.1", - "side-channel-weakmap": "^1.0.2" + "object-inspect": "^1.13.3", + "side-channel-list": "^1.0.0", + "side-channel-map": "^1.0.1", + "side-channel-weakmap": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/side-channel-list": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.0.tgz", + "integrity": "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==", + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "object-inspect": "^1.13.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/side-channel-map": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/side-channel-map/-/side-channel-map-1.0.1.tgz", + "integrity": "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==", + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.2", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.5", + "object-inspect": "^1.13.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/side-channel-weakmap": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz", + "integrity": "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==", + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.2", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.5", + "object-inspect": "^1.13.3", + "side-channel-map": "^1.0.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/signal-exit": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", + "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", + "dev": true, + "license": "ISC", + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/slice-ansi": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-5.0.0.tgz", + "integrity": "sha512-FC+lgizVPfie0kkhqUScwRu1O/lF6NOgJmlCgK+/LYxDCTk8sGelYaHDhFcDN+Sn3Cv+3VSa4Byeo+IMCzpMgQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-styles": "^6.0.0", + "is-fullwidth-code-point": "^4.0.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/slice-ansi?sponsor=1" + } + }, + "node_modules/sonic-boom": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/sonic-boom/-/sonic-boom-4.2.0.tgz", + "integrity": "sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==", + "license": "MIT", + "dependencies": { + "atomic-sleep": "^1.0.0" + } + }, + "node_modules/split2": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", + "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", + "license": "ISC", + "engines": { + "node": ">= 10.x" + } + }, + "node_modules/statuses": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", + "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/stop-iteration-iterator": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/stop-iteration-iterator/-/stop-iteration-iterator-1.1.0.tgz", + "integrity": "sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "internal-slot": "^1.1.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/string-argv": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz", + "integrity": "sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.6.19" + } + }, + "node_modules/string-width": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-7.2.0.tgz", + "integrity": "sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "emoji-regex": "^10.3.0", + "get-east-asian-width": "^1.0.0", + "strip-ansi": "^7.1.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/string.prototype.matchall": { + "version": "4.0.12", + "resolved": "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.12.tgz", + "integrity": "sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.3", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.6", + "es-errors": "^1.3.0", + "es-object-atoms": "^1.0.0", + "get-intrinsic": "^1.2.6", + "gopd": "^1.2.0", + "has-symbols": "^1.1.0", + "internal-slot": "^1.1.0", + "regexp.prototype.flags": "^1.5.3", + "set-function-name": "^2.0.2", + "side-channel": "^1.1.0" }, "engines": { "node": ">= 0.4" @@ -2495,14 +5697,31 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/side-channel-list": { + "node_modules/string.prototype.repeat": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.0.tgz", - "integrity": "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==", + "resolved": "https://registry.npmjs.org/string.prototype.repeat/-/string.prototype.repeat-1.0.0.tgz", + "integrity": "sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==", + "dev": true, "license": "MIT", "dependencies": { - "es-errors": "^1.3.0", - "object-inspect": "^1.13.3" + "define-properties": "^1.1.3", + "es-abstract": "^1.17.5" + } + }, + "node_modules/string.prototype.trim": { + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.10.tgz", + "integrity": "sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "call-bound": "^1.0.2", + "define-data-property": "^1.1.4", + "define-properties": "^1.2.1", + "es-abstract": "^1.23.5", + "es-object-atoms": "^1.0.0", + "has-property-descriptors": "^1.0.2" }, "engines": { "node": ">= 0.4" @@ -2511,16 +5730,17 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/side-channel-map": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/side-channel-map/-/side-channel-map-1.0.1.tgz", - "integrity": "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==", + "node_modules/string.prototype.trimend": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.9.tgz", + "integrity": "sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==", + "dev": true, "license": "MIT", "dependencies": { + "call-bind": "^1.0.8", "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.5", - "object-inspect": "^1.13.3" + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" }, "engines": { "node": ">= 0.4" @@ -2529,17 +5749,16 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/side-channel-weakmap": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz", - "integrity": "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==", + "node_modules/string.prototype.trimstart": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.8.tgz", + "integrity": "sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==", + "dev": true, "license": "MIT", "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.5", - "object-inspect": "^1.13.3", - "side-channel-map": "^1.0.1" + "call-bind": "^1.0.7", + "define-properties": "^1.2.1", + "es-object-atoms": "^1.0.0" }, "engines": { "node": ">= 0.4" @@ -2548,31 +5767,20 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/sonic-boom": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/sonic-boom/-/sonic-boom-4.2.0.tgz", - "integrity": "sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==", + "node_modules/strip-ansi": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", + "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", + "dev": true, "license": "MIT", "dependencies": { - "atomic-sleep": "^1.0.0" - } - }, - "node_modules/split2": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", - "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", - "license": "ISC", - "engines": { - "node": ">= 10.x" - } - }, - "node_modules/statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "license": "MIT", + "ansi-regex": "^6.0.1" + }, "engines": { - "node": ">= 0.8" + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/strip-ansi?sponsor=1" } }, "node_modules/strip-json-comments": { @@ -2587,6 +5795,19 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "license": "MIT", + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", @@ -2652,6 +5873,19 @@ "integrity": "sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==", "license": "MIT" }, + "node_modules/to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-number": "^7.0.0" + }, + "engines": { + "node": ">=8.0" + } + }, "node_modules/toidentifier": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", @@ -2679,6 +5913,32 @@ "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", "license": "MIT" }, + "node_modules/ts-api-utils": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-2.1.0.tgz", + "integrity": "sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.12" + }, + "peerDependencies": { + "typescript": ">=4.8.4" + } + }, + "node_modules/type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "license": "MIT", + "dependencies": { + "prelude-ls": "^1.2.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, "node_modules/type-is": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/type-is/-/type-is-2.0.0.tgz", @@ -2693,6 +5953,84 @@ "node": ">= 0.6" } }, + "node_modules/typed-array-buffer": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.3.tgz", + "integrity": "sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "es-errors": "^1.3.0", + "is-typed-array": "^1.1.14" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/typed-array-byte-length": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.3.tgz", + "integrity": "sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.8", + "for-each": "^0.3.3", + "gopd": "^1.2.0", + "has-proto": "^1.2.0", + "is-typed-array": "^1.1.14" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typed-array-byte-offset": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.4.tgz", + "integrity": "sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "available-typed-arrays": "^1.0.7", + "call-bind": "^1.0.8", + "for-each": "^0.3.3", + "gopd": "^1.2.0", + "has-proto": "^1.2.0", + "is-typed-array": "^1.1.15", + "reflect.getprototypeof": "^1.0.9" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typed-array-length": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.7.tgz", + "integrity": "sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bind": "^1.0.7", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "is-typed-array": "^1.1.13", + "possible-typed-array-names": "^1.0.0", + "reflect.getprototypeof": "^1.0.6" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/typescript": { "version": "5.8.2", "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.8.2.tgz", @@ -2707,6 +6045,48 @@ "node": ">=14.17" } }, + "node_modules/typescript-eslint": { + "version": "8.35.1", + "resolved": "https://registry.npmjs.org/typescript-eslint/-/typescript-eslint-8.35.1.tgz", + "integrity": "sha512-xslJjFzhOmHYQzSB/QTeASAHbjmxOGEP6Coh93TXmUBFQoJ1VU35UHIDmG06Jd6taf3wqqC1ntBnCMeymy5Ovw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@typescript-eslint/eslint-plugin": "8.35.1", + "@typescript-eslint/parser": "8.35.1", + "@typescript-eslint/utils": "8.35.1" + }, + "engines": { + "node": "^18.18.0 || ^20.9.0 || >=21.1.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^8.57.0 || ^9.0.0", + "typescript": ">=4.8.4 <5.9.0" + } + }, + "node_modules/unbox-primitive": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.1.0.tgz", + "integrity": "sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.3", + "has-bigints": "^1.0.2", + "has-symbols": "^1.1.0", + "which-boxed-primitive": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/undici-types": { "version": "5.26.5", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", @@ -2811,6 +6191,123 @@ "node": ">= 8" } }, + "node_modules/which-boxed-primitive": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.1.1.tgz", + "integrity": "sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-bigint": "^1.1.0", + "is-boolean-object": "^1.2.1", + "is-number-object": "^1.1.1", + "is-string": "^1.1.1", + "is-symbol": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-builtin-type": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/which-builtin-type/-/which-builtin-type-1.2.1.tgz", + "integrity": "sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "call-bound": "^1.0.2", + "function.prototype.name": "^1.1.6", + "has-tostringtag": "^1.0.2", + "is-async-function": "^2.0.0", + "is-date-object": "^1.1.0", + "is-finalizationregistry": "^1.1.0", + "is-generator-function": "^1.0.10", + "is-regex": "^1.2.1", + "is-weakref": "^1.0.2", + "isarray": "^2.0.5", + "which-boxed-primitive": "^1.1.0", + "which-collection": "^1.0.2", + "which-typed-array": "^1.1.16" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-collection": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.2.tgz", + "integrity": "sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-map": "^2.0.3", + "is-set": "^2.0.3", + "is-weakmap": "^2.0.2", + "is-weakset": "^2.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-typed-array": { + "version": "1.1.19", + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.19.tgz", + "integrity": "sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==", + "dev": true, + "license": "MIT", + "dependencies": { + "available-typed-arrays": "^1.0.7", + "call-bind": "^1.0.8", + "call-bound": "^1.0.4", + "for-each": "^0.3.5", + "get-proto": "^1.0.1", + "gopd": "^1.2.0", + "has-tostringtag": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/word-wrap": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.5.tgz", + "integrity": "sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/wrap-ansi": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-9.0.0.tgz", + "integrity": "sha512-G8ura3S+3Z2G+mkgNRq8dqaFZAuxfsxpBB8OCTGRTCtp+l/v9nbFNmCUP1BZMts3G1142MsZfn6eeUKrr4PD1Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-styles": "^6.2.1", + "string-width": "^7.0.0", + "strip-ansi": "^7.1.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/chalk/wrap-ansi?sponsor=1" + } + }, "node_modules/wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", @@ -2838,10 +6335,36 @@ } } }, + "node_modules/yaml": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.8.0.tgz", + "integrity": "sha512-4lLa/EcQCB0cJkyts+FpIRx5G/llPxfP6VQU5KByHEhLxY3IJCH0f0Hy1MHI8sClTvsIb8qwRJ6R/ZdlDJ/leQ==", + "dev": true, + "license": "ISC", + "bin": { + "yaml": "bin.mjs" + }, + "engines": { + "node": ">= 14.6" + } + }, + "node_modules/yocto-queue": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", + "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/zod": { - "version": "3.24.2", - "resolved": "https://registry.npmjs.org/zod/-/zod-3.24.2.tgz", - "integrity": "sha512-lY7CDW43ECgW9u1TcT3IoXHflywfVqDYze4waEz812jR/bZ8FHDsl7pFQoSZTz5N+2NqRXs8GBwnAwo3ZNxqhQ==", + "version": "3.25.67", + "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.67.tgz", + "integrity": "sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/colinhacks" diff --git a/package.json b/package.json index 99d2014..722d272 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "@browserbasehq/mcp", "version": "2.0.0", - "description": "MCP server for AI web browser automation using Stagehand", + "description": "MCP server for AI web browser automation using Browserbase and Stagehand", "license": "Apache-2.0", "author": "Browserbase, Inc. (https://www.browserbase.com/)", "homepage": "https://www.browserbase.com", @@ -9,7 +9,7 @@ "type": "module", "main": "./cli.js", "bin": { - "mcp-server-stagehand": "cli.js" + "mcp-server-browserbase": "cli.js" }, "files": [ "dist", @@ -24,7 +24,9 @@ "watch": "tsc --watch", "lint": "eslint . --ext .ts", "prettier:check": "prettier --check .", - "prettier:fix": "prettier --write ." + "prettier:fix": "prettier --write .", + "clean": "rm -rf dist", + "npm-publish": "pnpm clean && pnpm build && npm publish" }, "lint-staged": { "*.{js,jsx,ts,tsx,json,css,scss,md}": [ @@ -37,7 +39,7 @@ "@modelcontextprotocol/sdk": "^1.13.1", "@playwright/test": "^1.49.0", "commander": "^14.0.0", - "dotenv": "^17.0.0", + "dotenv": "^16.4.6", "playwright-core": "^1.53.2", "zod": "^3.25.67" }, diff --git a/src/tools/navigate.ts b/src/tools/navigate.ts index acac0b2..b69f1af 100644 --- a/src/tools/navigate.ts +++ b/src/tools/navigate.ts @@ -22,7 +22,9 @@ async function handleNavigate( ): Promise { const action = async (): Promise => { try { + const stagehand = await context.getStagehand(); const page = await context.getActivePage(); + if (!page) { throw new Error("No active page available"); } @@ -36,7 +38,7 @@ async function handleNavigate( }, { type: "text", - text: `View the live session here: https://browserbase.com/sessions/${context.currentSessionId}`, + text: `View the live session here: https://www.browserbase.com/sessions/${stagehand.browserbaseSessionID}`, }, ], }; diff --git a/src/tools/session.ts b/src/tools/session.ts index 838bf6c..30c403f 100644 --- a/src/tools/session.ts +++ b/src/tools/session.ts @@ -76,7 +76,7 @@ async function handleCreateSession( ); process.stderr.write( - `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.sessionId}`, + `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.stagehand.browserbaseSessionID}`, ); return { From a4d74f6fe3cff7460152dfa2df811302b92acbae Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Mon, 30 Jun 2025 16:50:53 -0700 Subject: [PATCH 17/32] rename session list to multi session, added better prompting --- README.md | 4 ++-- src/mcp/prompts.ts | 4 ++-- src/tools/multiSession.ts | 6 +++--- 3 files changed, 7 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index ea97d0d..aa89ab9 100644 --- a/README.md +++ b/README.md @@ -349,7 +349,7 @@ The server supports managing multiple independent browser sessions in parallel, - Output: - Session ID and Browserbase session ID with live debugger URL -- **browserbase_stagehand_session_list** +- **multi_browserbase_stagehand_session_list** - List all currently active Stagehand browser sessions with detailed metadata - Shows session IDs, names, Browserbase session IDs, creation time, and age - No inputs required @@ -519,7 +519,7 @@ The server supports two session management approaches: - Automatically manages the active session 2. **Multi-Session Mode**: Advanced approach with multiple parallel browser sessions - - Tools: `multi_browserbase_stagehand_session_create`, `multi_browserbase_stagehand_session_close`, `browserbase_stagehand_session_list` + - Tools: `multi_browserbase_stagehand_session_create`, `multi_browserbase_stagehand_session_close`, `multi_browserbase_stagehand_session_list` - Session-specific variants of all core tools (with `_session` suffix) - Ideal for complex workflows requiring parallel browser instances - Each session maintains independent state, cookies, and browser context diff --git a/src/mcp/prompts.ts b/src/mcp/prompts.ts index 98e7171..f636c72 100644 --- a/src/mcp/prompts.ts +++ b/src/mcp/prompts.ts @@ -63,7 +63,7 @@ MULTI-SESSION INDICATORS - Use multi-session tools when you see: MULTI-SESSION WORKFLOW: 1. Create sessions: "multi_browserbase_stagehand_session_create" (give descriptive names) -2. Track sessions: "browserbase_stagehand_session_list" +2. Track sessions: "multi_browserbase_stagehand_session_list" 3. Use session tools: "multi_browserbase_stagehand_navigate_session", etc. 4. Cleanup: "multi_browserbase_stagehand_session_close" @@ -105,7 +105,7 @@ TOOL NAMING PATTERNS: RECOMMENDED WORKFLOW: 1. Create sessions: "multi_browserbase_stagehand_session_create" (give each a descriptive name) -2. List sessions: "browserbase_stagehand_session_list" (to track active sessions) +2. List sessions: "multi_browserbase_stagehand_session_list" (to track active sessions) 3. Use session-specific tools: "multi_browserbase_stagehand_navigate_session", "multi_browserbase_stagehand_act_session", etc. 4. Clean up: "multi_browserbase_stagehand_session_close" when done diff --git a/src/tools/multiSession.ts b/src/tools/multiSession.ts index bfcf464..264df81 100644 --- a/src/tools/multiSession.ts +++ b/src/tools/multiSession.ts @@ -140,9 +140,9 @@ export const createSessionTool = defineTool({ export const listSessionsTool = defineTool({ capability: "list_sessions", schema: { - name: "browserbase_stagehand_session_list", + name: "multi_browserbase_stagehand_session_list", description: - "Track all parallel sessions: Critical tool for multi-session management! Shows all active browser sessions with their IDs, names, ages, and Browserbase session IDs. Use this frequently to monitor your parallel automation workflows, verify sessions are running, and get session IDs for session-specific tools. Essential for debugging and resource management in complex multi-browser scenarios.", + "ONLY WORKS WITH MULTI-SESSION TOOLS! Track all parallel sessions: Critical tool for multi-session management! Shows all active browser sessions with their IDs, names, ages, and Browserbase session IDs. Use this frequently to monitor your parallel automation workflows, verify sessions are running, and get session IDs for session-specific tools. Essential for debugging and resource management in complex multi-browser scenarios.", inputSchema: z.object({}), }, handle: async (): Promise => { @@ -200,7 +200,7 @@ export const closeSessionTool = defineTool({ sessionId: z .string() .describe( - "Exact session ID to close (get from 'browserbase_stagehand_session_list'). Double-check this ID - once closed, the session cannot be recovered!", + "Exact session ID to close (get from 'multi_browserbase_stagehand_session_list'). Double-check this ID - once closed, the session cannot be recovered!", ), }), }, From d6fb91d2a7634e3339d4486679df06349045aa3f Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Tue, 1 Jul 2025 16:41:58 -0700 Subject: [PATCH 18/32] add modelapikey to config --- README.md | 36 ++++++++++++- config.d.ts | 5 ++ src/config.ts | 2 + src/index.ts | 136 +++++++++++++++++++++++++++++-------------------- src/program.ts | 4 ++ 5 files changed, 126 insertions(+), 57 deletions(-) diff --git a/README.md b/README.md index aa89ab9..a4cfdb9 100644 --- a/README.md +++ b/README.md @@ -130,6 +130,7 @@ The Browserbase MCP server accepts the following command-line flags: | `--browserWidth ` | Browser viewport width (default: 1024) | | `--browserHeight ` | Browser viewport height (default: 768) | | `--modelName ` | The model to use for Stagehand (default: google/gemini-2.0-flash) | +| `--modelApiKey ` | API key for the custom model provider (required when using custom models) | These flags can be passed directly to the CLI or configured in your MCP configuration file. @@ -256,6 +257,8 @@ Here's how to use it for custom browser sizing. We recommend to stick with 16:9 Stagehand defaults to using Google's Gemini 2.0 Flash model, but you can configure it to use other models like GPT-4o, Claude, or other providers. +**Important**: When using any custom model (non-default), you must provide your own API key for that model provider using the `--modelApiKey` flag. + Here's how to configure different models: ```json @@ -263,7 +266,36 @@ Here's how to configure different models: "mcpServers": { "browserbase": { "command": "npx", - "args": ["@browserbasehq/mcp", "--modelName", "gpt-4o"], + "args": [ + "@browserbasehq/mcp", + "--modelName", + "gpt-4o", + "--modelApiKey", + "your-openai-api-key" + ], + "env": { + "BROWSERBASE_API_KEY": "", + "BROWSERBASE_PROJECT_ID": "" + } + } + } +} +``` + +For Claude models: + +```json +{ + "mcpServers": { + "browserbase": { + "command": "npx", + "args": [ + "@browserbasehq/mcp", + "--modelName", + "claude-3-5-sonnet-latest", + "--modelApiKey", + "your-anthropic-api-key" + ], "env": { "BROWSERBASE_API_KEY": "", "BROWSERBASE_PROJECT_ID": "" @@ -280,7 +312,7 @@ Available models include: - **Claude**: `claude-3-5-sonnet-latest`, `claude-3-7-sonnet-latest` - **Other providers**: Cerebras, Groq, and more -_Note: The model must be supported in Stagehand. Check out the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms)._ +_Note: The model must be supported in Stagehand. Check out the docs [here](https://docs.stagehand.dev/examples/custom_llms#supported-llms). When using any custom model, you must provide your own API key for that provider._ ## Tools diff --git a/config.d.ts b/config.d.ts index d77566b..365b42e 100644 --- a/config.d.ts +++ b/config.d.ts @@ -78,4 +78,9 @@ export type Config = { * @default "google/gemini-2.0-flash" */ modelName?: AvailableModelSchema; + /** + * API key for the custom model provider + * Required when using a model other than the default google/gemini-2.0-flash + */ + modelApiKey?: string; }; diff --git a/src/config.ts b/src/config.ts index ce2151b..65b0baa 100644 --- a/src/config.ts +++ b/src/config.ts @@ -22,6 +22,7 @@ export type CLIOptions = { browserWidth?: number; browserHeight?: number; modelName?: typeof AvailableModelSchema; + modelApiKey?: string; }; // Default Configuration Values @@ -92,6 +93,7 @@ export async function configFromCLIOptions( advancedStealth: cliOptions.advancedStealth, cookies: cliOptions.cookies, modelName: cliOptions.modelName, + modelApiKey: cliOptions.modelApiKey, }; } diff --git a/src/index.ts b/src/index.ts index fbeacb7..e54f2d3 100644 --- a/src/index.ts +++ b/src/index.ts @@ -32,61 +32,87 @@ const cookieSchema = z.object({ }); // Configuration schema for Smithery - matches existing Config interface -export const configSchema = z.object({ - browserbaseApiKey: z.string().describe("The Browserbase API Key to use"), - browserbaseProjectId: z - .string() - .describe("The Browserbase Project ID to use"), - proxies: z - .boolean() - .optional() - .describe("Whether or not to use Browserbase proxies"), - advancedStealth: z - .boolean() - .optional() - .describe( - "Use advanced stealth mode. Only available to Browserbase Scale Plan users", - ), - context: z - .object({ - contextId: z.string().optional().describe("The ID of the context to use"), - persist: z - .boolean() - .optional() - .describe("Whether or not to persist the context"), - }) - .optional(), - viewPort: z - .object({ - browserWidth: z.number().optional().describe("The width of the browser"), - browserHeight: z - .number() - .optional() - .describe("The height of the browser"), - }) - .optional(), - cookies: z - .array(cookieSchema) - .optional() - .describe("Cookies to inject into the Browserbase context"), - server: z - .object({ - port: z - .number() - .optional() - .describe("The port to listen on for SSE or MCP transport"), - host: z - .string() - .optional() - .describe( - "The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces", - ), - }) - .optional(), - modelName: AvailableModelSchema.optional().describe( - "The model to use for Stagehand (default: google/gemini-2.0-flash)", - ), // Already an existing Zod Enum -}); +export const configSchema = z + .object({ + browserbaseApiKey: z.string().describe("The Browserbase API Key to use"), + browserbaseProjectId: z + .string() + .describe("The Browserbase Project ID to use"), + proxies: z + .boolean() + .optional() + .describe("Whether or not to use Browserbase proxies"), + advancedStealth: z + .boolean() + .optional() + .describe( + "Use advanced stealth mode. Only available to Browserbase Scale Plan users", + ), + context: z + .object({ + contextId: z + .string() + .optional() + .describe("The ID of the context to use"), + persist: z + .boolean() + .optional() + .describe("Whether or not to persist the context"), + }) + .optional(), + viewPort: z + .object({ + browserWidth: z + .number() + .optional() + .describe("The width of the browser"), + browserHeight: z + .number() + .optional() + .describe("The height of the browser"), + }) + .optional(), + cookies: z + .array(cookieSchema) + .optional() + .describe("Cookies to inject into the Browserbase context"), + server: z + .object({ + port: z + .number() + .optional() + .describe("The port to listen on for SSE or MCP transport"), + host: z + .string() + .optional() + .describe( + "The host to bind the server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces", + ), + }) + .optional(), + modelName: AvailableModelSchema.optional().describe( + "The model to use for Stagehand (default: google/gemini-2.0-flash)", + ), // Already an existing Zod Enum + modelApiKey: z + .string() + .optional() + .describe( + "API key for the custom model provider. Required when using a model other than the default google/gemini-2.0-flash", + ), + }) + .refine( + (data) => { + // If any model is explicitly specified, API key is required + if (data.modelName) { + return data.modelApiKey !== undefined && data.modelApiKey.length > 0; + } + return true; + }, + { + message: "modelApiKey is required when specifying a custom model", + path: ["modelApiKey"], + }, + ); // Default function for Smithery export default function ({ config }: { config: z.infer }) { diff --git a/src/program.ts b/src/program.ts index d3c7681..6c0fad9 100644 --- a/src/program.ts +++ b/src/program.ts @@ -60,6 +60,10 @@ program "--modelName ", "The model to use for Stagehand (default: google/gemini-2.0-flash)", ) + .option( + "--modelApiKey ", + "API key for the custom model provider (required when using custom models)", + ) .action(async (options) => { const config = await resolveConfig(options); const serverList = new ServerList(async () => From d81dcc810c9f4398dcb9fca10dc4ffd9145f1fda Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 2 Jul 2025 17:25:54 -0700 Subject: [PATCH 19/32] moving types around, removing unnecessary code, reworking stagehand session create --- LICENSE | 2 +- eslint.config.js | 5 ++- src/context.ts | 22 +++----------- src/index.ts | 4 +-- src/program.ts | 3 +- src/sessionManager.ts | 64 +++++++++++---------------------------- src/stagehandStore.ts | 34 ++++++++++++++------- src/tools/act.ts | 2 +- src/tools/extract.ts | 2 +- src/tools/multiSession.ts | 14 +++------ src/tools/navigate.ts | 2 +- src/tools/observe.ts | 2 +- src/tools/screenshot.ts | 2 +- src/tools/session.ts | 17 +++-------- src/types/types.ts | 24 +++++++++++++-- 15 files changed, 89 insertions(+), 110 deletions(-) diff --git a/LICENSE b/LICENSE index 1c012e4..624e143 100644 --- a/LICENSE +++ b/LICENSE @@ -1,5 +1,5 @@ Apache License - Version 2.0, June 2025 + Version 2.0, January 2004 http://www.apache.org/licenses/ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION diff --git a/eslint.config.js b/eslint.config.js index 786dae4..b4c556f 100644 --- a/eslint.config.js +++ b/eslint.config.js @@ -15,15 +15,14 @@ export default defineConfig([ languageOptions: { globals: { ...globals.browser, ...globals.node } }, ignores: ["dist/**/*"], }, - tseslint.configs.recommended, + ...tseslint.configs.recommended, { - files: ["**/*.{ts,mts,cts}"], + files: ["src/types/**/*.ts", "src/mcp/**/*.ts"], rules: { "@typescript-eslint/no-explicit-any": "off", "@typescript-eslint/no-unused-vars": "off", "@typescript-eslint/ban-ts-comment": "off", }, - ignores: ["dist/**/*"], }, { ignores: ["dist/**/*", "node_modules/**/*"], diff --git a/src/context.ts b/src/context.ts index c72460e..ae18ad9 100644 --- a/src/context.ts +++ b/src/context.ts @@ -1,22 +1,10 @@ import type { Stagehand } from "@browserbasehq/stagehand"; import { Server } from "@modelcontextprotocol/sdk/server/index.js"; import type { Config } from "../config.js"; -import { - CallToolResult, - TextContent, - ImageContent, -} from "@modelcontextprotocol/sdk/types.js"; +import { CallToolResult } from "@modelcontextprotocol/sdk/types.js"; import { listResources, readResource } from "./mcp/resources.js"; -import { - getSession, - defaultSessionId, - type BrowserSession, -} from "./sessionManager.js"; - -export type ToolActionResult = - | { content?: (ImageContent | TextContent)[] } - | undefined - | void; +import { getSession, defaultSessionId } from "./sessionManager.js"; +import type { MCPTool, BrowserSession } from "./types/types.js"; export class Context { public readonly config: Config; @@ -69,7 +57,7 @@ export class Context { return session.browser; } - async run(tool: any, args: any): Promise { + async run(tool: MCPTool, args: unknown): Promise { try { console.error( `Executing tool: ${tool.schema.name} with args: ${JSON.stringify(args)}`, @@ -77,7 +65,7 @@ export class Context { // Check if this tool has a handle method (new tool system) if ("handle" in tool && typeof tool.handle === "function") { - const toolResult = await tool.handle(this as any, args); + const toolResult = await tool.handle(this, args); if (toolResult?.action) { const actionResult = await toolResult.action(); diff --git a/src/index.ts b/src/index.ts index e54f2d3..900caa8 100644 --- a/src/index.ts +++ b/src/index.ts @@ -3,7 +3,7 @@ dotenv.config(); import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js"; import { z } from "zod"; -import type { Tool } from "./tools/tool.js"; +import type { MCPToolsArray } from "./types/types.js"; import { Context } from "./context.js"; import type { Config } from "../config.js"; @@ -185,7 +185,7 @@ export default function ({ config }: { config: z.infer }) { return prompt; }); - const tools: Tool[] = [...TOOLS]; + const tools: MCPToolsArray = [...TOOLS]; // Register each tool with the Smithery server tools.forEach((tool) => { diff --git a/src/program.ts b/src/program.ts index 6c0fad9..5a0ff80 100644 --- a/src/program.ts +++ b/src/program.ts @@ -20,7 +20,8 @@ try { } catch { // Fallback for CommonJS or when import.meta is not available __filename = - (globalThis as any).__filename || process.cwd() + "/dist/program.js"; + (globalThis as { __filename: string }).__filename || + process.cwd() + "/dist/program.js"; __dirname = path.dirname(__filename); } diff --git a/src/sessionManager.ts b/src/sessionManager.ts index 4b6ff15..7150353 100644 --- a/src/sessionManager.ts +++ b/src/sessionManager.ts @@ -1,14 +1,9 @@ -import { Browser, Page } from "playwright-core"; -import { AvailableModel, Stagehand } from "@browserbasehq/stagehand"; +import { Page } from "playwright-core"; +import { BrowserContext } from "@browserbasehq/stagehand"; import type { Config } from "../config.js"; import type { Cookie } from "playwright-core"; - -export type BrowserSession = { - browser: Browser; - page: Page; - sessionId: string; - stagehand: Stagehand; -}; +import { createStagehandInstance } from "./stagehandStore.js"; +import type { BrowserSession } from "./types/types.js"; // Global state for managing browser sessions const browsers = new Map(); @@ -50,7 +45,7 @@ export function getActiveSessionId(): string { * @param cookies Array of cookies to add */ export async function addCookiesToContext( - context: any, + context: BrowserContext, cookies: Cookie[], ): Promise { if (!cookies || cookies.length === 0) { @@ -92,40 +87,14 @@ export async function createNewBrowserSession( `[SessionManager] ${resumeSessionId ? "Resuming" : "Creating"} Stagehand session ${newSessionId}...\n`, ); - // Create and initialize Stagehand instance - const stagehand = new Stagehand({ - env: "BROWSERBASE", - apiKey: config.browserbaseApiKey, - projectId: config.browserbaseProjectId, - modelName: (config.modelName || - "google/gemini-2.0-flash") as AvailableModel, - modelClientOptions: { - apiKey: process.env.GEMINI_API_KEY, // TODO: change this in prod to just use our key - }, - ...(resumeSessionId && { browserbaseSessionID: resumeSessionId }), - browserbaseSessionCreateParams: { - projectId: config.browserbaseProjectId!, - proxies: config.proxies, - browserSettings: { - viewport: { - width: config.viewPort?.browserWidth ?? 1024, - height: config.viewPort?.browserHeight ?? 768, - }, - context: config.context?.contextId - ? { - id: config.context?.contextId, - persist: config.context?.persist ?? true, - } - : undefined, - advancedStealth: config.advancedStealth ?? undefined, - }, + // Create and initialize Stagehand instance using shared function + const stagehand = await createStagehandInstance( + config, + { + ...(resumeSessionId && { browserbaseSessionID: resumeSessionId }), }, - logger: (logLine) => { - console.error(`Stagehand[${newSessionId}]: ${logLine.message}`); - }, - }); - - await stagehand.init(); + newSessionId, + ); // Get the page and browser from Stagehand const page = stagehand.page as unknown as Page; @@ -171,7 +140,10 @@ export async function createNewBrowserSession( Array.isArray(config.cookies) && config.cookies.length > 0 ) { - await addCookiesToContext(page.context(), config.cookies); + await addCookiesToContext( + page.context() as BrowserContext, + config.cookies, + ); } const sessionObj: BrowserSession = { @@ -306,7 +278,7 @@ export async function getSession( if (sessionId === defaultSessionId && createIfMissing) { try { return await ensureDefaultSessionInternal(config); - } catch (error) { + } catch { process.stderr.write( `[SessionManager] Failed to get default session due to error in ensureDefaultSessionInternal for ${sessionId}. See previous messages for details.\n`, ); @@ -385,7 +357,7 @@ export async function closeAllSessions(): Promise { } try { await Promise.all(closePromises); - } catch (_e) { + } catch { // Individual errors are caught and logged by closeBrowserGracefully process.stderr.write( `[SessionManager] WARN - Some errors occurred during batch session closing. See individual messages.\n`, diff --git a/src/stagehandStore.ts b/src/stagehandStore.ts index 4bef116..40645a2 100644 --- a/src/stagehandStore.ts +++ b/src/stagehandStore.ts @@ -8,15 +8,13 @@ import type { Config } from "../config.js"; const store = new Map(); /** - * Create a new Stagehand session + * Create a configured Stagehand instance */ -export const create = async ( +export const createStagehandInstance = async ( config: Config, params: CreateSessionParams = {}, -): Promise => { - const id = randomUUID() + "_" + Date.now(); - - // Merge config with params + sessionId: string, +): Promise => { const apiKey = params.apiKey || config.browserbaseApiKey; const projectId = params.projectId || config.browserbaseProjectId; @@ -24,8 +22,6 @@ export const create = async ( throw new Error("Browserbase API Key and Project ID are required"); } - process.stderr.write(`[StagehandStore] Creating new session ${id}...\n`); - const stagehand = new Stagehand({ env: "BROWSERBASE", apiKey, @@ -34,12 +30,12 @@ export const create = async ( config.modelName || "google/gemini-2.0-flash") as AvailableModel, modelClientOptions: { - apiKey: process.env.GEMINI_API_KEY, //TODO: + apiKey: config.modelApiKey || process.env.GEMINI_API_KEY, }, ...(params.browserbaseSessionID && { browserbaseSessionID: params.browserbaseSessionID, }), - browserbaseSessionCreateParams: params.browserbaseSessionCreateParams || { + browserbaseSessionCreateParams: { projectId, proxies: config.proxies, browserSettings: { @@ -57,11 +53,27 @@ export const create = async ( }, }, logger: (logLine) => { - console.error(`Stagehand[${id}]: ${logLine.message}`); + console.error(`Stagehand[${sessionId}]: ${logLine.message}`); }, }); await stagehand.init(); + return stagehand; +}; + +/** + * Create a new Stagehand session + */ +export const create = async ( + config: Config, + params: CreateSessionParams = {}, +): Promise => { + // Global ID, must be 100% Unique + const id = randomUUID() + "_" + config.browserbaseProjectId; + + process.stderr.write(`[StagehandStore] Creating new session ${id}...\n`); + + const stagehand = await createStagehandInstance(config, params, id); const page = stagehand.page as unknown as Page; const browser = page.context().browser(); diff --git a/src/tools/act.ts b/src/tools/act.ts index ead9868..09d5aab 100644 --- a/src/tools/act.ts +++ b/src/tools/act.ts @@ -1,7 +1,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { ToolActionResult } from "../types/types.js"; const ActInputSchema = z.object({ action: z diff --git a/src/tools/extract.ts b/src/tools/extract.ts index eec032e..b371cd3 100644 --- a/src/tools/extract.ts +++ b/src/tools/extract.ts @@ -1,7 +1,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { ToolActionResult } from "../types/types.js"; const ExtractInputSchema = z.object({ instruction: z diff --git a/src/tools/multiSession.ts b/src/tools/multiSession.ts index 264df81..4428dc6 100644 --- a/src/tools/multiSession.ts +++ b/src/tools/multiSession.ts @@ -51,7 +51,10 @@ function createMultiSessionAwareTool( description: `${originalTool.schema.description} (for a specific session)`, inputSchema: newInputSchema, }, - handle: async (context: Context, params: any): Promise => { + handle: async ( + context: Context, + params: z.infer, + ): Promise => { const { sessionId, ...originalParams } = params; // Get the session @@ -94,22 +97,15 @@ export const createSessionTool = defineTool({ .describe( "Resume an existing Browserbase session by providing its session ID. Use this to continue work in a previously created browser session that may have been paused or disconnected.", ), - browserbaseSessionCreateParams: z - .any() - .optional() - .describe( - "Advanced Browserbase session configuration parameters for customizing browser settings, viewport, user agent, etc. Leave empty for default settings.", - ), }), }, handle: async ( context: Context, - { name, browserbaseSessionID, browserbaseSessionCreateParams }, + { name, browserbaseSessionID }, ): Promise => { try { const params: CreateSessionParams = { browserbaseSessionID, - browserbaseSessionCreateParams, meta: name ? { name } : undefined, }; diff --git a/src/tools/navigate.ts b/src/tools/navigate.ts index b69f1af..1f77ae9 100644 --- a/src/tools/navigate.ts +++ b/src/tools/navigate.ts @@ -1,7 +1,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { ToolActionResult } from "../types/types.js"; const NavigateInputSchema = z.object({ url: z.string().describe("The URL to navigate to"), diff --git a/src/tools/observe.ts b/src/tools/observe.ts index ec44889..4470214 100644 --- a/src/tools/observe.ts +++ b/src/tools/observe.ts @@ -1,7 +1,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { ToolActionResult } from "../types/types.js"; const ObserveInputSchema = z.object({ instruction: z diff --git a/src/tools/screenshot.ts b/src/tools/screenshot.ts index 4a024a7..95d3d54 100644 --- a/src/tools/screenshot.ts +++ b/src/tools/screenshot.ts @@ -1,7 +1,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { ToolActionResult } from "../types/types.js"; import { screenshots } from "../mcp/resources.js"; const ScreenshotInputSchema = z.object({ diff --git a/src/tools/session.ts b/src/tools/session.ts index 30c403f..691b40f 100644 --- a/src/tools/session.ts +++ b/src/tools/session.ts @@ -1,7 +1,7 @@ import { z } from "zod"; import type { Tool, ToolSchema, ToolResult } from "./tool.js"; import type { Context } from "../context.js"; -import type { ToolActionResult } from "../context.js"; +import type { ToolActionResult } from "../types/types.js"; // Import SessionManager functions import { @@ -10,8 +10,8 @@ import { ensureDefaultSessionInternal, cleanupSession, getSession, - type BrowserSession, } from "../sessionManager.js"; +import type { BrowserSession } from "../types/types.js"; // --- Tool: Create Session --- const CreateSessionInputSchema = z.object({ @@ -113,13 +113,7 @@ const createSessionTool: Tool = { }; // --- Tool: Close Session --- -const CloseSessionInputSchema = z.object({ - random_string: z - .string() - .optional() - .describe("Dummy parameter to ensure consistent tool call format."), -}); -type CloseSessionInput = z.infer; +const CloseSessionInputSchema = z.object({}); const closeSessionSchema: ToolSchema = { name: "browserbase_session_close", @@ -128,10 +122,7 @@ const closeSessionSchema: ToolSchema = { inputSchema: CloseSessionInputSchema, }; -async function handleCloseSession( - context: Context, - _params: CloseSessionInput, -): Promise { +async function handleCloseSession(context: Context): Promise { const action = async (): Promise => { // Store the current session ID before it's potentially changed. const previousSessionId = context.currentSessionId; diff --git a/src/types/types.ts b/src/types/types.ts index 78752ae..bba3bd7 100644 --- a/src/types/types.ts +++ b/src/types/types.ts @@ -1,5 +1,8 @@ -import { Stagehand } from "@browserbasehq/stagehand"; -import { Browser, Page } from "playwright-core"; +import type { Stagehand } from "@browserbasehq/stagehand"; +import type { Browser, Page } from "playwright-core"; +import { ImageContent, TextContent } from "@modelcontextprotocol/sdk/types.js"; +import { Tool } from "../tools/tool.js"; +import { InputType } from "../tools/tool.js"; export type StagehandSession = { id: string; // MCP-side ID @@ -14,7 +17,24 @@ export type CreateSessionParams = { apiKey?: string; projectId?: string; modelName?: string; + modelApiKey?: string; browserbaseSessionID?: string; browserbaseSessionCreateParams?: any; meta?: Record; }; + +export type BrowserSession = { + browser: Browser; + page: Page; + sessionId: string; + stagehand: Stagehand; +}; + +export type ToolActionResult = + | { content?: (ImageContent | TextContent)[] } + | undefined + | void; + +// Type for the tools array used in MCP server registration +export type MCPTool = Tool; +export type MCPToolsArray = MCPTool[]; From 64d70df8e62e8a61c0543eb9665821374fe9b4b6 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Wed, 2 Jul 2025 23:17:46 -0700 Subject: [PATCH 20/32] typo in navigate tool --- src/tools/navigate.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/tools/navigate.ts b/src/tools/navigate.ts index 1f77ae9..0f231f8 100644 --- a/src/tools/navigate.ts +++ b/src/tools/navigate.ts @@ -12,7 +12,7 @@ type NavigateInput = z.infer; const navigateSchema: ToolSchema = { name: "browserbase_stagehand_navigate", description: - "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otheriwse use https://google.com as the starting point", + "Navigate to a URL in the browser. Only use this tool with URLs you're confident will work and stay up to date. Otherwise, use https://google.com as the starting point", inputSchema: NavigateInputSchema, }; From 763acafe0a0f6766ae49fd350c8ea8805a8f174b Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 00:22:40 -0700 Subject: [PATCH 21/32] fix potential mem leak, pnpm, prompts session typeof --- .github/workflows/ci.yml | 12 +- .github/workflows/publish.yml | 10 +- .npmrc | 4 + README.md | 60 +- package-lock.json | 6383 --------------------------------- package.json | 2 +- pnpm-workspace.yaml | 2 + src/config.ts | 15 - src/mcp/prompts.ts | 21 - src/stagehandStore.ts | 20 +- src/tools/session.ts | 12 +- src/utils.ts | 28 - tsconfig.json | 2 +- 13 files changed, 107 insertions(+), 6464 deletions(-) create mode 100644 .npmrc delete mode 100644 package-lock.json create mode 100644 pnpm-workspace.yaml delete mode 100644 src/utils.ts diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 2bf6aa3..1ab78b1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -15,11 +15,15 @@ jobs: uses: actions/setup-node@v4 with: node-version: '22' - cache: 'npm' + cache: 'pnpm' + - name: Install pnpm + uses: pnpm/action-setup@v4 + with: + version: 8 - name: Install dependencies - run: npm ci - - run: npm run build + run: pnpm install --frozen-lockfile + - run: pnpm run build - name: Run ESLint - run: npm run lint + run: pnpm run lint - name: Ensure no changes run: git diff --exit-code \ No newline at end of file diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 199020a..e6586f9 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -14,8 +14,12 @@ jobs: with: node-version: 22 registry-url: https://registry.npmjs.org/ - - run: npm ci - - run: npm run build - - run: npm publish --provenance + - name: Install pnpm + uses: pnpm/action-setup@v4 + with: + version: 8 + - run: pnpm install --frozen-lockfile + - run: pnpm run build + - run: pnpm publish --provenance env: NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} \ No newline at end of file diff --git a/.npmrc b/.npmrc new file mode 100644 index 0000000..0a6ad7b --- /dev/null +++ b/.npmrc @@ -0,0 +1,4 @@ +# Use pnpm for package management +engine-strict=true +auto-install-peers=true +strict-peer-dependencies=false \ No newline at end of file diff --git a/README.md b/README.md index a4cfdb9..e66dbbf 100644 --- a/README.md +++ b/README.md @@ -25,6 +25,16 @@ This server provides cloud browser automation capabilities using [Browserbase](h [Smithery](https://smithery.ai/server/@browserbasehq/mcp-browserbase) +## Prerequisites + +This project uses [pnpm](https://pnpm.io/) as the package manager. If you don't have pnpm installed, you can install it via: + +```bash +npm install -g pnpm +# or +curl -fsSL https://get.pnpm.io/install.sh | sh +``` + ## How to Setup ### Quickstarts: @@ -62,7 +72,7 @@ git clone https://github.com/browserbase/mcp-server-browserbase.git cd mcp-server-browserbase # Install the dependencies and build the project -npm install && npm run build +pnpm install && pnpm build ``` Then in your MCP Config JSON run the server. To run locally we can use STDIO or self-host SHTTP. @@ -112,6 +122,54 @@ Then in your MCP Config JSON file put the following: Then reload your MCP client and you should be good to go! +## Development + +### Getting Started + +1. **Clone the repository:** + + ```bash + git clone https://github.com/browserbase/mcp-server-browserbase.git + cd mcp-server-browserbase + ``` + +2. **Install dependencies:** + + ```bash + pnpm install + ``` + +3. **Build the project:** + + ```bash + pnpm run build + ``` + +4. **Run in development mode:** + ```bash + pnpm run watch + ``` + +### Available Scripts + +- `pnpm build` - Build the TypeScript project +- `pnpm watch` - Watch for changes and rebuild +- `pnpm lint` - Run ESLint +- `pnpm prettier:check` - Check code formatting +- `pnpm prettier:fix` - Fix code formatting +- `pnpm clean` - Clean build artifacts +- `pnpm publish` - Build and publish to npm registry + +### Publishing + +To publish a new version: + +```bash +pnpm run publish +``` + +This will clean, build, and publish the package using pnpm's built-in publishing capabilities. + ## Configuration The Browserbase MCP server accepts the following command-line flags: diff --git a/package-lock.json b/package-lock.json deleted file mode 100644 index fa199e3..0000000 --- a/package-lock.json +++ /dev/null @@ -1,6383 +0,0 @@ -{ - "name": "@browserbasehq/mcp", - "version": "2.0.0", - "lockfileVersion": 3, - "requires": true, - "packages": { - "": { - "name": "@browserbasehq/mcp", - "version": "2.0.0", - "license": "Apache-2.0", - "dependencies": { - "@browserbasehq/stagehand": "^2.4.0", - "@modelcontextprotocol/sdk": "^1.13.1", - "@playwright/test": "^1.49.0", - "commander": "^14.0.0", - "dotenv": "^16.4.6", - "playwright-core": "^1.53.2", - "zod": "^3.25.67" - }, - "bin": { - "mcp-server-stagehand": "cli.js" - }, - "devDependencies": { - "@eslint/js": "^9.29.0", - "eslint": "^9.29.0", - "eslint-plugin-react": "^7.37.5", - "globals": "^16.2.0", - "husky": "^9.1.7", - "lint-staged": "^16.1.2", - "prettier": "^3.6.1", - "shx": "^0.3.4", - "typescript": "^5.6.2", - "typescript-eslint": "^8.35.0" - } - }, - "node_modules/@ai-sdk/anthropic": { - "version": "1.2.12", - "resolved": "https://registry.npmjs.org/@ai-sdk/anthropic/-/anthropic-1.2.12.tgz", - "integrity": "sha512-YSzjlko7JvuiyQFmI9RN1tNZdEiZxc+6xld/0tq/VkJaHpEzGAb1yiNxxvmYVcjvfu/PcvCxAAYXmTYQQ63IHQ==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/azure": { - "version": "1.3.23", - "resolved": "https://registry.npmjs.org/@ai-sdk/azure/-/azure-1.3.23.tgz", - "integrity": "sha512-vpsaPtU24RBVk/IMM5UylR/N4RtAuL2NZLWc7LJ3tvMTHu6pI46a7w+1qIwR3F6yO9ehWR8qvfLaBefJNFxaVw==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/openai": "1.3.22", - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/cerebras": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@ai-sdk/cerebras/-/cerebras-0.2.14.tgz", - "integrity": "sha512-BIDf9hfgAEEu3xhNUyBWvAzeSgt7A7cSMj7UcKS4jhBDybRoKjoEGWHC7916j8LS/5Hkdmo6jwaxWxn/gZJYbQ==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/openai-compatible": "0.2.14", - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/deepseek": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@ai-sdk/deepseek/-/deepseek-0.2.14.tgz", - "integrity": "sha512-TISD1FzBWuQkHEHoVustoJILV33ZNgfYxeTkq1xU2vHEZuWTGZV7/IlXixyFsfqDCdVgrbLeIABk5FuCw7niLg==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/openai-compatible": "0.2.14", - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/google": { - "version": "1.2.19", - "resolved": "https://registry.npmjs.org/@ai-sdk/google/-/google-1.2.19.tgz", - "integrity": "sha512-Xgl6eftIRQ4srUdCzxM112JuewVMij5q4JLcNmHcB68Bxn9dpr3MVUSPlJwmameuiQuISIA8lMB+iRiRbFsaqA==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/groq": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/@ai-sdk/groq/-/groq-1.2.9.tgz", - "integrity": "sha512-7MoDaxm8yWtiRbD1LipYZG0kBl+Xe0sv/EeyxnHnGPZappXdlgtdOgTZVjjXkT3nWP30jjZi9A45zoVrBMb3Xg==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/mistral": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/@ai-sdk/mistral/-/mistral-1.2.8.tgz", - "integrity": "sha512-lv857D9UJqCVxiq2Fcu7mSPTypEHBUqLl1K+lCaP6X/7QAkcaxI36QDONG+tOhGHJOXTsS114u8lrUTaEiGXbg==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/openai": { - "version": "1.3.22", - "resolved": "https://registry.npmjs.org/@ai-sdk/openai/-/openai-1.3.22.tgz", - "integrity": "sha512-QwA+2EkG0QyjVR+7h6FE7iOu2ivNqAVMm9UJZkVxxTk5OIq5fFJDTEI/zICEMuHImTTXR2JjsL6EirJ28Jc4cw==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/openai-compatible": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@ai-sdk/openai-compatible/-/openai-compatible-0.2.14.tgz", - "integrity": "sha512-icjObfMCHKSIbywijaoLdZ1nSnuRnWgMEMLgwoxPJgxsUHMx0aVORnsLUid4SPtdhHI3X2masrt6iaEQLvOSFw==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/perplexity": { - "version": "1.1.9", - "resolved": "https://registry.npmjs.org/@ai-sdk/perplexity/-/perplexity-1.1.9.tgz", - "integrity": "sha512-Ytolh/v2XupXbTvjE18EFBrHLoNMH0Ueji3lfSPhCoRUfkwrgZ2D9jlNxvCNCCRiGJG5kfinSHvzrH5vGDklYA==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/provider": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/@ai-sdk/provider/-/provider-1.1.3.tgz", - "integrity": "sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==", - "license": "Apache-2.0", - "dependencies": { - "json-schema": "^0.4.0" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@ai-sdk/provider-utils": { - "version": "2.2.8", - "resolved": "https://registry.npmjs.org/@ai-sdk/provider-utils/-/provider-utils-2.2.8.tgz", - "integrity": "sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==", - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "nanoid": "^3.3.8", - "secure-json-parse": "^2.7.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.23.8" - } - }, - "node_modules/@ai-sdk/react": { - "version": "1.2.12", - "resolved": "https://registry.npmjs.org/@ai-sdk/react/-/react-1.2.12.tgz", - "integrity": "sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==", - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider-utils": "2.2.8", - "@ai-sdk/ui-utils": "1.2.11", - "swr": "^2.2.5", - "throttleit": "2.1.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "react": "^18 || ^19 || ^19.0.0-rc", - "zod": "^3.23.8" - }, - "peerDependenciesMeta": { - "zod": { - "optional": true - } - } - }, - "node_modules/@ai-sdk/togetherai": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/@ai-sdk/togetherai/-/togetherai-0.2.14.tgz", - "integrity": "sha512-tdCe5kawsQrnMZB8aF1iL1P3+NfrPwILH9UudAZ5cNVY5dTFl+mXk3R37YJS+mkWeAoedr8Cb7mAuGxR47bsFw==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/openai-compatible": "0.2.14", - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@ai-sdk/ui-utils": { - "version": "1.2.11", - "resolved": "https://registry.npmjs.org/@ai-sdk/ui-utils/-/ui-utils-1.2.11.tgz", - "integrity": "sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==", - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8", - "zod-to-json-schema": "^3.24.1" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.23.8" - } - }, - "node_modules/@ai-sdk/xai": { - "version": "1.2.16", - "resolved": "https://registry.npmjs.org/@ai-sdk/xai/-/xai-1.2.16.tgz", - "integrity": "sha512-UOZT8td9PWwMi2dF9a0U44t/Oltmf6QmIJdSvrOcLG4mvpRc1UJn6YJaR0HtXs3YnW6SvY1zRdIDrW4GFpv4NA==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/openai-compatible": "0.2.14", - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - } - }, - "node_modules/@anthropic-ai/sdk": { - "version": "0.39.0", - "resolved": "https://registry.npmjs.org/@anthropic-ai/sdk/-/sdk-0.39.0.tgz", - "integrity": "sha512-eMyDIPRZbt1CCLErRCi3exlAvNkBtRe+kW5vvJyef93PmNr/clstYgHhtvmkxN82nlKgzyGPCyGxrm0JQ1ZIdg==", - "license": "MIT", - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - } - }, - "node_modules/@browserbasehq/sdk": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@browserbasehq/sdk/-/sdk-2.5.0.tgz", - "integrity": "sha512-bcnbYZvm5Ht1nrHUfWDK4crspiTy1ESJYMApsMiOTUnlKOan0ocRD6m7hZH34iSC2c2XWsoryR80cwsYgCBWzQ==", - "license": "Apache-2.0", - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - } - }, - "node_modules/@browserbasehq/stagehand": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@browserbasehq/stagehand/-/stagehand-2.4.0.tgz", - "integrity": "sha512-Jna8wG55D6FtI3KpsabrNvGKAS7FuM2cIloHJuGDjRvZ5vis7loRhPBQCI+rrhkBcT4b68Ic8MI9WTvuXi/N8g==", - "license": "MIT", - "dependencies": { - "@anthropic-ai/sdk": "0.39.0", - "@browserbasehq/sdk": "^2.4.0", - "@google/genai": "^0.8.0", - "ai": "^4.3.9", - "devtools-protocol": "^0.0.1464554", - "fetch-cookie": "^3.1.0", - "openai": "^4.87.1", - "pino": "^9.6.0", - "pino-pretty": "^13.0.0", - "playwright": "^1.52.0", - "ws": "^8.18.0", - "zod-to-json-schema": "^3.23.5" - }, - "optionalDependencies": { - "@ai-sdk/anthropic": "^1.2.6", - "@ai-sdk/azure": "^1.3.19", - "@ai-sdk/cerebras": "^0.2.6", - "@ai-sdk/deepseek": "^0.2.13", - "@ai-sdk/google": "^1.2.6", - "@ai-sdk/groq": "^1.2.4", - "@ai-sdk/mistral": "^1.2.7", - "@ai-sdk/openai": "^1.0.14", - "@ai-sdk/perplexity": "^1.1.7", - "@ai-sdk/togetherai": "^0.2.6", - "@ai-sdk/xai": "^1.2.15", - "ollama-ai-provider": "^1.2.0" - }, - "peerDependencies": { - "deepmerge": "^4.3.1", - "dotenv": "^16.4.5", - "zod": "^3.23.8" - } - }, - "node_modules/@browserbasehq/stagehand/node_modules/playwright": { - "version": "1.53.1", - "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.53.1.tgz", - "integrity": "sha512-LJ13YLr/ocweuwxyGf1XNFWIU4M2zUSo149Qbp+A4cpwDjsxRPj7k6H25LBrEHiEwxvRbD8HdwvQmRMSvquhYw==", - "license": "Apache-2.0", - "dependencies": { - "playwright-core": "1.53.1" - }, - "bin": { - "playwright": "cli.js" - }, - "engines": { - "node": ">=18" - }, - "optionalDependencies": { - "fsevents": "2.3.2" - } - }, - "node_modules/@browserbasehq/stagehand/node_modules/playwright-core": { - "version": "1.53.1", - "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.53.1.tgz", - "integrity": "sha512-Z46Oq7tLAyT0lGoFx4DOuB1IA9D1TPj0QkYxpPVUnGDqHHvDpCftu1J2hM2PiWsNMoZh8+LQaarAWcDfPBc6zg==", - "license": "Apache-2.0", - "bin": { - "playwright-core": "cli.js" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@eslint-community/eslint-utils": { - "version": "4.7.0", - "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.7.0.tgz", - "integrity": "sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==", - "dev": true, - "license": "MIT", - "dependencies": { - "eslint-visitor-keys": "^3.4.3" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - }, - "peerDependencies": { - "eslint": "^6.0.0 || ^7.0.0 || >=8.0.0" - } - }, - "node_modules/@eslint-community/eslint-utils/node_modules/eslint-visitor-keys": { - "version": "3.4.3", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz", - "integrity": "sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/@eslint-community/regexpp": { - "version": "4.12.1", - "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.12.1.tgz", - "integrity": "sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^12.0.0 || ^14.0.0 || >=16.0.0" - } - }, - "node_modules/@eslint/config-array": { - "version": "0.21.0", - "resolved": "https://registry.npmjs.org/@eslint/config-array/-/config-array-0.21.0.tgz", - "integrity": "sha512-ENIdc4iLu0d93HeYirvKmrzshzofPw6VkZRKQGe9Nv46ZnWUzcF1xV01dcvEg/1wXUR61OmmlSfyeyO7EvjLxQ==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@eslint/object-schema": "^2.1.6", - "debug": "^4.3.1", - "minimatch": "^3.1.2" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@eslint/config-helpers": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/@eslint/config-helpers/-/config-helpers-0.3.0.tgz", - "integrity": "sha512-ViuymvFmcJi04qdZeDc2whTHryouGcDlaxPqarTD0ZE10ISpxGUVZGZDx4w01upyIynL3iu6IXH2bS1NhclQMw==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@eslint/core": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.14.0.tgz", - "integrity": "sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@types/json-schema": "^7.0.15" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@eslint/eslintrc": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-3.3.1.tgz", - "integrity": "sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "ajv": "^6.12.4", - "debug": "^4.3.2", - "espree": "^10.0.1", - "globals": "^14.0.0", - "ignore": "^5.2.0", - "import-fresh": "^3.2.1", - "js-yaml": "^4.1.0", - "minimatch": "^3.1.2", - "strip-json-comments": "^3.1.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/@eslint/eslintrc/node_modules/globals": { - "version": "14.0.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-14.0.0.tgz", - "integrity": "sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/@eslint/js": { - "version": "9.30.0", - "resolved": "https://registry.npmjs.org/@eslint/js/-/js-9.30.0.tgz", - "integrity": "sha512-Wzw3wQwPvc9sHM+NjakWTcPx11mbZyiYHuwWa/QfZ7cIRX7WK54PSk7bdyXDaoaopUcMatv1zaQvOAAO8hCdww==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://eslint.org/donate" - } - }, - "node_modules/@eslint/object-schema": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/@eslint/object-schema/-/object-schema-2.1.6.tgz", - "integrity": "sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@eslint/plugin-kit": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/@eslint/plugin-kit/-/plugin-kit-0.3.3.tgz", - "integrity": "sha512-1+WqvgNMhmlAambTvT3KPtCl/Ibr68VldY2XY40SL1CE0ZXiakFR/cbTspaF5HsnpDMvcYYoJHfl4980NBjGag==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@eslint/core": "^0.15.1", - "levn": "^0.4.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@eslint/plugin-kit/node_modules/@eslint/core": { - "version": "0.15.1", - "resolved": "https://registry.npmjs.org/@eslint/core/-/core-0.15.1.tgz", - "integrity": "sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@types/json-schema": "^7.0.15" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - } - }, - "node_modules/@google/genai": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/@google/genai/-/genai-0.8.0.tgz", - "integrity": "sha512-Zs+OGyZKyMbFofGJTR9/jTQSv8kITh735N3tEuIZj4VlMQXTC0soCFahysJ9NaeenRlD7xGb6fyqmX+FwrpU6Q==", - "license": "Apache-2.0", - "dependencies": { - "google-auth-library": "^9.14.2", - "ws": "^8.18.0" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/@humanfs/core": { - "version": "0.19.1", - "resolved": "https://registry.npmjs.org/@humanfs/core/-/core-0.19.1.tgz", - "integrity": "sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=18.18.0" - } - }, - "node_modules/@humanfs/node": { - "version": "0.16.6", - "resolved": "https://registry.npmjs.org/@humanfs/node/-/node-0.16.6.tgz", - "integrity": "sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "@humanfs/core": "^0.19.1", - "@humanwhocodes/retry": "^0.3.0" - }, - "engines": { - "node": ">=18.18.0" - } - }, - "node_modules/@humanfs/node/node_modules/@humanwhocodes/retry": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.3.1.tgz", - "integrity": "sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=18.18" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" - } - }, - "node_modules/@humanwhocodes/module-importer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", - "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=12.22" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" - } - }, - "node_modules/@humanwhocodes/retry": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.4.3.tgz", - "integrity": "sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": ">=18.18" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/nzakas" - } - }, - "node_modules/@modelcontextprotocol/sdk": { - "version": "1.13.1", - "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.13.1.tgz", - "integrity": "sha512-8q6+9aF0yA39/qWT/uaIj6zTpC+Qu07DnN/lb9mjoquCJsAh6l3HyYqc9O3t2j7GilseOQOQimLg7W3By6jqvg==", - "license": "MIT", - "dependencies": { - "ajv": "^6.12.6", - "content-type": "^1.0.5", - "cors": "^2.8.5", - "cross-spawn": "^7.0.5", - "eventsource": "^3.0.2", - "express": "^5.0.1", - "express-rate-limit": "^7.5.0", - "pkce-challenge": "^5.0.0", - "raw-body": "^3.0.0", - "zod": "^3.23.8", - "zod-to-json-schema": "^3.24.1" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@nodelib/fs.scandir": { - "version": "2.1.5", - "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", - "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", - "dev": true, - "license": "MIT", - "dependencies": { - "@nodelib/fs.stat": "2.0.5", - "run-parallel": "^1.1.9" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/@nodelib/fs.stat": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", - "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 8" - } - }, - "node_modules/@nodelib/fs.walk": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", - "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@nodelib/fs.scandir": "2.1.5", - "fastq": "^1.6.0" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/@opentelemetry/api": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.0.tgz", - "integrity": "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==", - "license": "Apache-2.0", - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/@playwright/test": { - "version": "1.51.0", - "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.51.0.tgz", - "integrity": "sha512-dJ0dMbZeHhI+wb77+ljx/FeC8VBP6j/rj9OAojO08JI80wTZy6vRk9KvHKiDCUh4iMpEiseMgqRBIeW+eKX6RA==", - "license": "Apache-2.0", - "dependencies": { - "playwright": "1.51.0" - }, - "bin": { - "playwright": "cli.js" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/@types/diff-match-patch": { - "version": "1.0.36", - "resolved": "https://registry.npmjs.org/@types/diff-match-patch/-/diff-match-patch-1.0.36.tgz", - "integrity": "sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==", - "license": "MIT" - }, - "node_modules/@types/estree": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", - "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", - "dev": true, - "license": "MIT" - }, - "node_modules/@types/json-schema": { - "version": "7.0.15", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", - "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", - "dev": true, - "license": "MIT" - }, - "node_modules/@types/node": { - "version": "18.19.80", - "resolved": "https://registry.npmjs.org/@types/node/-/node-18.19.80.tgz", - "integrity": "sha512-kEWeMwMeIvxYkeg1gTc01awpwLbfMRZXdIhwRcakd/KlK53jmRC26LqcbIt7fnAQTu5GzlnWmzA3H6+l1u6xxQ==", - "license": "MIT", - "dependencies": { - "undici-types": "~5.26.4" - } - }, - "node_modules/@types/node-fetch": { - "version": "2.6.12", - "resolved": "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-2.6.12.tgz", - "integrity": "sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA==", - "license": "MIT", - "dependencies": { - "@types/node": "*", - "form-data": "^4.0.0" - } - }, - "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.35.1.tgz", - "integrity": "sha512-9XNTlo7P7RJxbVeICaIIIEipqxLKguyh+3UbXuT2XQuFp6d8VOeDEGuz5IiX0dgZo8CiI6aOFLg4e8cF71SFVg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.35.1", - "@typescript-eslint/type-utils": "8.35.1", - "@typescript-eslint/utils": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", - "graphemer": "^1.4.0", - "ignore": "^7.0.0", - "natural-compare": "^1.4.0", - "ts-api-utils": "^2.1.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "@typescript-eslint/parser": "^8.35.1", - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/eslint-plugin/node_modules/ignore": { - "version": "7.0.5", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-7.0.5.tgz", - "integrity": "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/@typescript-eslint/parser": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.35.1.tgz", - "integrity": "sha512-3MyiDfrfLeK06bi/g9DqJxP5pV74LNv4rFTyvGDmT3x2p1yp1lOd+qYZfiRPIOf/oON+WRZR5wxxuF85qOar+w==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/scope-manager": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/typescript-estree": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", - "debug": "^4.3.4" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/project-service": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.35.1.tgz", - "integrity": "sha512-VYxn/5LOpVxADAuP3NrnxxHYfzVtQzLKeldIhDhzC8UHaiQvYlXvKuVho1qLduFbJjjy5U5bkGwa3rUGUb1Q6Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.35.1", - "@typescript-eslint/types": "^8.35.1", - "debug": "^4.3.4" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/scope-manager": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.35.1.tgz", - "integrity": "sha512-s/Bpd4i7ht2934nG+UoSPlYXd08KYz3bmjLEb7Ye1UVob0d1ENiT3lY8bsCmik4RqfSbPw9xJJHbugpPpP5JUg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.35.1.tgz", - "integrity": "sha512-K5/U9VmT9dTHoNowWZpz+/TObS3xqC5h0xAIjXPw+MNcKV9qg6eSatEnmeAwkjHijhACH0/N7bkhKvbt1+DXWQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/type-utils": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.35.1.tgz", - "integrity": "sha512-HOrUBlfVRz5W2LIKpXzZoy6VTZzMu2n8q9C2V/cFngIC5U1nStJgv0tMV4sZPzdf4wQm9/ToWUFPMN9Vq9VJQQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/typescript-estree": "8.35.1", - "@typescript-eslint/utils": "8.35.1", - "debug": "^4.3.4", - "ts-api-utils": "^2.1.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/types": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.35.1.tgz", - "integrity": "sha512-q/O04vVnKHfrrhNAscndAn1tuQhIkwqnaW+eu5waD5IPts2eX1dgJxgqcPx5BX109/qAz7IG6VrEPTOYKCNfRQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.35.1.tgz", - "integrity": "sha512-Vvpuvj4tBxIka7cPs6Y1uvM7gJgdF5Uu9F+mBJBPY4MhvjrjWGK4H0lVgLJd/8PWZ23FTqsaJaLEkBCFUk8Y9g==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/project-service": "8.35.1", - "@typescript-eslint/tsconfig-utils": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/visitor-keys": "8.35.1", - "debug": "^4.3.4", - "fast-glob": "^3.3.2", - "is-glob": "^4.0.3", - "minimatch": "^9.0.4", - "semver": "^7.6.0", - "ts-api-utils": "^2.1.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/typescript-estree/node_modules/brace-expansion": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz", - "integrity": "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0" - } - }, - "node_modules/@typescript-eslint/typescript-estree/node_modules/minimatch": { - "version": "9.0.5", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz", - "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==", - "dev": true, - "license": "ISC", - "dependencies": { - "brace-expansion": "^2.0.1" - }, - "engines": { - "node": ">=16 || 14 >=14.17" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/@typescript-eslint/typescript-estree/node_modules/semver": { - "version": "7.7.2", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.2.tgz", - "integrity": "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA==", - "dev": true, - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/@typescript-eslint/utils": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.35.1.tgz", - "integrity": "sha512-lhnwatFmOFcazAsUm3ZnZFpXSxiwoa1Lj50HphnDe1Et01NF4+hrdXONSUHIcbVu2eFb1bAf+5yjXkGVkXBKAQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.35.1", - "@typescript-eslint/types": "8.35.1", - "@typescript-eslint/typescript-estree": "8.35.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.35.1.tgz", - "integrity": "sha512-VRwixir4zBWCSTP/ljEo091lbpypz57PoeAQ9imjG+vbeof9LplljsL1mos4ccG6H9IjfrVGM359RozUnuFhpw==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/types": "8.35.1", - "eslint-visitor-keys": "^4.2.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/abort-controller": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", - "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", - "license": "MIT", - "dependencies": { - "event-target-shim": "^5.0.0" - }, - "engines": { - "node": ">=6.5" - } - }, - "node_modules/accepts": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-2.0.0.tgz", - "integrity": "sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==", - "license": "MIT", - "dependencies": { - "mime-types": "^3.0.0", - "negotiator": "^1.0.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/acorn": { - "version": "8.15.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", - "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", - "dev": true, - "license": "MIT", - "bin": { - "acorn": "bin/acorn" - }, - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/acorn-jsx": { - "version": "5.3.2", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", - "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", - "dev": true, - "license": "MIT", - "peerDependencies": { - "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" - } - }, - "node_modules/agent-base": { - "version": "7.1.3", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.3.tgz", - "integrity": "sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==", - "license": "MIT", - "engines": { - "node": ">= 14" - } - }, - "node_modules/agentkeepalive": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.6.0.tgz", - "integrity": "sha512-kja8j7PjmncONqaTsB8fQ+wE2mSU2DJ9D4XKoJ5PFWIdRMa6SLSN1ff4mOr4jCbfRSsxR4keIiySJU0N9T5hIQ==", - "license": "MIT", - "dependencies": { - "humanize-ms": "^1.2.1" - }, - "engines": { - "node": ">= 8.0.0" - } - }, - "node_modules/ai": { - "version": "4.3.16", - "resolved": "https://registry.npmjs.org/ai/-/ai-4.3.16.tgz", - "integrity": "sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==", - "license": "Apache-2.0", - "dependencies": { - "@ai-sdk/provider": "1.1.3", - "@ai-sdk/provider-utils": "2.2.8", - "@ai-sdk/react": "1.2.12", - "@ai-sdk/ui-utils": "1.2.11", - "@opentelemetry/api": "1.9.0", - "jsondiffpatch": "0.6.0" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "react": "^18 || ^19 || ^19.0.0-rc", - "zod": "^3.23.8" - }, - "peerDependenciesMeta": { - "react": { - "optional": true - } - } - }, - "node_modules/ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "license": "MIT", - "dependencies": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" - } - }, - "node_modules/ansi-escapes": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-7.0.0.tgz", - "integrity": "sha512-GdYO7a61mR0fOlAsvC9/rIHf7L96sBc6dEWzeOu+KAea5bZyQRPIpojrVoI4AXGJS/ycu/fBTdLrUkA4ODrvjw==", - "dev": true, - "license": "MIT", - "dependencies": { - "environment": "^1.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/ansi-regex": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", - "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-regex?sponsor=1" - } - }, - "node_modules/ansi-styles": { - "version": "6.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.1.tgz", - "integrity": "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/argparse": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", - "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", - "dev": true, - "license": "Python-2.0" - }, - "node_modules/array-buffer-byte-length": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/array-buffer-byte-length/-/array-buffer-byte-length-1.0.2.tgz", - "integrity": "sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "is-array-buffer": "^3.0.5" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/array-includes": { - "version": "3.1.9", - "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.9.tgz", - "integrity": "sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.4", - "define-properties": "^1.2.1", - "es-abstract": "^1.24.0", - "es-object-atoms": "^1.1.1", - "get-intrinsic": "^1.3.0", - "is-string": "^1.1.1", - "math-intrinsics": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/array.prototype.findlast": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/array.prototype.findlast/-/array.prototype.findlast-1.2.5.tgz", - "integrity": "sha512-CVvd6FHg1Z3POpBLxO6E6zr+rSKEQ9L6rZHAaY7lLfhKsWYUBBOuMs0e9o24oopj6H+geRCX0YJ+TJLBK2eHyQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.7", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.2", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.0.0", - "es-shim-unscopables": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/array.prototype.flat": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.3.tgz", - "integrity": "sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.5", - "es-shim-unscopables": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/array.prototype.flatmap": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.3.tgz", - "integrity": "sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.5", - "es-shim-unscopables": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/array.prototype.tosorted": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/array.prototype.tosorted/-/array.prototype.tosorted-1.1.4.tgz", - "integrity": "sha512-p6Fx8B7b7ZhL/gmUsAy0D15WhvDccw3mnGNbZpi3pmeJdxtWsj2jEaI4Y6oo3XiHfzuSgPwKc04MYt6KgvC/wA==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.7", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.3", - "es-errors": "^1.3.0", - "es-shim-unscopables": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/arraybuffer.prototype.slice": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.4.tgz", - "integrity": "sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "array-buffer-byte-length": "^1.0.1", - "call-bind": "^1.0.8", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.5", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.6", - "is-array-buffer": "^3.0.4" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/async-function": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/async-function/-/async-function-1.0.0.tgz", - "integrity": "sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", - "license": "MIT" - }, - "node_modules/atomic-sleep": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/atomic-sleep/-/atomic-sleep-1.0.0.tgz", - "integrity": "sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==", - "license": "MIT", - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/available-typed-arrays": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.7.tgz", - "integrity": "sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "possible-typed-array-names": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/balanced-match": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", - "dev": true, - "license": "MIT" - }, - "node_modules/base64-js": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", - "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/bignumber.js": { - "version": "9.3.0", - "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.3.0.tgz", - "integrity": "sha512-EM7aMFTXbptt/wZdMlBv2t8IViwQL+h6SLHosp8Yf0dqJMTnY6iL32opnAB6kAdL0SZPuvcAzFr31o0c/R3/RA==", - "license": "MIT", - "engines": { - "node": "*" - } - }, - "node_modules/body-parser": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.1.0.tgz", - "integrity": "sha512-/hPxh61E+ll0Ujp24Ilm64cykicul1ypfwjVttduAiEdtnJFvLePSrIPk+HMImtNv5270wOGCb1Tns2rybMkoQ==", - "license": "MIT", - "dependencies": { - "bytes": "^3.1.2", - "content-type": "^1.0.5", - "debug": "^4.4.0", - "http-errors": "^2.0.0", - "iconv-lite": "^0.5.2", - "on-finished": "^2.4.1", - "qs": "^6.14.0", - "raw-body": "^3.0.0", - "type-is": "^2.0.0" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/body-parser/node_modules/debug": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", - "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", - "license": "MIT", - "dependencies": { - "ms": "^2.1.3" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/body-parser/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" - }, - "node_modules/body-parser/node_modules/qs": { - "version": "6.14.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.14.0.tgz", - "integrity": "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==", - "license": "BSD-3-Clause", - "dependencies": { - "side-channel": "^1.1.0" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "dev": true, - "license": "MIT", - "dependencies": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "node_modules/braces": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", - "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", - "dev": true, - "license": "MIT", - "dependencies": { - "fill-range": "^7.1.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/buffer-equal-constant-time": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", - "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==", - "license": "BSD-3-Clause" - }, - "node_modules/bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/call-bind": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.8.tgz", - "integrity": "sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.0", - "es-define-property": "^1.0.0", - "get-intrinsic": "^1.2.4", - "set-function-length": "^1.2.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/call-bind-apply-helpers": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", - "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/call-bound": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.4.tgz", - "integrity": "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==", - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.2", - "get-intrinsic": "^1.3.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/callsites": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", - "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/chalk": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.4.1.tgz", - "integrity": "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==", - "license": "MIT", - "engines": { - "node": "^12.17.0 || ^14.13 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/cli-cursor": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-5.0.0.tgz", - "integrity": "sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==", - "dev": true, - "license": "MIT", - "dependencies": { - "restore-cursor": "^5.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/cli-truncate": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-4.0.0.tgz", - "integrity": "sha512-nPdaFdQ0h/GEigbPClz11D0v/ZJEwxmeVZGeMo3Z5StPtUTkA9o1lD6QwoirYiSDzbcwn2XcjwmCp68W1IS4TA==", - "dev": true, - "license": "MIT", - "dependencies": { - "slice-ansi": "^5.0.0", - "string-width": "^7.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true, - "license": "MIT" - }, - "node_modules/colorette": { - "version": "2.0.20", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", - "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", - "license": "MIT" - }, - "node_modules/combined-stream": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", - "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", - "license": "MIT", - "dependencies": { - "delayed-stream": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/commander": { - "version": "14.0.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-14.0.0.tgz", - "integrity": "sha512-2uM9rYjPvyq39NwLRqaiLtWHyDC1FvryJDa2ATTVims5YAS4PupsEQsDvP14FqhFr0P49CYDugi59xaxJlTXRA==", - "license": "MIT", - "engines": { - "node": ">=20" - } - }, - "node_modules/concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", - "dev": true, - "license": "MIT" - }, - "node_modules/content-disposition": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.0.0.tgz", - "integrity": "sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==", - "license": "MIT", - "dependencies": { - "safe-buffer": "5.2.1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/content-type": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", - "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.1.tgz", - "integrity": "sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie-signature": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.2.2.tgz", - "integrity": "sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==", - "license": "MIT", - "engines": { - "node": ">=6.6.0" - } - }, - "node_modules/cors": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", - "license": "MIT", - "dependencies": { - "object-assign": "^4", - "vary": "^1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/cross-spawn": { - "version": "7.0.6", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.6.tgz", - "integrity": "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==", - "license": "MIT", - "dependencies": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/data-view-buffer": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.2.tgz", - "integrity": "sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "es-errors": "^1.3.0", - "is-data-view": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/data-view-byte-length": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/data-view-byte-length/-/data-view-byte-length-1.0.2.tgz", - "integrity": "sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "es-errors": "^1.3.0", - "is-data-view": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/inspect-js" - } - }, - "node_modules/data-view-byte-offset": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/data-view-byte-offset/-/data-view-byte-offset-1.0.1.tgz", - "integrity": "sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "is-data-view": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/dateformat": { - "version": "4.6.3", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-4.6.3.tgz", - "integrity": "sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==", - "license": "MIT", - "engines": { - "node": "*" - } - }, - "node_modules/debug": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.6.tgz", - "integrity": "sha512-O/09Bd4Z1fBrU4VzkhFqVgpPzaGbw6Sm9FEkBT1A/YBXQFGuuSxa1dN2nxgxS34JmKXqYx8CZAwEVoJFImUXIg==", - "license": "MIT", - "dependencies": { - "ms": "2.1.2" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/deep-is": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", - "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/deepmerge": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", - "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", - "license": "MIT", - "peer": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/define-data-property": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", - "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", - "dev": true, - "license": "MIT", - "dependencies": { - "es-define-property": "^1.0.0", - "es-errors": "^1.3.0", - "gopd": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/define-properties": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz", - "integrity": "sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==", - "dev": true, - "license": "MIT", - "dependencies": { - "define-data-property": "^1.0.1", - "has-property-descriptors": "^1.0.0", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", - "license": "MIT", - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/dequal": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", - "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/destroy": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", - "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", - "license": "MIT", - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, - "node_modules/devtools-protocol": { - "version": "0.0.1464554", - "resolved": "https://registry.npmjs.org/devtools-protocol/-/devtools-protocol-0.0.1464554.tgz", - "integrity": "sha512-CAoP3lYfwAGQTaAXYvA6JZR0fjGUb7qec1qf4mToyoH2TZgUFeIqYcjh6f9jNuhHfuZiEdH+PONHYrLhRQX6aw==", - "license": "BSD-3-Clause" - }, - "node_modules/diff-match-patch": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/diff-match-patch/-/diff-match-patch-1.0.5.tgz", - "integrity": "sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==", - "license": "Apache-2.0" - }, - "node_modules/doctrine": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", - "dev": true, - "license": "Apache-2.0", - "dependencies": { - "esutils": "^2.0.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/dotenv": { - "version": "16.6.1", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.6.1.tgz", - "integrity": "sha512-uBq4egWHTcTt33a72vpSG0z3HnPuIl6NqYcTrKEg2azoEyl2hpW0zqlxysq2pK9HlDIHyHyakeYaYnSAwd8bow==", - "license": "BSD-2-Clause", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://dotenvx.com" - } - }, - "node_modules/dunder-proto": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", - "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.1", - "es-errors": "^1.3.0", - "gopd": "^1.2.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/ecdsa-sig-formatter": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", - "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", - "license": "Apache-2.0", - "dependencies": { - "safe-buffer": "^5.0.1" - } - }, - "node_modules/ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", - "license": "MIT" - }, - "node_modules/emoji-regex": { - "version": "10.4.0", - "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.4.0.tgz", - "integrity": "sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw==", - "dev": true, - "license": "MIT" - }, - "node_modules/encodeurl": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-2.0.0.tgz", - "integrity": "sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/end-of-stream": { - "version": "1.4.4", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", - "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", - "license": "MIT", - "dependencies": { - "once": "^1.4.0" - } - }, - "node_modules/environment": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/environment/-/environment-1.1.0.tgz", - "integrity": "sha512-xUtoPkMggbz0MPyPiIWr1Kp4aeWJjDZ6SMvURhimjdZgsRuDplF5/s9hcgGhyXMhs+6vpnuoiZ2kFiu3FMnS8Q==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/es-abstract": { - "version": "1.24.0", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.0.tgz", - "integrity": "sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg==", - "dev": true, - "license": "MIT", - "dependencies": { - "array-buffer-byte-length": "^1.0.2", - "arraybuffer.prototype.slice": "^1.0.4", - "available-typed-arrays": "^1.0.7", - "call-bind": "^1.0.8", - "call-bound": "^1.0.4", - "data-view-buffer": "^1.0.2", - "data-view-byte-length": "^1.0.2", - "data-view-byte-offset": "^1.0.1", - "es-define-property": "^1.0.1", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.1.1", - "es-set-tostringtag": "^2.1.0", - "es-to-primitive": "^1.3.0", - "function.prototype.name": "^1.1.8", - "get-intrinsic": "^1.3.0", - "get-proto": "^1.0.1", - "get-symbol-description": "^1.1.0", - "globalthis": "^1.0.4", - "gopd": "^1.2.0", - "has-property-descriptors": "^1.0.2", - "has-proto": "^1.2.0", - "has-symbols": "^1.1.0", - "hasown": "^2.0.2", - "internal-slot": "^1.1.0", - "is-array-buffer": "^3.0.5", - "is-callable": "^1.2.7", - "is-data-view": "^1.0.2", - "is-negative-zero": "^2.0.3", - "is-regex": "^1.2.1", - "is-set": "^2.0.3", - "is-shared-array-buffer": "^1.0.4", - "is-string": "^1.1.1", - "is-typed-array": "^1.1.15", - "is-weakref": "^1.1.1", - "math-intrinsics": "^1.1.0", - "object-inspect": "^1.13.4", - "object-keys": "^1.1.1", - "object.assign": "^4.1.7", - "own-keys": "^1.0.1", - "regexp.prototype.flags": "^1.5.4", - "safe-array-concat": "^1.1.3", - "safe-push-apply": "^1.0.0", - "safe-regex-test": "^1.1.0", - "set-proto": "^1.0.0", - "stop-iteration-iterator": "^1.1.0", - "string.prototype.trim": "^1.2.10", - "string.prototype.trimend": "^1.0.9", - "string.prototype.trimstart": "^1.0.8", - "typed-array-buffer": "^1.0.3", - "typed-array-byte-length": "^1.0.3", - "typed-array-byte-offset": "^1.0.4", - "typed-array-length": "^1.0.7", - "unbox-primitive": "^1.1.0", - "which-typed-array": "^1.1.19" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/es-define-property": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", - "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-errors": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", - "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-iterator-helpers": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.2.1.tgz", - "integrity": "sha512-uDn+FE1yrDzyC0pCo961B2IHbdM8y/ACZsKD4dG6WqrjV53BADjwa7D+1aom2rsNVfLyDgU/eigvlJGJ08OQ4w==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.3", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.6", - "es-errors": "^1.3.0", - "es-set-tostringtag": "^2.0.3", - "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.6", - "globalthis": "^1.0.4", - "gopd": "^1.2.0", - "has-property-descriptors": "^1.0.2", - "has-proto": "^1.2.0", - "has-symbols": "^1.1.0", - "internal-slot": "^1.1.0", - "iterator.prototype": "^1.1.4", - "safe-array-concat": "^1.1.3" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-object-atoms": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", - "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-set-tostringtag": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz", - "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.6", - "has-tostringtag": "^1.0.2", - "hasown": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-shim-unscopables": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.1.0.tgz", - "integrity": "sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw==", - "dev": true, - "license": "MIT", - "dependencies": { - "hasown": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-to-primitive": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.3.0.tgz", - "integrity": "sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-callable": "^1.2.7", - "is-date-object": "^1.0.5", - "is-symbol": "^1.0.4" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "license": "MIT" - }, - "node_modules/escape-string-regexp": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", - "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/eslint": { - "version": "9.30.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-9.30.0.tgz", - "integrity": "sha512-iN/SiPxmQu6EVkf+m1qpBxzUhE12YqFLOSySuOyVLJLEF9nzTf+h/1AJYc1JWzCnktggeNrjvQGLngDzXirU6g==", - "dev": true, - "license": "MIT", - "dependencies": { - "@eslint-community/eslint-utils": "^4.2.0", - "@eslint-community/regexpp": "^4.12.1", - "@eslint/config-array": "^0.21.0", - "@eslint/config-helpers": "^0.3.0", - "@eslint/core": "^0.14.0", - "@eslint/eslintrc": "^3.3.1", - "@eslint/js": "9.30.0", - "@eslint/plugin-kit": "^0.3.1", - "@humanfs/node": "^0.16.6", - "@humanwhocodes/module-importer": "^1.0.1", - "@humanwhocodes/retry": "^0.4.2", - "@types/estree": "^1.0.6", - "@types/json-schema": "^7.0.15", - "ajv": "^6.12.4", - "chalk": "^4.0.0", - "cross-spawn": "^7.0.6", - "debug": "^4.3.2", - "escape-string-regexp": "^4.0.0", - "eslint-scope": "^8.4.0", - "eslint-visitor-keys": "^4.2.1", - "espree": "^10.4.0", - "esquery": "^1.5.0", - "esutils": "^2.0.2", - "fast-deep-equal": "^3.1.3", - "file-entry-cache": "^8.0.0", - "find-up": "^5.0.0", - "glob-parent": "^6.0.2", - "ignore": "^5.2.0", - "imurmurhash": "^0.1.4", - "is-glob": "^4.0.0", - "json-stable-stringify-without-jsonify": "^1.0.1", - "lodash.merge": "^4.6.2", - "minimatch": "^3.1.2", - "natural-compare": "^1.4.0", - "optionator": "^0.9.3" - }, - "bin": { - "eslint": "bin/eslint.js" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://eslint.org/donate" - }, - "peerDependencies": { - "jiti": "*" - }, - "peerDependenciesMeta": { - "jiti": { - "optional": true - } - } - }, - "node_modules/eslint-plugin-react": { - "version": "7.37.5", - "resolved": "https://registry.npmjs.org/eslint-plugin-react/-/eslint-plugin-react-7.37.5.tgz", - "integrity": "sha512-Qteup0SqU15kdocexFNAJMvCJEfa2xUKNV4CC1xsVMrIIqEy3SQ/rqyxCWNzfrd3/ldy6HMlD2e0JDVpDg2qIA==", - "dev": true, - "license": "MIT", - "dependencies": { - "array-includes": "^3.1.8", - "array.prototype.findlast": "^1.2.5", - "array.prototype.flatmap": "^1.3.3", - "array.prototype.tosorted": "^1.1.4", - "doctrine": "^2.1.0", - "es-iterator-helpers": "^1.2.1", - "estraverse": "^5.3.0", - "hasown": "^2.0.2", - "jsx-ast-utils": "^2.4.1 || ^3.0.0", - "minimatch": "^3.1.2", - "object.entries": "^1.1.9", - "object.fromentries": "^2.0.8", - "object.values": "^1.2.1", - "prop-types": "^15.8.1", - "resolve": "^2.0.0-next.5", - "semver": "^6.3.1", - "string.prototype.matchall": "^4.0.12", - "string.prototype.repeat": "^1.0.0" - }, - "engines": { - "node": ">=4" - }, - "peerDependencies": { - "eslint": "^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7" - } - }, - "node_modules/eslint-plugin-react/node_modules/resolve": { - "version": "2.0.0-next.5", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", - "integrity": "sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-core-module": "^2.13.0", - "path-parse": "^1.0.7", - "supports-preserve-symlinks-flag": "^1.0.0" - }, - "bin": { - "resolve": "bin/resolve" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/eslint-scope": { - "version": "8.4.0", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-8.4.0.tgz", - "integrity": "sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==", - "dev": true, - "license": "BSD-2-Clause", - "dependencies": { - "esrecurse": "^4.3.0", - "estraverse": "^5.2.0" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/eslint-visitor-keys": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz", - "integrity": "sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==", - "dev": true, - "license": "Apache-2.0", - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/eslint/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "license": "MIT", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/eslint/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/espree": { - "version": "10.4.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-10.4.0.tgz", - "integrity": "sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==", - "dev": true, - "license": "BSD-2-Clause", - "dependencies": { - "acorn": "^8.15.0", - "acorn-jsx": "^5.3.2", - "eslint-visitor-keys": "^4.2.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "url": "https://opencollective.com/eslint" - } - }, - "node_modules/esquery": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.6.0.tgz", - "integrity": "sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==", - "dev": true, - "license": "BSD-3-Clause", - "dependencies": { - "estraverse": "^5.1.0" - }, - "engines": { - "node": ">=0.10" - } - }, - "node_modules/esrecurse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", - "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", - "dev": true, - "license": "BSD-2-Clause", - "dependencies": { - "estraverse": "^5.2.0" - }, - "engines": { - "node": ">=4.0" - } - }, - "node_modules/estraverse": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", - "dev": true, - "license": "BSD-2-Clause", - "engines": { - "node": ">=4.0" - } - }, - "node_modules/esutils": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", - "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", - "dev": true, - "license": "BSD-2-Clause", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/event-target-shim": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", - "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/eventemitter3": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.1.tgz", - "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==", - "dev": true, - "license": "MIT" - }, - "node_modules/eventsource": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/eventsource/-/eventsource-3.0.5.tgz", - "integrity": "sha512-LT/5J605bx5SNyE+ITBDiM3FxffBiq9un7Vx0EwMDM3vg8sWKx/tO2zC+LMqZ+smAM0F2hblaDZUVZF0te2pSw==", - "license": "MIT", - "dependencies": { - "eventsource-parser": "^3.0.0" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/eventsource-parser": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.0.tgz", - "integrity": "sha512-T1C0XCUimhxVQzW4zFipdx0SficT651NnkR0ZSH3yQwh+mFMdLfgjABVi4YtMTtaL4s168593DaoaRLMqryavA==", - "license": "MIT", - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/express": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/express/-/express-5.0.1.tgz", - "integrity": "sha512-ORF7g6qGnD+YtUG9yx4DFoqCShNMmUKiXuT5oWMHiOvt/4WFbHC6yCwQMTSBMno7AqntNCAzzcnnjowRkTL9eQ==", - "license": "MIT", - "dependencies": { - "accepts": "^2.0.0", - "body-parser": "^2.0.1", - "content-disposition": "^1.0.0", - "content-type": "~1.0.4", - "cookie": "0.7.1", - "cookie-signature": "^1.2.1", - "debug": "4.3.6", - "depd": "2.0.0", - "encodeurl": "~2.0.0", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "^2.0.0", - "fresh": "2.0.0", - "http-errors": "2.0.0", - "merge-descriptors": "^2.0.0", - "methods": "~1.1.2", - "mime-types": "^3.0.0", - "on-finished": "2.4.1", - "once": "1.4.0", - "parseurl": "~1.3.3", - "proxy-addr": "~2.0.7", - "qs": "6.13.0", - "range-parser": "~1.2.1", - "router": "^2.0.0", - "safe-buffer": "5.2.1", - "send": "^1.1.0", - "serve-static": "^2.1.0", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "type-is": "^2.0.0", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/express-rate-limit": { - "version": "7.5.0", - "resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-7.5.0.tgz", - "integrity": "sha512-eB5zbQh5h+VenMPM3fh+nw1YExi5nMr6HUCR62ELSP11huvxm/Uir1H1QEyTkk5QX6A58pX6NmaTMceKZ0Eodg==", - "license": "MIT", - "engines": { - "node": ">= 16" - }, - "funding": { - "url": "https://github.com/sponsors/express-rate-limit" - }, - "peerDependencies": { - "express": "^4.11 || 5 || ^5.0.0-beta.1" - } - }, - "node_modules/extend": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", - "license": "MIT" - }, - "node_modules/fast-copy": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/fast-copy/-/fast-copy-3.0.2.tgz", - "integrity": "sha512-dl0O9Vhju8IrcLndv2eU4ldt1ftXMqqfgN4H1cpmGV7P6jeB9FwpN9a2c8DPGE1Ys88rNUJVYDHq73CGAGOPfQ==", - "license": "MIT" - }, - "node_modules/fast-deep-equal": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "license": "MIT" - }, - "node_modules/fast-glob": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.3.3.tgz", - "integrity": "sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg==", - "dev": true, - "license": "MIT", - "dependencies": { - "@nodelib/fs.stat": "^2.0.2", - "@nodelib/fs.walk": "^1.2.3", - "glob-parent": "^5.1.2", - "merge2": "^1.3.0", - "micromatch": "^4.0.8" - }, - "engines": { - "node": ">=8.6.0" - } - }, - "node_modules/fast-glob/node_modules/glob-parent": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", - "dev": true, - "license": "ISC", - "dependencies": { - "is-glob": "^4.0.1" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/fast-json-stable-stringify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", - "license": "MIT" - }, - "node_modules/fast-levenshtein": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", - "dev": true, - "license": "MIT" - }, - "node_modules/fast-redact": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/fast-redact/-/fast-redact-3.5.0.tgz", - "integrity": "sha512-dwsoQlS7h9hMeYUq1W++23NDcBLV4KqONnITDV9DjfS3q1SgDGVrBdvvTLUotWtPSD7asWDV9/CmsZPy8Hf70A==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/fast-safe-stringify": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", - "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==", - "license": "MIT" - }, - "node_modules/fastq": { - "version": "1.19.1", - "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.19.1.tgz", - "integrity": "sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==", - "dev": true, - "license": "ISC", - "dependencies": { - "reusify": "^1.0.4" - } - }, - "node_modules/fetch-cookie": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/fetch-cookie/-/fetch-cookie-3.1.0.tgz", - "integrity": "sha512-s/XhhreJpqH0ftkGVcQt8JE9bqk+zRn4jF5mPJXWZeQMCI5odV9K+wEWYbnzFPHgQZlvPSMjS4n4yawWE8RINw==", - "license": "Unlicense", - "dependencies": { - "set-cookie-parser": "^2.4.8", - "tough-cookie": "^5.0.0" - } - }, - "node_modules/file-entry-cache": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-8.0.0.tgz", - "integrity": "sha512-XXTUwCvisa5oacNGRP9SfNtYBNAMi+RPwBFmblZEF7N7swHYQS6/Zfk7SRwx4D5j3CH211YNRco1DEMNVfZCnQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "flat-cache": "^4.0.0" - }, - "engines": { - "node": ">=16.0.0" - } - }, - "node_modules/fill-range": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", - "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", - "dev": true, - "license": "MIT", - "dependencies": { - "to-regex-range": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/finalhandler": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-2.1.0.tgz", - "integrity": "sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==", - "license": "MIT", - "dependencies": { - "debug": "^4.4.0", - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "on-finished": "^2.4.1", - "parseurl": "^1.3.3", - "statuses": "^2.0.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/finalhandler/node_modules/debug": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz", - "integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==", - "license": "MIT", - "dependencies": { - "ms": "^2.1.3" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/finalhandler/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" - }, - "node_modules/find-up": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", - "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", - "dev": true, - "license": "MIT", - "dependencies": { - "locate-path": "^6.0.0", - "path-exists": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/flat-cache": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-4.0.1.tgz", - "integrity": "sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==", - "dev": true, - "license": "MIT", - "dependencies": { - "flatted": "^3.2.9", - "keyv": "^4.5.4" - }, - "engines": { - "node": ">=16" - } - }, - "node_modules/flatted": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.3.3.tgz", - "integrity": "sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==", - "dev": true, - "license": "ISC" - }, - "node_modules/for-each": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.5.tgz", - "integrity": "sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-callable": "^1.2.7" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/form-data": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.2.tgz", - "integrity": "sha512-hGfm/slu0ZabnNt4oaRZ6uREyfCj6P4fT/n6A1rGV+Z0VdGXjfOhVUpkn6qVQONHGIFwmveGXyDs75+nr6FM8w==", - "license": "MIT", - "dependencies": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "es-set-tostringtag": "^2.1.0", - "mime-types": "^2.1.12" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/form-data-encoder": { - "version": "1.7.2", - "resolved": "https://registry.npmjs.org/form-data-encoder/-/form-data-encoder-1.7.2.tgz", - "integrity": "sha512-qfqtYan3rxrnCk1VYaA4H+Ms9xdpPqvLZa6xmMgFvhO32x7/3J/ExcTd6qpxM0vH2GdMI+poehyBZvqfMTto8A==", - "license": "MIT" - }, - "node_modules/form-data/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/form-data/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/formdata-node": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/formdata-node/-/formdata-node-4.4.1.tgz", - "integrity": "sha512-0iirZp3uVDjVGt9p49aTaqjk84TrglENEDuqfdlZQ1roC9CWlPk6Avf8EEnZNcAqPonwkG35x4n3ww/1THYAeQ==", - "license": "MIT", - "dependencies": { - "node-domexception": "1.0.0", - "web-streams-polyfill": "4.0.0-beta.3" - }, - "engines": { - "node": ">= 12.20" - } - }, - "node_modules/forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fresh": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-2.0.0.tgz", - "integrity": "sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", - "dev": true, - "license": "ISC" - }, - "node_modules/fsevents": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", - "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", - "hasInstallScript": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" - } - }, - "node_modules/function-bind": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", - "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/function.prototype.name": { - "version": "1.1.8", - "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.8.tgz", - "integrity": "sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.3", - "define-properties": "^1.2.1", - "functions-have-names": "^1.2.3", - "hasown": "^2.0.2", - "is-callable": "^1.2.7" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/functions-have-names": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", - "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", - "dev": true, - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/gaxios": { - "version": "6.7.1", - "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-6.7.1.tgz", - "integrity": "sha512-LDODD4TMYx7XXdpwxAVRAIAuB0bzv0s+ywFonY46k126qzQHT9ygyoa9tncmOiQmmDrik65UYsEkv3lbfqQ3yQ==", - "license": "Apache-2.0", - "dependencies": { - "extend": "^3.0.2", - "https-proxy-agent": "^7.0.1", - "is-stream": "^2.0.0", - "node-fetch": "^2.6.9", - "uuid": "^9.0.1" - }, - "engines": { - "node": ">=14" - } - }, - "node_modules/gcp-metadata": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-6.1.1.tgz", - "integrity": "sha512-a4tiq7E0/5fTjxPAaH4jpjkSv/uCaU2p5KC6HVGrvl0cDjA8iBZv4vv1gyzlmK0ZUKqwpOyQMKzZQe3lTit77A==", - "license": "Apache-2.0", - "dependencies": { - "gaxios": "^6.1.1", - "google-logging-utils": "^0.0.2", - "json-bigint": "^1.0.0" - }, - "engines": { - "node": ">=14" - } - }, - "node_modules/get-east-asian-width": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/get-east-asian-width/-/get-east-asian-width-1.3.0.tgz", - "integrity": "sha512-vpeMIQKxczTD/0s2CdEWHcb0eeJe6TFjxb+J5xgX7hScxqrGuyjmv4c1D4A/gelKfyox0gJJwIHF+fLjeaM8kQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/get-intrinsic": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", - "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", - "license": "MIT", - "dependencies": { - "call-bind-apply-helpers": "^1.0.2", - "es-define-property": "^1.0.1", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.1.1", - "function-bind": "^1.1.2", - "get-proto": "^1.0.1", - "gopd": "^1.2.0", - "has-symbols": "^1.1.0", - "hasown": "^2.0.2", - "math-intrinsics": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/get-proto": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", - "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", - "license": "MIT", - "dependencies": { - "dunder-proto": "^1.0.1", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/get-symbol-description": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.1.0.tgz", - "integrity": "sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.6" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/glob": { - "version": "7.2.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", - "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "deprecated": "Glob versions prior to v9 are no longer supported", - "dev": true, - "license": "ISC", - "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.1.1", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - }, - "engines": { - "node": "*" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/glob-parent": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", - "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", - "dev": true, - "license": "ISC", - "dependencies": { - "is-glob": "^4.0.3" - }, - "engines": { - "node": ">=10.13.0" - } - }, - "node_modules/globals": { - "version": "16.2.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-16.2.0.tgz", - "integrity": "sha512-O+7l9tPdHCU320IigZZPj5zmRCFG9xHmx9cU8FqU2Rp+JN714seHV+2S9+JslCpY4gJwU2vOGox0wzgae/MCEg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/globalthis": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.4.tgz", - "integrity": "sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "define-properties": "^1.2.1", - "gopd": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/google-auth-library": { - "version": "9.15.1", - "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-9.15.1.tgz", - "integrity": "sha512-Jb6Z0+nvECVz+2lzSMt9u98UsoakXxA2HGHMCxh+so3n90XgYWkq5dur19JAJV7ONiJY22yBTyJB1TSkvPq9Ng==", - "license": "Apache-2.0", - "dependencies": { - "base64-js": "^1.3.0", - "ecdsa-sig-formatter": "^1.0.11", - "gaxios": "^6.1.1", - "gcp-metadata": "^6.1.0", - "gtoken": "^7.0.0", - "jws": "^4.0.0" - }, - "engines": { - "node": ">=14" - } - }, - "node_modules/google-logging-utils": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-0.0.2.tgz", - "integrity": "sha512-NEgUnEcBiP5HrPzufUkBzJOD/Sxsco3rLNo1F1TNf7ieU8ryUzBhqba8r756CjLX7rn3fHl6iLEwPYuqpoKgQQ==", - "license": "Apache-2.0", - "engines": { - "node": ">=14" - } - }, - "node_modules/gopd": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", - "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/graphemer": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/graphemer/-/graphemer-1.4.0.tgz", - "integrity": "sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==", - "dev": true, - "license": "MIT" - }, - "node_modules/gtoken": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/gtoken/-/gtoken-7.1.0.tgz", - "integrity": "sha512-pCcEwRi+TKpMlxAQObHDQ56KawURgyAf6jtIY046fJ5tIv3zDe/LEIubckAO8fj6JnAxLdmWkUfNyulQ2iKdEw==", - "license": "MIT", - "dependencies": { - "gaxios": "^6.0.0", - "jws": "^4.0.0" - }, - "engines": { - "node": ">=14.0.0" - } - }, - "node_modules/has-bigints": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz", - "integrity": "sha512-R3pbpkcIqv2Pm3dUwgjclDRVmWpTJW2DcMzcIhEXEx1oh/CEMObMm3KLmRJOdvhM7o4uQBnwr8pzRK2sJWIqfg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/has-property-descriptors": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", - "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", - "dev": true, - "license": "MIT", - "dependencies": { - "es-define-property": "^1.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-proto": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.2.0.tgz", - "integrity": "sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "dunder-proto": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-symbols": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", - "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-tostringtag": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz", - "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==", - "license": "MIT", - "dependencies": { - "has-symbols": "^1.0.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/hasown": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", - "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", - "license": "MIT", - "dependencies": { - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/help-me": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/help-me/-/help-me-5.0.0.tgz", - "integrity": "sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==", - "license": "MIT" - }, - "node_modules/http-errors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", - "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", - "license": "MIT", - "dependencies": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/https-proxy-agent": { - "version": "7.0.6", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", - "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", - "license": "MIT", - "dependencies": { - "agent-base": "^7.1.2", - "debug": "4" - }, - "engines": { - "node": ">= 14" - } - }, - "node_modules/humanize-ms": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", - "integrity": "sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==", - "license": "MIT", - "dependencies": { - "ms": "^2.0.0" - } - }, - "node_modules/husky": { - "version": "9.1.7", - "resolved": "https://registry.npmjs.org/husky/-/husky-9.1.7.tgz", - "integrity": "sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==", - "dev": true, - "license": "MIT", - "bin": { - "husky": "bin.js" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/typicode" - } - }, - "node_modules/iconv-lite": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.5.2.tgz", - "integrity": "sha512-kERHXvpSaB4aU3eANwidg79K8FlrN77m8G9V+0vOR3HYaRifrlwMEpT7ZBJqLSEIHnEgJTHcWK82wwLwwKwtag==", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/ignore": { - "version": "5.3.2", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz", - "integrity": "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, - "node_modules/import-fresh": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.1.tgz", - "integrity": "sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "parent-module": "^1.0.0", - "resolve-from": "^4.0.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.8.19" - } - }, - "node_modules/inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", - "deprecated": "This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful.", - "dev": true, - "license": "ISC", - "dependencies": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "node_modules/inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "license": "ISC" - }, - "node_modules/internal-slot": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.1.0.tgz", - "integrity": "sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==", - "dev": true, - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "hasown": "^2.0.2", - "side-channel": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/interpret": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", - "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/ipaddr.js": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", - "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/is-array-buffer": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.5.tgz", - "integrity": "sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.3", - "get-intrinsic": "^1.2.6" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-async-function": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-async-function/-/is-async-function-2.1.1.tgz", - "integrity": "sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "async-function": "^1.0.0", - "call-bound": "^1.0.3", - "get-proto": "^1.0.1", - "has-tostringtag": "^1.0.2", - "safe-regex-test": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-bigint": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.1.0.tgz", - "integrity": "sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "has-bigints": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-boolean-object": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.2.2.tgz", - "integrity": "sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "has-tostringtag": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-callable": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", - "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-core-module": { - "version": "2.16.1", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.1.tgz", - "integrity": "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==", - "dev": true, - "license": "MIT", - "dependencies": { - "hasown": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-data-view": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-data-view/-/is-data-view-1.0.2.tgz", - "integrity": "sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "get-intrinsic": "^1.2.6", - "is-typed-array": "^1.1.13" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-date-object": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.1.0.tgz", - "integrity": "sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "has-tostringtag": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-finalizationregistry": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-finalizationregistry/-/is-finalizationregistry-1.1.1.tgz", - "integrity": "sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-fullwidth-code-point": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-4.0.0.tgz", - "integrity": "sha512-O4L094N2/dZ7xqVdrXhh9r1KODPJpFms8B5sGdJLPy664AgvXsreZUyCQQNItZRDlYug4xStLjNp/sz3HvBowQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-generator-function": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.1.0.tgz", - "integrity": "sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "get-proto": "^1.0.0", - "has-tostringtag": "^1.0.2", - "safe-regex-test": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-glob": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", - "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-extglob": "^2.1.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-map": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/is-map/-/is-map-2.0.3.tgz", - "integrity": "sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-negative-zero": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz", - "integrity": "sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-number": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.12.0" - } - }, - "node_modules/is-number-object": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.1.1.tgz", - "integrity": "sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "has-tostringtag": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-promise": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-4.0.0.tgz", - "integrity": "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==", - "license": "MIT" - }, - "node_modules/is-regex": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.2.1.tgz", - "integrity": "sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "gopd": "^1.2.0", - "has-tostringtag": "^1.0.2", - "hasown": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-set": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/is-set/-/is-set-2.0.3.tgz", - "integrity": "sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-shared-array-buffer": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.4.tgz", - "integrity": "sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-stream": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", - "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", - "license": "MIT", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-string": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.1.1.tgz", - "integrity": "sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "has-tostringtag": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-symbol": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.1.1.tgz", - "integrity": "sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "has-symbols": "^1.1.0", - "safe-regex-test": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-typed-array": { - "version": "1.1.15", - "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.15.tgz", - "integrity": "sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "which-typed-array": "^1.1.16" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-weakmap": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/is-weakmap/-/is-weakmap-2.0.2.tgz", - "integrity": "sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-weakref": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.1.1.tgz", - "integrity": "sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-weakset": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-weakset/-/is-weakset-2.0.4.tgz", - "integrity": "sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "get-intrinsic": "^1.2.6" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/isarray": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", - "integrity": "sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==", - "dev": true, - "license": "MIT" - }, - "node_modules/isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", - "license": "ISC" - }, - "node_modules/iterator.prototype": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/iterator.prototype/-/iterator.prototype-1.1.5.tgz", - "integrity": "sha512-H0dkQoCa3b2VEeKQBOxFph+JAbcrQdE7KC0UkqwpLmv2EC4P41QXP+rqo9wYodACiG5/WM5s9oDApTU8utwj9g==", - "dev": true, - "license": "MIT", - "dependencies": { - "define-data-property": "^1.1.4", - "es-object-atoms": "^1.0.0", - "get-intrinsic": "^1.2.6", - "get-proto": "^1.0.0", - "has-symbols": "^1.1.0", - "set-function-name": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/joycon": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/joycon/-/joycon-3.1.1.tgz", - "integrity": "sha512-34wB/Y7MW7bzjKRjUKTa46I2Z7eV62Rkhva+KkopW7Qvv/OSWBqvkSY7vusOPrNuZcUG3tApvdVgNB8POj3SPw==", - "license": "MIT", - "engines": { - "node": ">=10" - } - }, - "node_modules/js-tokens": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/js-yaml": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", - "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", - "dev": true, - "license": "MIT", - "dependencies": { - "argparse": "^2.0.1" - }, - "bin": { - "js-yaml": "bin/js-yaml.js" - } - }, - "node_modules/json-bigint": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz", - "integrity": "sha512-SiPv/8VpZuWbvLSMtTDU8hEfrZWg/mH/nV/b4o0CYbSxu1UIQPLdwKOCIyLQX+VIPO5vrLX3i8qtqFyhdPSUSQ==", - "license": "MIT", - "dependencies": { - "bignumber.js": "^9.0.0" - } - }, - "node_modules/json-buffer": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", - "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/json-schema": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", - "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==", - "license": "(AFL-2.1 OR BSD-3-Clause)" - }, - "node_modules/json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "license": "MIT" - }, - "node_modules/json-stable-stringify-without-jsonify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", - "integrity": "sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==", - "dev": true, - "license": "MIT" - }, - "node_modules/jsondiffpatch": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/jsondiffpatch/-/jsondiffpatch-0.6.0.tgz", - "integrity": "sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==", - "license": "MIT", - "dependencies": { - "@types/diff-match-patch": "^1.0.36", - "chalk": "^5.3.0", - "diff-match-patch": "^1.0.5" - }, - "bin": { - "jsondiffpatch": "bin/jsondiffpatch.js" - }, - "engines": { - "node": "^18.0.0 || >=20.0.0" - } - }, - "node_modules/jsx-ast-utils": { - "version": "3.3.5", - "resolved": "https://registry.npmjs.org/jsx-ast-utils/-/jsx-ast-utils-3.3.5.tgz", - "integrity": "sha512-ZZow9HBI5O6EPgSJLUb8n2NKgmVWTwCvHGwFuJlMjvLFqlGG6pjirPhtdsseaLZjSibD8eegzmYpUZwoIlj2cQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "array-includes": "^3.1.6", - "array.prototype.flat": "^1.3.1", - "object.assign": "^4.1.4", - "object.values": "^1.1.6" - }, - "engines": { - "node": ">=4.0" - } - }, - "node_modules/jwa": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.1.tgz", - "integrity": "sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==", - "license": "MIT", - "dependencies": { - "buffer-equal-constant-time": "^1.0.1", - "ecdsa-sig-formatter": "1.0.11", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/jws": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.0.tgz", - "integrity": "sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==", - "license": "MIT", - "dependencies": { - "jwa": "^2.0.0", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/keyv": { - "version": "4.5.4", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", - "integrity": "sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==", - "dev": true, - "license": "MIT", - "dependencies": { - "json-buffer": "3.0.1" - } - }, - "node_modules/levn": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", - "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "prelude-ls": "^1.2.1", - "type-check": "~0.4.0" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/lilconfig": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.3.tgz", - "integrity": "sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/antonk52" - } - }, - "node_modules/lint-staged": { - "version": "16.1.2", - "resolved": "https://registry.npmjs.org/lint-staged/-/lint-staged-16.1.2.tgz", - "integrity": "sha512-sQKw2Si2g9KUZNY3XNvRuDq4UJqpHwF0/FQzZR2M7I5MvtpWvibikCjUVJzZdGE0ByurEl3KQNvsGetd1ty1/Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "chalk": "^5.4.1", - "commander": "^14.0.0", - "debug": "^4.4.1", - "lilconfig": "^3.1.3", - "listr2": "^8.3.3", - "micromatch": "^4.0.8", - "nano-spawn": "^1.0.2", - "pidtree": "^0.6.0", - "string-argv": "^0.3.2", - "yaml": "^2.8.0" - }, - "bin": { - "lint-staged": "bin/lint-staged.js" - }, - "engines": { - "node": ">=20.17" - }, - "funding": { - "url": "https://opencollective.com/lint-staged" - } - }, - "node_modules/lint-staged/node_modules/debug": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.1.tgz", - "integrity": "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "ms": "^2.1.3" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/lint-staged/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "dev": true, - "license": "MIT" - }, - "node_modules/listr2": { - "version": "8.3.3", - "resolved": "https://registry.npmjs.org/listr2/-/listr2-8.3.3.tgz", - "integrity": "sha512-LWzX2KsqcB1wqQ4AHgYb4RsDXauQiqhjLk+6hjbaeHG4zpjjVAB6wC/gz6X0l+Du1cN3pUB5ZlrvTbhGSNnUQQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "cli-truncate": "^4.0.0", - "colorette": "^2.0.20", - "eventemitter3": "^5.0.1", - "log-update": "^6.1.0", - "rfdc": "^1.4.1", - "wrap-ansi": "^9.0.0" - }, - "engines": { - "node": ">=18.0.0" - } - }, - "node_modules/locate-path": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", - "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", - "dev": true, - "license": "MIT", - "dependencies": { - "p-locate": "^5.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/lodash.merge": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", - "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/log-update": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/log-update/-/log-update-6.1.0.tgz", - "integrity": "sha512-9ie8ItPR6tjY5uYJh8K/Zrv/RMZ5VOlOWvtZdEHYSTFKZfIBPQa9tOAEeAWhd+AnIneLJ22w5fjOYtoutpWq5w==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-escapes": "^7.0.0", - "cli-cursor": "^5.0.0", - "slice-ansi": "^7.1.0", - "strip-ansi": "^7.1.0", - "wrap-ansi": "^9.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/log-update/node_modules/is-fullwidth-code-point": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-5.0.0.tgz", - "integrity": "sha512-OVa3u9kkBbw7b8Xw5F9P+D/T9X+Z4+JruYVNapTjPYZYUznQ5YfWeFkOj606XYYW8yugTfC8Pj0hYqvi4ryAhA==", - "dev": true, - "license": "MIT", - "dependencies": { - "get-east-asian-width": "^1.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/log-update/node_modules/slice-ansi": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-7.1.0.tgz", - "integrity": "sha512-bSiSngZ/jWeX93BqeIAbImyTbEihizcwNjFoRUIY/T1wWQsfsm2Vw1agPKylXvQTU7iASGdHhyqRlqQzfz+Htg==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^6.2.1", - "is-fullwidth-code-point": "^5.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/chalk/slice-ansi?sponsor=1" - } - }, - "node_modules/loose-envify": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", - "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "js-tokens": "^3.0.0 || ^4.0.0" - }, - "bin": { - "loose-envify": "cli.js" - } - }, - "node_modules/math-intrinsics": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", - "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/media-typer": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-1.1.0.tgz", - "integrity": "sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/merge-descriptors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-2.0.0.tgz", - "integrity": "sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==", - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/merge2": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", - "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 8" - } - }, - "node_modules/methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/micromatch": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", - "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", - "dev": true, - "license": "MIT", - "dependencies": { - "braces": "^3.0.3", - "picomatch": "^2.3.1" - }, - "engines": { - "node": ">=8.6" - } - }, - "node_modules/mime-db": { - "version": "1.53.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.53.0.tgz", - "integrity": "sha512-oHlN/w+3MQ3rba9rqFr6V/ypF10LSkdwUysQL7GkXoTgIWeV+tcXGA852TBxH+gsh8UWoyhR1hKcoMJTuWflpg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/mime-types": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-3.0.0.tgz", - "integrity": "sha512-XqoSHeCGjVClAmoGFG3lVFqQFRIrTVw2OH3axRqAcfaw+gHWIfnASS92AV+Rl/mk0MupgZTRHQOjxY6YVnzK5w==", - "license": "MIT", - "dependencies": { - "mime-db": "^1.53.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/mimic-function": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/mimic-function/-/mimic-function-5.0.1.tgz", - "integrity": "sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/minimatch": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", - "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", - "dev": true, - "license": "ISC", - "dependencies": { - "brace-expansion": "^1.1.7" - }, - "engines": { - "node": "*" - } - }, - "node_modules/minimist": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", - "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "license": "MIT" - }, - "node_modules/nano-spawn": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/nano-spawn/-/nano-spawn-1.0.2.tgz", - "integrity": "sha512-21t+ozMQDAL/UGgQVBbZ/xXvNO10++ZPuTmKRO8k9V3AClVRht49ahtDjfY8l1q6nSHOrE5ASfthzH3ol6R/hg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=20.17" - }, - "funding": { - "url": "https://github.com/sindresorhus/nano-spawn?sponsor=1" - } - }, - "node_modules/nanoid": { - "version": "3.3.11", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.11.tgz", - "integrity": "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/ai" - } - ], - "license": "MIT", - "bin": { - "nanoid": "bin/nanoid.cjs" - }, - "engines": { - "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" - } - }, - "node_modules/natural-compare": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", - "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", - "dev": true, - "license": "MIT" - }, - "node_modules/negotiator": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-1.0.0.tgz", - "integrity": "sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/node-domexception": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", - "integrity": "sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/jimmywarting" - }, - { - "type": "github", - "url": "https://paypal.me/jimmywarting" - } - ], - "license": "MIT", - "engines": { - "node": ">=10.5.0" - } - }, - "node_modules/node-fetch": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz", - "integrity": "sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==", - "license": "MIT", - "dependencies": { - "whatwg-url": "^5.0.0" - }, - "engines": { - "node": "4.x || >=6.0.0" - }, - "peerDependencies": { - "encoding": "^0.1.0" - }, - "peerDependenciesMeta": { - "encoding": { - "optional": true - } - } - }, - "node_modules/object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/object-inspect": { - "version": "1.13.4", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.4.tgz", - "integrity": "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==", - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object-keys": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", - "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/object.assign": { - "version": "4.1.7", - "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.7.tgz", - "integrity": "sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.3", - "define-properties": "^1.2.1", - "es-object-atoms": "^1.0.0", - "has-symbols": "^1.1.0", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object.entries": { - "version": "1.1.9", - "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.9.tgz", - "integrity": "sha512-8u/hfXFRBD1O0hPUjioLhoWFHRmt6tKA4/vZPyckBr18l1KE9uHrFaFaUi8MDRTpi4uak2goyPTSNJLXX2k2Hw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.4", - "define-properties": "^1.2.1", - "es-object-atoms": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/object.fromentries": { - "version": "2.0.8", - "resolved": "https://registry.npmjs.org/object.fromentries/-/object.fromentries-2.0.8.tgz", - "integrity": "sha512-k6E21FzySsSK5a21KRADBd/NGneRegFO5pLHfdQLpRDETUNJueLXs3WCzyQ3tFRDYgbq3KHGXfTbi2bs8WQ6rQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.7", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.2", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object.values": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.2.1.tgz", - "integrity": "sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.3", - "define-properties": "^1.2.1", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/ollama-ai-provider": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/ollama-ai-provider/-/ollama-ai-provider-1.2.0.tgz", - "integrity": "sha512-jTNFruwe3O/ruJeppI/quoOUxG7NA6blG3ZyQj3lei4+NnJo7bi3eIRWqlVpRlu/mbzbFXeJSBuYQWF6pzGKww==", - "license": "Apache-2.0", - "optional": true, - "dependencies": { - "@ai-sdk/provider": "^1.0.0", - "@ai-sdk/provider-utils": "^2.0.0", - "partial-json": "0.1.7" - }, - "engines": { - "node": ">=18" - }, - "peerDependencies": { - "zod": "^3.0.0" - }, - "peerDependenciesMeta": { - "zod": { - "optional": true - } - } - }, - "node_modules/on-exit-leak-free": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/on-exit-leak-free/-/on-exit-leak-free-2.1.2.tgz", - "integrity": "sha512-0eJJY6hXLGf1udHwfNftBqH+g73EU4B504nZeKpz1sYRKafAghwxEJunB2O7rDZkL4PGfsMVnTXZ2EjibbqcsA==", - "license": "MIT", - "engines": { - "node": ">=14.0.0" - } - }, - "node_modules/on-finished": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", - "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", - "license": "MIT", - "dependencies": { - "ee-first": "1.1.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", - "license": "ISC", - "dependencies": { - "wrappy": "1" - } - }, - "node_modules/onetime": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-7.0.0.tgz", - "integrity": "sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "mimic-function": "^5.0.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/openai": { - "version": "4.92.0", - "resolved": "https://registry.npmjs.org/openai/-/openai-4.92.0.tgz", - "integrity": "sha512-vLIBP8gygD5M7XIrdBkUFKnfEq3EmaI+lmGjDDAmjahzmdhwdpzDA+GBA4ZZwj7rgu1WMNh9/SqyTysxMulC2g==", - "license": "Apache-2.0", - "dependencies": { - "@types/node": "^18.11.18", - "@types/node-fetch": "^2.6.4", - "abort-controller": "^3.0.0", - "agentkeepalive": "^4.2.1", - "form-data-encoder": "1.7.2", - "formdata-node": "^4.3.2", - "node-fetch": "^2.6.7" - }, - "bin": { - "openai": "bin/cli" - }, - "peerDependencies": { - "ws": "^8.18.0", - "zod": "^3.23.8" - }, - "peerDependenciesMeta": { - "ws": { - "optional": true - }, - "zod": { - "optional": true - } - } - }, - "node_modules/optionator": { - "version": "0.9.4", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.4.tgz", - "integrity": "sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==", - "dev": true, - "license": "MIT", - "dependencies": { - "deep-is": "^0.1.3", - "fast-levenshtein": "^2.0.6", - "levn": "^0.4.1", - "prelude-ls": "^1.2.1", - "type-check": "^0.4.0", - "word-wrap": "^1.2.5" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/own-keys": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/own-keys/-/own-keys-1.0.1.tgz", - "integrity": "sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg==", - "dev": true, - "license": "MIT", - "dependencies": { - "get-intrinsic": "^1.2.6", - "object-keys": "^1.1.1", - "safe-push-apply": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/p-limit": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", - "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "yocto-queue": "^0.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-locate": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", - "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", - "dev": true, - "license": "MIT", - "dependencies": { - "p-limit": "^3.0.2" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/parent-module": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", - "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", - "dev": true, - "license": "MIT", - "dependencies": { - "callsites": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/partial-json": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/partial-json/-/partial-json-0.1.7.tgz", - "integrity": "sha512-Njv/59hHaokb/hRUjce3Hdv12wd60MtM9Z5Olmn+nehe0QDAsRtRbJPvJ0Z91TusF0SuZRIvnM+S4l6EIP8leA==", - "license": "MIT", - "optional": true - }, - "node_modules/path-exists": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", - "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/path-key": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", - "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/path-parse": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", - "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", - "dev": true, - "license": "MIT" - }, - "node_modules/path-to-regexp": { - "version": "8.2.0", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-8.2.0.tgz", - "integrity": "sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==", - "license": "MIT", - "engines": { - "node": ">=16" - } - }, - "node_modules/picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=8.6" - }, - "funding": { - "url": "https://github.com/sponsors/jonschlinkert" - } - }, - "node_modules/pidtree": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/pidtree/-/pidtree-0.6.0.tgz", - "integrity": "sha512-eG2dWTVw5bzqGRztnHExczNxt5VGsE6OwTeCG3fdUf9KBsZzO3R5OIIIzWR+iZA0NtZ+RDVdaoE2dK1cn6jH4g==", - "dev": true, - "license": "MIT", - "bin": { - "pidtree": "bin/pidtree.js" - }, - "engines": { - "node": ">=0.10" - } - }, - "node_modules/pino": { - "version": "9.6.0", - "resolved": "https://registry.npmjs.org/pino/-/pino-9.6.0.tgz", - "integrity": "sha512-i85pKRCt4qMjZ1+L7sy2Ag4t1atFcdbEt76+7iRJn1g2BvsnRMGu9p8pivl9fs63M2kF/A0OacFZhTub+m/qMg==", - "license": "MIT", - "dependencies": { - "atomic-sleep": "^1.0.0", - "fast-redact": "^3.1.1", - "on-exit-leak-free": "^2.1.0", - "pino-abstract-transport": "^2.0.0", - "pino-std-serializers": "^7.0.0", - "process-warning": "^4.0.0", - "quick-format-unescaped": "^4.0.3", - "real-require": "^0.2.0", - "safe-stable-stringify": "^2.3.1", - "sonic-boom": "^4.0.1", - "thread-stream": "^3.0.0" - }, - "bin": { - "pino": "bin.js" - } - }, - "node_modules/pino-abstract-transport": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/pino-abstract-transport/-/pino-abstract-transport-2.0.0.tgz", - "integrity": "sha512-F63x5tizV6WCh4R6RHyi2Ml+M70DNRXt/+HANowMflpgGFMAym/VKm6G7ZOQRjqN7XbGxK1Lg9t6ZrtzOaivMw==", - "license": "MIT", - "dependencies": { - "split2": "^4.0.0" - } - }, - "node_modules/pino-pretty": { - "version": "13.0.0", - "resolved": "https://registry.npmjs.org/pino-pretty/-/pino-pretty-13.0.0.tgz", - "integrity": "sha512-cQBBIVG3YajgoUjo1FdKVRX6t9XPxwB9lcNJVD5GCnNM4Y6T12YYx8c6zEejxQsU0wrg9TwmDulcE9LR7qcJqA==", - "license": "MIT", - "dependencies": { - "colorette": "^2.0.7", - "dateformat": "^4.6.3", - "fast-copy": "^3.0.2", - "fast-safe-stringify": "^2.1.1", - "help-me": "^5.0.0", - "joycon": "^3.1.1", - "minimist": "^1.2.6", - "on-exit-leak-free": "^2.1.0", - "pino-abstract-transport": "^2.0.0", - "pump": "^3.0.0", - "secure-json-parse": "^2.4.0", - "sonic-boom": "^4.0.1", - "strip-json-comments": "^3.1.1" - }, - "bin": { - "pino-pretty": "bin.js" - } - }, - "node_modules/pino-std-serializers": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/pino-std-serializers/-/pino-std-serializers-7.0.0.tgz", - "integrity": "sha512-e906FRY0+tV27iq4juKzSYPbUj2do2X2JX4EzSca1631EB2QJQUqGbDuERal7LCtOpxl6x3+nvo9NPZcmjkiFA==", - "license": "MIT" - }, - "node_modules/pkce-challenge": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/pkce-challenge/-/pkce-challenge-5.0.0.tgz", - "integrity": "sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==", - "license": "MIT", - "engines": { - "node": ">=16.20.0" - } - }, - "node_modules/playwright": { - "version": "1.51.0", - "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.51.0.tgz", - "integrity": "sha512-442pTfGM0xxfCYxuBa/Pu6B2OqxqqaYq39JS8QDMGThUvIOCd6s0ANDog3uwA0cHavVlnTQzGCN7Id2YekDSXA==", - "license": "Apache-2.0", - "dependencies": { - "playwright-core": "1.51.0" - }, - "bin": { - "playwright": "cli.js" - }, - "engines": { - "node": ">=18" - }, - "optionalDependencies": { - "fsevents": "2.3.2" - } - }, - "node_modules/playwright-core": { - "version": "1.53.2", - "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.53.2.tgz", - "integrity": "sha512-ox/OytMy+2w1jcYEYlOo1Hhp8hZkLCximMTUTMBXjGUA1KoFfiSZ+DU+3a739jsPY0yoKH2TFy9S2fsJas8yAw==", - "license": "Apache-2.0", - "bin": { - "playwright-core": "cli.js" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/playwright/node_modules/playwright-core": { - "version": "1.51.0", - "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.51.0.tgz", - "integrity": "sha512-x47yPE3Zwhlil7wlNU/iktF7t2r/URR3VLbH6EknJd/04Qc/PSJ0EY3CMXipmglLG+zyRxW6HNo2EGbKLHPWMg==", - "license": "Apache-2.0", - "bin": { - "playwright-core": "cli.js" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/possible-typed-array-names": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.1.0.tgz", - "integrity": "sha512-/+5VFTchJDoVj3bhoqi6UeymcD00DAwb1nJwamzPvHEszJ4FpF6SNNbUbOS8yI56qHzdV8eK0qEfOSiodkTdxg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/prelude-ls": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", - "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/prettier": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.6.2.tgz", - "integrity": "sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ==", - "dev": true, - "license": "MIT", - "bin": { - "prettier": "bin/prettier.cjs" - }, - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/prettier/prettier?sponsor=1" - } - }, - "node_modules/process-warning": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/process-warning/-/process-warning-4.0.1.tgz", - "integrity": "sha512-3c2LzQ3rY9d0hc1emcsHhfT9Jwz0cChib/QN89oME2R451w5fy3f0afAhERFZAwrbDU43wk12d0ORBpDVME50Q==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/fastify" - }, - { - "type": "opencollective", - "url": "https://opencollective.com/fastify" - } - ], - "license": "MIT" - }, - "node_modules/prop-types": { - "version": "15.8.1", - "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", - "integrity": "sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==", - "dev": true, - "license": "MIT", - "dependencies": { - "loose-envify": "^1.4.0", - "object-assign": "^4.1.1", - "react-is": "^16.13.1" - } - }, - "node_modules/proxy-addr": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", - "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", - "license": "MIT", - "dependencies": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/pump": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.2.tgz", - "integrity": "sha512-tUPXtzlGM8FE3P0ZL6DVs/3P58k9nk8/jZeQCurTJylQA8qFYzHFfhBJkuqyE0FifOsQ0uKWekiZ5g8wtr28cw==", - "license": "MIT", - "dependencies": { - "end-of-stream": "^1.1.0", - "once": "^1.3.1" - } - }, - "node_modules/punycode": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", - "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", - "license": "MIT", - "engines": { - "node": ">=6" - } - }, - "node_modules/qs": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.13.0.tgz", - "integrity": "sha512-+38qI9SOr8tfZ4QmJNplMUxqjbe7LKvvZgWdExBOmd+egZTtjLB67Gu0HRX3u/XOq7UU2Nx6nsjvS16Z9uwfpg==", - "license": "BSD-3-Clause", - "dependencies": { - "side-channel": "^1.0.6" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/queue-microtask": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", - "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", - "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/quick-format-unescaped": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/quick-format-unescaped/-/quick-format-unescaped-4.0.4.tgz", - "integrity": "sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==", - "license": "MIT" - }, - "node_modules/range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/raw-body": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-3.0.0.tgz", - "integrity": "sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==", - "license": "MIT", - "dependencies": { - "bytes": "3.1.2", - "http-errors": "2.0.0", - "iconv-lite": "0.6.3", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/raw-body/node_modules/iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/react": { - "version": "19.1.0", - "resolved": "https://registry.npmjs.org/react/-/react-19.1.0.tgz", - "integrity": "sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==", - "license": "MIT", - "peer": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/react-is": { - "version": "16.13.1", - "resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz", - "integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==", - "dev": true, - "license": "MIT" - }, - "node_modules/real-require": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/real-require/-/real-require-0.2.0.tgz", - "integrity": "sha512-57frrGM/OCTLqLOAh0mhVA9VBMHd+9U7Zb2THMGdBUoZVOtGbJzjxsYGDJ3A9AYYCP4hn6y1TVbaOfzWtm5GFg==", - "license": "MIT", - "engines": { - "node": ">= 12.13.0" - } - }, - "node_modules/rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==", - "dev": true, - "dependencies": { - "resolve": "^1.1.6" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/reflect.getprototypeof": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/reflect.getprototypeof/-/reflect.getprototypeof-1.0.10.tgz", - "integrity": "sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.9", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.0.0", - "get-intrinsic": "^1.2.7", - "get-proto": "^1.0.1", - "which-builtin-type": "^1.2.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/regexp.prototype.flags": { - "version": "1.5.4", - "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.5.4.tgz", - "integrity": "sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "define-properties": "^1.2.1", - "es-errors": "^1.3.0", - "get-proto": "^1.0.1", - "gopd": "^1.2.0", - "set-function-name": "^2.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/resolve": { - "version": "1.22.10", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.10.tgz", - "integrity": "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-core-module": "^2.16.0", - "path-parse": "^1.0.7", - "supports-preserve-symlinks-flag": "^1.0.0" - }, - "bin": { - "resolve": "bin/resolve" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/resolve-from": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", - "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=4" - } - }, - "node_modules/restore-cursor": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz", - "integrity": "sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==", - "dev": true, - "license": "MIT", - "dependencies": { - "onetime": "^7.0.0", - "signal-exit": "^4.1.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/reusify": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.1.0.tgz", - "integrity": "sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==", - "dev": true, - "license": "MIT", - "engines": { - "iojs": ">=1.0.0", - "node": ">=0.10.0" - } - }, - "node_modules/rfdc": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.4.1.tgz", - "integrity": "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==", - "dev": true, - "license": "MIT" - }, - "node_modules/router": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/router/-/router-2.1.0.tgz", - "integrity": "sha512-/m/NSLxeYEgWNtyC+WtNHCF7jbGxOibVWKnn+1Psff4dJGOfoXP+MuC/f2CwSmyiHdOIzYnYFp4W6GxWfekaLA==", - "license": "MIT", - "dependencies": { - "is-promise": "^4.0.0", - "parseurl": "^1.3.3", - "path-to-regexp": "^8.0.0" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/run-parallel": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", - "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", - "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT", - "dependencies": { - "queue-microtask": "^1.2.2" - } - }, - "node_modules/safe-array-concat": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.1.3.tgz", - "integrity": "sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.2", - "get-intrinsic": "^1.2.6", - "has-symbols": "^1.1.0", - "isarray": "^2.0.5" - }, - "engines": { - "node": ">=0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, - "node_modules/safe-push-apply": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/safe-push-apply/-/safe-push-apply-1.0.0.tgz", - "integrity": "sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA==", - "dev": true, - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "isarray": "^2.0.5" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/safe-regex-test": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.1.0.tgz", - "integrity": "sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "is-regex": "^1.2.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/safe-stable-stringify": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/safe-stable-stringify/-/safe-stable-stringify-2.5.0.tgz", - "integrity": "sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==", - "license": "MIT", - "engines": { - "node": ">=10" - } - }, - "node_modules/safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "license": "MIT" - }, - "node_modules/secure-json-parse": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/secure-json-parse/-/secure-json-parse-2.7.0.tgz", - "integrity": "sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==", - "license": "BSD-3-Clause" - }, - "node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "dev": true, - "license": "ISC", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/send": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/send/-/send-1.1.0.tgz", - "integrity": "sha512-v67WcEouB5GxbTWL/4NeToqcZiAWEq90N888fczVArY8A79J0L4FD7vj5hm3eUMua5EpoQ59wa/oovY6TLvRUA==", - "license": "MIT", - "dependencies": { - "debug": "^4.3.5", - "destroy": "^1.2.0", - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "etag": "^1.8.1", - "fresh": "^0.5.2", - "http-errors": "^2.0.0", - "mime-types": "^2.1.35", - "ms": "^2.1.3", - "on-finished": "^2.4.1", - "range-parser": "^1.2.1", - "statuses": "^2.0.1" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/send/node_modules/fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/send/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/send/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/send/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" - }, - "node_modules/serve-static": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-2.1.0.tgz", - "integrity": "sha512-A3We5UfEjG8Z7VkDv6uItWw6HY2bBSBJT1KtVESn6EOoOr2jAxNhxWCLY3jDE2WcuHXByWju74ck3ZgLwL8xmA==", - "license": "MIT", - "dependencies": { - "encodeurl": "^2.0.0", - "escape-html": "^1.0.3", - "parseurl": "^1.3.3", - "send": "^1.0.0" - }, - "engines": { - "node": ">= 18" - } - }, - "node_modules/set-cookie-parser": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/set-cookie-parser/-/set-cookie-parser-2.7.1.tgz", - "integrity": "sha512-IOc8uWeOZgnb3ptbCURJWNjWUPcO3ZnTTdzsurqERrP6nPyv+paC55vJM0LpOlT2ne+Ix+9+CRG1MNLlyZ4GjQ==", - "license": "MIT" - }, - "node_modules/set-function-length": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", - "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", - "dev": true, - "license": "MIT", - "dependencies": { - "define-data-property": "^1.1.4", - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.4", - "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/set-function-name": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/set-function-name/-/set-function-name-2.0.2.tgz", - "integrity": "sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "define-data-property": "^1.1.4", - "es-errors": "^1.3.0", - "functions-have-names": "^1.2.3", - "has-property-descriptors": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/set-proto": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/set-proto/-/set-proto-1.0.0.tgz", - "integrity": "sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw==", - "dev": true, - "license": "MIT", - "dependencies": { - "dunder-proto": "^1.0.1", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", - "license": "ISC" - }, - "node_modules/shebang-command": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", - "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", - "license": "MIT", - "dependencies": { - "shebang-regex": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/shebang-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", - "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/shelljs": { - "version": "0.8.5", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.5.tgz", - "integrity": "sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==", - "dev": true, - "license": "BSD-3-Clause", - "dependencies": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - }, - "bin": { - "shjs": "bin/shjs" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/shx": { - "version": "0.3.4", - "resolved": "https://registry.npmjs.org/shx/-/shx-0.3.4.tgz", - "integrity": "sha512-N6A9MLVqjxZYcVn8hLmtneQWIJtp8IKzMP4eMnx+nqkvXoqinUPCbUFLp2UcWTEIUONhlk0ewxr/jaVGlc+J+g==", - "dev": true, - "license": "MIT", - "dependencies": { - "minimist": "^1.2.3", - "shelljs": "^0.8.5" - }, - "bin": { - "shx": "lib/cli.js" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/side-channel": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.1.0.tgz", - "integrity": "sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "object-inspect": "^1.13.3", - "side-channel-list": "^1.0.0", - "side-channel-map": "^1.0.1", - "side-channel-weakmap": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/side-channel-list": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.0.tgz", - "integrity": "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "object-inspect": "^1.13.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/side-channel-map": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/side-channel-map/-/side-channel-map-1.0.1.tgz", - "integrity": "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==", - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.5", - "object-inspect": "^1.13.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/side-channel-weakmap": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz", - "integrity": "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==", - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.5", - "object-inspect": "^1.13.3", - "side-channel-map": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/signal-exit": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", - "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", - "dev": true, - "license": "ISC", - "engines": { - "node": ">=14" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/slice-ansi": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-5.0.0.tgz", - "integrity": "sha512-FC+lgizVPfie0kkhqUScwRu1O/lF6NOgJmlCgK+/LYxDCTk8sGelYaHDhFcDN+Sn3Cv+3VSa4Byeo+IMCzpMgQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^6.0.0", - "is-fullwidth-code-point": "^4.0.0" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/slice-ansi?sponsor=1" - } - }, - "node_modules/sonic-boom": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/sonic-boom/-/sonic-boom-4.2.0.tgz", - "integrity": "sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==", - "license": "MIT", - "dependencies": { - "atomic-sleep": "^1.0.0" - } - }, - "node_modules/split2": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", - "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", - "license": "ISC", - "engines": { - "node": ">= 10.x" - } - }, - "node_modules/statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/stop-iteration-iterator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/stop-iteration-iterator/-/stop-iteration-iterator-1.1.0.tgz", - "integrity": "sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "internal-slot": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/string-argv": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz", - "integrity": "sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.6.19" - } - }, - "node_modules/string-width": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-7.2.0.tgz", - "integrity": "sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "emoji-regex": "^10.3.0", - "get-east-asian-width": "^1.0.0", - "strip-ansi": "^7.1.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/string.prototype.matchall": { - "version": "4.0.12", - "resolved": "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.12.tgz", - "integrity": "sha512-6CC9uyBL+/48dYizRf7H7VAYCMCNTBeM78x/VTUe9bFEaxBepPJDa1Ow99LqI/1yF7kuy7Q3cQsYMrcjGUcskA==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.3", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.6", - "es-errors": "^1.3.0", - "es-object-atoms": "^1.0.0", - "get-intrinsic": "^1.2.6", - "gopd": "^1.2.0", - "has-symbols": "^1.1.0", - "internal-slot": "^1.1.0", - "regexp.prototype.flags": "^1.5.3", - "set-function-name": "^2.0.2", - "side-channel": "^1.1.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/string.prototype.repeat": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/string.prototype.repeat/-/string.prototype.repeat-1.0.0.tgz", - "integrity": "sha512-0u/TldDbKD8bFCQ/4f5+mNRrXwZ8hg2w7ZR8wa16e8z9XpePWl3eGEcUD0OXpEH/VJH/2G3gjUtR3ZOiBe2S/w==", - "dev": true, - "license": "MIT", - "dependencies": { - "define-properties": "^1.1.3", - "es-abstract": "^1.17.5" - } - }, - "node_modules/string.prototype.trim": { - "version": "1.2.10", - "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.2.10.tgz", - "integrity": "sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.2", - "define-data-property": "^1.1.4", - "define-properties": "^1.2.1", - "es-abstract": "^1.23.5", - "es-object-atoms": "^1.0.0", - "has-property-descriptors": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/string.prototype.trimend": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.9.tgz", - "integrity": "sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "call-bound": "^1.0.2", - "define-properties": "^1.2.1", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/string.prototype.trimstart": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.8.tgz", - "integrity": "sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.7", - "define-properties": "^1.2.1", - "es-object-atoms": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/strip-ansi": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", - "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-regex": "^6.0.1" - }, - "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/chalk/strip-ansi?sponsor=1" - } - }, - "node_modules/strip-json-comments": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", - "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", - "license": "MIT", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dev": true, - "license": "MIT", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/supports-preserve-symlinks-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", - "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/swr": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/swr/-/swr-2.3.3.tgz", - "integrity": "sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==", - "license": "MIT", - "dependencies": { - "dequal": "^2.0.3", - "use-sync-external-store": "^1.4.0" - }, - "peerDependencies": { - "react": "^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" - } - }, - "node_modules/thread-stream": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/thread-stream/-/thread-stream-3.1.0.tgz", - "integrity": "sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A==", - "license": "MIT", - "dependencies": { - "real-require": "^0.2.0" - } - }, - "node_modules/throttleit": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/throttleit/-/throttleit-2.1.0.tgz", - "integrity": "sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==", - "license": "MIT", - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/tldts": { - "version": "6.1.86", - "resolved": "https://registry.npmjs.org/tldts/-/tldts-6.1.86.tgz", - "integrity": "sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==", - "license": "MIT", - "dependencies": { - "tldts-core": "^6.1.86" - }, - "bin": { - "tldts": "bin/cli.js" - } - }, - "node_modules/tldts-core": { - "version": "6.1.86", - "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-6.1.86.tgz", - "integrity": "sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==", - "license": "MIT" - }, - "node_modules/to-regex-range": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", - "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-number": "^7.0.0" - }, - "engines": { - "node": ">=8.0" - } - }, - "node_modules/toidentifier": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", - "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", - "license": "MIT", - "engines": { - "node": ">=0.6" - } - }, - "node_modules/tough-cookie": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-5.1.2.tgz", - "integrity": "sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==", - "license": "BSD-3-Clause", - "dependencies": { - "tldts": "^6.1.32" - }, - "engines": { - "node": ">=16" - } - }, - "node_modules/tr46": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", - "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", - "license": "MIT" - }, - "node_modules/ts-api-utils": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-2.1.0.tgz", - "integrity": "sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=18.12" - }, - "peerDependencies": { - "typescript": ">=4.8.4" - } - }, - "node_modules/type-check": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", - "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", - "dev": true, - "license": "MIT", - "dependencies": { - "prelude-ls": "^1.2.1" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/type-is": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-2.0.0.tgz", - "integrity": "sha512-gd0sGezQYCbWSbkZr75mln4YBidWUN60+devscpLF5mtRDUpiaTvKpBNrdaCvel1NdR2k6vclXybU5fBd2i+nw==", - "license": "MIT", - "dependencies": { - "content-type": "^1.0.5", - "media-typer": "^1.1.0", - "mime-types": "^3.0.0" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/typed-array-buffer": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.3.tgz", - "integrity": "sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "es-errors": "^1.3.0", - "is-typed-array": "^1.1.14" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/typed-array-byte-length": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/typed-array-byte-length/-/typed-array-byte-length-1.0.3.tgz", - "integrity": "sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.8", - "for-each": "^0.3.3", - "gopd": "^1.2.0", - "has-proto": "^1.2.0", - "is-typed-array": "^1.1.14" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/typed-array-byte-offset": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/typed-array-byte-offset/-/typed-array-byte-offset-1.0.4.tgz", - "integrity": "sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ==", - "dev": true, - "license": "MIT", - "dependencies": { - "available-typed-arrays": "^1.0.7", - "call-bind": "^1.0.8", - "for-each": "^0.3.3", - "gopd": "^1.2.0", - "has-proto": "^1.2.0", - "is-typed-array": "^1.1.15", - "reflect.getprototypeof": "^1.0.9" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/typed-array-length": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.7.tgz", - "integrity": "sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bind": "^1.0.7", - "for-each": "^0.3.3", - "gopd": "^1.0.1", - "is-typed-array": "^1.1.13", - "possible-typed-array-names": "^1.0.0", - "reflect.getprototypeof": "^1.0.6" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/typescript": { - "version": "5.8.2", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.8.2.tgz", - "integrity": "sha512-aJn6wq13/afZp/jT9QZmwEjDqqvSGp1VT5GVg+f/t6/oVyrgXM6BY1h9BRh/O5p3PlUPAe+WuiEZOmb/49RqoQ==", - "dev": true, - "license": "Apache-2.0", - "bin": { - "tsc": "bin/tsc", - "tsserver": "bin/tsserver" - }, - "engines": { - "node": ">=14.17" - } - }, - "node_modules/typescript-eslint": { - "version": "8.35.1", - "resolved": "https://registry.npmjs.org/typescript-eslint/-/typescript-eslint-8.35.1.tgz", - "integrity": "sha512-xslJjFzhOmHYQzSB/QTeASAHbjmxOGEP6Coh93TXmUBFQoJ1VU35UHIDmG06Jd6taf3wqqC1ntBnCMeymy5Ovw==", - "dev": true, - "license": "MIT", - "dependencies": { - "@typescript-eslint/eslint-plugin": "8.35.1", - "@typescript-eslint/parser": "8.35.1", - "@typescript-eslint/utils": "8.35.1" - }, - "engines": { - "node": "^18.18.0 || ^20.9.0 || >=21.1.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - }, - "peerDependencies": { - "eslint": "^8.57.0 || ^9.0.0", - "typescript": ">=4.8.4 <5.9.0" - } - }, - "node_modules/unbox-primitive": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.1.0.tgz", - "integrity": "sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.3", - "has-bigints": "^1.0.2", - "has-symbols": "^1.1.0", - "which-boxed-primitive": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/undici-types": { - "version": "5.26.5", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", - "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==", - "license": "MIT" - }, - "node_modules/unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/uri-js": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", - "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", - "license": "BSD-2-Clause", - "dependencies": { - "punycode": "^2.1.0" - } - }, - "node_modules/use-sync-external-store": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.5.0.tgz", - "integrity": "sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==", - "license": "MIT", - "peerDependencies": { - "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" - } - }, - "node_modules/utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", - "license": "MIT", - "engines": { - "node": ">= 0.4.0" - } - }, - "node_modules/uuid": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", - "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/web-streams-polyfill": { - "version": "4.0.0-beta.3", - "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-4.0.0-beta.3.tgz", - "integrity": "sha512-QW95TCTaHmsYfHDybGMwO5IJIM93I/6vTRk+daHTWFPhwh+C8Cg7j7XyKrwrj8Ib6vYXe0ocYNrmzY4xAAN6ug==", - "license": "MIT", - "engines": { - "node": ">= 14" - } - }, - "node_modules/webidl-conversions": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", - "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==", - "license": "BSD-2-Clause" - }, - "node_modules/whatwg-url": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", - "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", - "license": "MIT", - "dependencies": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" - } - }, - "node_modules/which": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", - "license": "ISC", - "dependencies": { - "isexe": "^2.0.0" - }, - "bin": { - "node-which": "bin/node-which" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/which-boxed-primitive": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.1.1.tgz", - "integrity": "sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-bigint": "^1.1.0", - "is-boolean-object": "^1.2.1", - "is-number-object": "^1.1.1", - "is-string": "^1.1.1", - "is-symbol": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/which-builtin-type": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/which-builtin-type/-/which-builtin-type-1.2.1.tgz", - "integrity": "sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "call-bound": "^1.0.2", - "function.prototype.name": "^1.1.6", - "has-tostringtag": "^1.0.2", - "is-async-function": "^2.0.0", - "is-date-object": "^1.1.0", - "is-finalizationregistry": "^1.1.0", - "is-generator-function": "^1.0.10", - "is-regex": "^1.2.1", - "is-weakref": "^1.0.2", - "isarray": "^2.0.5", - "which-boxed-primitive": "^1.1.0", - "which-collection": "^1.0.2", - "which-typed-array": "^1.1.16" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/which-collection": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/which-collection/-/which-collection-1.0.2.tgz", - "integrity": "sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==", - "dev": true, - "license": "MIT", - "dependencies": { - "is-map": "^2.0.3", - "is-set": "^2.0.3", - "is-weakmap": "^2.0.2", - "is-weakset": "^2.0.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/which-typed-array": { - "version": "1.1.19", - "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.19.tgz", - "integrity": "sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw==", - "dev": true, - "license": "MIT", - "dependencies": { - "available-typed-arrays": "^1.0.7", - "call-bind": "^1.0.8", - "call-bound": "^1.0.4", - "for-each": "^0.3.5", - "get-proto": "^1.0.1", - "gopd": "^1.2.0", - "has-tostringtag": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/word-wrap": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.5.tgz", - "integrity": "sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/wrap-ansi": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-9.0.0.tgz", - "integrity": "sha512-G8ura3S+3Z2G+mkgNRq8dqaFZAuxfsxpBB8OCTGRTCtp+l/v9nbFNmCUP1BZMts3G1142MsZfn6eeUKrr4PD1Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "ansi-styles": "^6.2.1", - "string-width": "^7.0.0", - "strip-ansi": "^7.1.0" - }, - "engines": { - "node": ">=18" - }, - "funding": { - "url": "https://github.com/chalk/wrap-ansi?sponsor=1" - } - }, - "node_modules/wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", - "license": "ISC" - }, - "node_modules/ws": { - "version": "8.18.1", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.1.tgz", - "integrity": "sha512-RKW2aJZMXeMxVpnZ6bck+RswznaxmzdULiBr6KY7XkTnW8uvt0iT9H5DkHUChXrc+uurzwa0rVI16n/Xzjdz1w==", - "license": "MIT", - "engines": { - "node": ">=10.0.0" - }, - "peerDependencies": { - "bufferutil": "^4.0.1", - "utf-8-validate": ">=5.0.2" - }, - "peerDependenciesMeta": { - "bufferutil": { - "optional": true - }, - "utf-8-validate": { - "optional": true - } - } - }, - "node_modules/yaml": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.8.0.tgz", - "integrity": "sha512-4lLa/EcQCB0cJkyts+FpIRx5G/llPxfP6VQU5KByHEhLxY3IJCH0f0Hy1MHI8sClTvsIb8qwRJ6R/ZdlDJ/leQ==", - "dev": true, - "license": "ISC", - "bin": { - "yaml": "bin.mjs" - }, - "engines": { - "node": ">= 14.6" - } - }, - "node_modules/yocto-queue": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", - "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/zod": { - "version": "3.25.67", - "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.67.tgz", - "integrity": "sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==", - "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/colinhacks" - } - }, - "node_modules/zod-to-json-schema": { - "version": "3.24.3", - "resolved": "https://registry.npmjs.org/zod-to-json-schema/-/zod-to-json-schema-3.24.3.tgz", - "integrity": "sha512-HIAfWdYIt1sssHfYZFCXp4rU1w2r8hVVXYIlmoa0r0gABLs5di3RCqPU5DDROogVz1pAdYBaz7HK5n9pSUNs3A==", - "license": "ISC", - "peerDependencies": { - "zod": "^3.24.1" - } - } - } -} diff --git a/package.json b/package.json index 722d272..49df217 100644 --- a/package.json +++ b/package.json @@ -26,7 +26,7 @@ "prettier:check": "prettier --check .", "prettier:fix": "prettier --write .", "clean": "rm -rf dist", - "npm-publish": "pnpm clean && pnpm build && npm publish" + "publish": "pnpm clean && pnpm build && npm publish" }, "lint-staged": { "*.{js,jsx,ts,tsx,json,css,scss,md}": [ diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml new file mode 100644 index 0000000..6bdb532 --- /dev/null +++ b/pnpm-workspace.yaml @@ -0,0 +1,2 @@ +packages: + - '.' \ No newline at end of file diff --git a/src/config.ts b/src/config.ts index 65b0baa..42a1e45 100644 --- a/src/config.ts +++ b/src/config.ts @@ -1,7 +1,3 @@ -import os from "os"; -import fs from "fs"; -import path from "path"; -import { sanitizeForFilePath } from "./utils.js"; import type { Cookie } from "playwright-core"; import type { Config } from "../config.js"; import { AvailableModelSchema } from "@browserbasehq/stagehand"; @@ -97,17 +93,6 @@ export async function configFromCLIOptions( }; } -// Create an output file path within the configured output directory -export async function outputFile( - config: Config, - name: string, -): Promise { - const outputDir = os.tmpdir(); - await fs.promises.mkdir(outputDir, { recursive: true }); - const sanitizedName = sanitizeForFilePath(name); - return path.join(outputDir, sanitizedName); -} - // Helper function to merge config objects, excluding undefined values function pickDefined(obj: T | undefined): Partial { if (!obj) return {}; diff --git a/src/mcp/prompts.ts b/src/mcp/prompts.ts index f636c72..893c493 100644 --- a/src/mcp/prompts.ts +++ b/src/mcp/prompts.ts @@ -18,11 +18,6 @@ export const PROMPTS = [ "Guidance on when and how to use multi-session browser automation", arguments: [], }, - { - name: "click_search_button", - description: "A prompt template for clicking on a search button", - arguments: [], // No arguments required for this specific prompt - }, ]; /** @@ -125,21 +120,5 @@ SINGLE VS MULTI-SESSION: }; } - if (name === "click_search_button") { - return { - description: - "This prompt provides instructions for clicking on a search button", - messages: [ - { - role: "user", - content: { - type: "text", - text: "Please click on the search button", - }, - }, - ], - }; - } - throw new Error(`Invalid prompt name: ${name}`); } diff --git a/src/stagehandStore.ts b/src/stagehandStore.ts index 40645a2..0224ba0 100644 --- a/src/stagehandStore.ts +++ b/src/stagehandStore.ts @@ -104,10 +104,18 @@ export const create = async ( ); // Set up disconnect handler - browser.on("disconnected", () => { + const disconnectHandler = () => { process.stderr.write(`[StagehandStore] Session disconnected: ${id}\n`); store.delete(id); - }); + }; + + browser.on("disconnected", disconnectHandler); + + // Store the handler for cleanup + session.metadata = { + ...session.metadata, + disconnectHandler, + }; return session; }; @@ -141,6 +149,10 @@ export const remove = async (id: string): Promise => { process.stderr.write(`[StagehandStore] Removing session: ${id}\n`); try { + if (session.metadata?.disconnectHandler) { + session.browser.off("disconnected", session.metadata.disconnectHandler); + } + await session.stagehand.close(); process.stderr.write(`[StagehandStore] Session closed: ${id}\n`); } catch (error) { @@ -149,9 +161,9 @@ export const remove = async (id: string): Promise => { error instanceof Error ? error.message : String(error) }\n`, ); + } finally { + store.delete(id); } - - store.delete(id); }; /** diff --git a/src/tools/session.ts b/src/tools/session.ts index 691b40f..cc0069f 100644 --- a/src/tools/session.ts +++ b/src/tools/session.ts @@ -64,7 +64,13 @@ async function handleCreateSession( ); } - if (!session || !session.browser || !session.page || !session.sessionId) { + if ( + !session || + !session.browser || + !session.page || + !session.sessionId || + !session.stagehand + ) { throw new Error( `SessionManager failed to return a valid session object with actualSessionId for ID: ${targetSessionId}`, ); @@ -76,7 +82,7 @@ async function handleCreateSession( ); process.stderr.write( - `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.stagehand.browserbaseSessionID}`, + `[SessionManager] Browserbase Live Debugger URL: https://www.browserbase.com/sessions/${session.sessionId}`, ); return { @@ -192,7 +198,7 @@ async function handleCloseSession(context: Context): Promise { if (stagehandClosedSuccessfully) { let successMessage = `Browserbase session (${previousSessionId || "default"}) closed successfully via Stagehand. Context reset to default.`; if (browserbaseSessionId && previousSessionId !== defaultSessionId) { - successMessage += ` View replay at https://browserbase.com/sessions/${browserbaseSessionId}`; + successMessage += ` View replay at https://www.browserbase.com/sessions/${browserbaseSessionId}`; } return { content: [{ type: "text", text: successMessage }] }; } diff --git a/src/utils.ts b/src/utils.ts deleted file mode 100644 index be464d4..0000000 --- a/src/utils.ts +++ /dev/null @@ -1,28 +0,0 @@ -/** - * Sanitizes a message to ensure it's properly formatted JSON - * @param message The message to sanitize - * @returns A sanitized JSON string - */ -export function sanitizeMessage(message: unknown): string { - try { - // Ensure the message is properly stringified JSON - if (typeof message === "string") { - JSON.parse(message); // Validate JSON structure - return message; - } - return JSON.stringify(message); - } catch { - return JSON.stringify({ - jsonrpc: "2.0", - error: { - code: -32700, - message: "Parse error", - }, - id: null, - }); - } -} - -export function sanitizeForFilePath(s: string) { - return s.replace(/[^a-zA-Z0-9_.-]/g, "_"); // More robust sanitization -} diff --git a/tsconfig.json b/tsconfig.json index 6c2b6de..7177886 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -12,6 +12,6 @@ "rootDir": "src", "noErrorTruncation": false }, - "include": ["src/**/*.ts", "src/types/types.ts"], + "include": ["src/**/*.ts"], "exclude": ["node_modules"] } From 73b205d52f60fbb0fa6b8253414cfbdb4c8bc69a Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 12:20:33 -0700 Subject: [PATCH 22/32] pnpm fix ci, screenshot unique, transport validation, formatting --- .github/workflows/ci.yml | 8 ++++---- .github/workflows/publish.yml | 1 - .npmrc | 2 +- package.json | 2 +- pnpm-lock.yaml | 16 ++++++++-------- src/tools/screenshot.ts | 3 ++- src/transport.ts | 5 +++++ 7 files changed, 21 insertions(+), 16 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 1ab78b1..20f6f67 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -11,15 +11,15 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + - name: Install pnpm + uses: pnpm/action-setup@v4 + with: + version: 8 - name: Use Node.js 22 uses: actions/setup-node@v4 with: node-version: '22' cache: 'pnpm' - - name: Install pnpm - uses: pnpm/action-setup@v4 - with: - version: 8 - name: Install dependencies run: pnpm install --frozen-lockfile - run: pnpm run build diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index e6586f9..9ac15ea 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -19,7 +19,6 @@ jobs: with: version: 8 - run: pnpm install --frozen-lockfile - - run: pnpm run build - run: pnpm publish --provenance env: NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} \ No newline at end of file diff --git a/.npmrc b/.npmrc index 0a6ad7b..ca2770b 100644 --- a/.npmrc +++ b/.npmrc @@ -1,4 +1,4 @@ # Use pnpm for package management engine-strict=true auto-install-peers=true -strict-peer-dependencies=false \ No newline at end of file +strict-peer-dependencies=false diff --git a/package.json b/package.json index 49df217..ecbf7f2 100644 --- a/package.json +++ b/package.json @@ -26,7 +26,7 @@ "prettier:check": "prettier --check .", "prettier:fix": "prettier --write .", "clean": "rm -rf dist", - "publish": "pnpm clean && pnpm build && npm publish" + "prepublishOnly": "pnpm clean && pnpm build" }, "lint-staged": { "*.{js,jsx,ts,tsx,json,css,scss,md}": [ diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index bc46436..888ac5f 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -10,7 +10,7 @@ importers: dependencies: '@browserbasehq/stagehand': specifier: ^2.4.0 - version: 2.4.0(deepmerge@4.3.1)(dotenv@17.0.0)(react@19.1.0)(zod@3.25.67) + version: 2.4.0(deepmerge@4.3.1)(dotenv@16.6.1)(react@19.1.0)(zod@3.25.67) '@modelcontextprotocol/sdk': specifier: ^1.13.1 version: 1.13.1 @@ -21,8 +21,8 @@ importers: specifier: ^14.0.0 version: 14.0.0 dotenv: - specifier: ^17.0.0 - version: 17.0.0 + specifier: ^16.4.6 + version: 16.6.1 playwright-core: specifier: ^1.53.2 version: 1.53.2 @@ -608,8 +608,8 @@ packages: resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} engines: {node: '>=0.10.0'} - dotenv@17.0.0: - resolution: {integrity: sha512-A0BJ5lrpJVSfnMMXjmeO0xUnoxqsBHWCoqqTnGwGYVdnctqXXUEhJOO7LxmgxJon9tEZFGpe0xPRX0h2v3AANQ==} + dotenv@16.6.1: + resolution: {integrity: sha512-uBq4egWHTcTt33a72vpSG0z3HnPuIl6NqYcTrKEg2azoEyl2hpW0zqlxysq2pK9HlDIHyHyakeYaYnSAwd8bow==} engines: {node: '>=12'} dunder-proto@1.0.1: @@ -2022,7 +2022,7 @@ snapshots: transitivePeerDependencies: - encoding - '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@17.0.0)(react@19.1.0)(zod@3.25.67)': + '@browserbasehq/stagehand@2.4.0(deepmerge@4.3.1)(dotenv@16.6.1)(react@19.1.0)(zod@3.25.67)': dependencies: '@anthropic-ai/sdk': 0.39.0 '@browserbasehq/sdk': 2.6.0 @@ -2030,7 +2030,7 @@ snapshots: ai: 4.3.16(react@19.1.0)(zod@3.25.67) deepmerge: 4.3.1 devtools-protocol: 0.0.1464554 - dotenv: 17.0.0 + dotenv: 16.6.1 fetch-cookie: 3.1.0 openai: 4.104.0(ws@8.18.2)(zod@3.25.67) pino: 9.7.0 @@ -2555,7 +2555,7 @@ snapshots: dependencies: esutils: 2.0.3 - dotenv@17.0.0: {} + dotenv@16.6.1: {} dunder-proto@1.0.1: dependencies: diff --git a/src/tools/screenshot.ts b/src/tools/screenshot.ts index 95d3d54..a680799 100644 --- a/src/tools/screenshot.ts +++ b/src/tools/screenshot.ts @@ -38,7 +38,8 @@ async function handleScreenshot( ? `screenshot-${params.name}-${new Date() .toISOString() .replace(/:/g, "-")}` - : `screenshot-${new Date().toISOString().replace(/:/g, "-")}`; + : `screenshot-${new Date().toISOString().replace(/:/g, "-")}` + + context.config.browserbaseProjectId; screenshots.set(name, screenshotBase64); // Notify the client that the resources changed diff --git a/src/transport.ts b/src/transport.ts index 0a266ad..abef1a0 100644 --- a/src/transport.ts +++ b/src/transport.ts @@ -94,6 +94,11 @@ export function startHttpTransport( const sseSessions = new Map(); const streamableSessions = new Map(); const httpServer = http.createServer(async (req, res) => { + if (!req.url) { + res.statusCode = 400; + res.end("Bad request: missing URL"); + return; + } const url = new URL(`http://localhost${req.url}`); if (url.pathname.startsWith("/mcp")) await handleStreamable(req, res, serverList, streamableSessions); From 8c485a3d6fa5137cbb0e8a1a09f8f83e80c0d5da Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 13:32:59 -0700 Subject: [PATCH 23/32] fix pnpm versioning in ci --- .github/workflows/ci.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 20f6f67..d61a739 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -13,8 +13,6 @@ jobs: - uses: actions/checkout@v4 - name: Install pnpm uses: pnpm/action-setup@v4 - with: - version: 8 - name: Use Node.js 22 uses: actions/setup-node@v4 with: From 398101a8a773691dc80edc6d1b32959d9622542f Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 16:23:34 -0700 Subject: [PATCH 24/32] console errors if user runs stdio with no api key + gemini key validation in config --- src/config.ts | 8 ++++++ src/program.ts | 2 +- src/transport.ts | 66 +++++++++++++++++++++++++++++++++++++++++++++++- 3 files changed, 74 insertions(+), 2 deletions(-) diff --git a/src/config.ts b/src/config.ts index 42a1e45..07d9368 100644 --- a/src/config.ts +++ b/src/config.ts @@ -51,6 +51,11 @@ export async function resolveConfig(cliOptions: CLIOptions): Promise { if (!mergedConfig.browserbaseProjectId) { mergedConfig.browserbaseProjectId = process.env.BROWSERBASE_PROJECT_ID; } + + if (!mergedConfig.modelApiKey) { + mergedConfig.modelApiKey = process.env.GEMINI_API_KEY; + } + // -------------------------------- // Basic validation for Browserbase keys @@ -62,6 +67,9 @@ export async function resolveConfig(cliOptions: CLIOptions): Promise { "Warning: BROWSERBASE_PROJECT_ID environment variable not set.", ); } + if (!mergedConfig.modelApiKey) { + console.warn("Warning: GEMINI_API_KEY environment variable not set."); + } return mergedConfig; } diff --git a/src/program.ts b/src/program.ts index 5a0ff80..78abaf6 100644 --- a/src/program.ts +++ b/src/program.ts @@ -79,7 +79,7 @@ program if (options.port) startHttpTransport(+options.port, options.host, serverList); - else await startStdioTransport(serverList); + else await startStdioTransport(serverList, config); }); function setupExitWatchdog(serverList: ServerList) { diff --git a/src/transport.ts b/src/transport.ts index abef1a0..c1f9152 100644 --- a/src/transport.ts +++ b/src/transport.ts @@ -6,8 +6,72 @@ import { ServerList } from "./server.js"; import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js"; import { SSEServerTransport } from "@modelcontextprotocol/sdk/server/sse.js"; import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js"; +import type { Config } from "../config.js"; + +export async function startStdioTransport( + serverList: ServerList, + config?: Config, +) { + // Check if we're using the default model without an API key + if (config) { + const modelName = config.modelName || "google/gemini-2.0-flash"; + const hasModelApiKey = config.modelApiKey || process.env.GEMINI_API_KEY; + + if (modelName.includes("google/gemini") && !hasModelApiKey) { + console.error(` +⚠️ IMPORTANT: MCP Server Configuration Update Required + +We've made changes to the MCP server that now require model API keys for local STDIO usage. + +You're using the default Gemini model (${modelName}) but no API key is configured. + +To fix this, you have two options: + +1. Set the GEMINI_API_KEY environment variable: + export GEMINI_API_KEY="your-gemini-api-key" + +2. Or add the --modelApiKey flag to your MCP config: + { + "mcpServers": { + "browserbase": { + "command": "npx", + "args": ["@browserbasehq/mcp"], + "env": { + "BROWSERBASE_API_KEY": "your-browserbase-key", + "BROWSERBASE_PROJECT_ID": "your-project-id" + "GEMINI_API_KEY": "your-gemini-api-key" + } + } + } + } + +You can get a Gemini API key from: https://aistudio.google.com/app/apikey + +3. Or choose another supported model: + Available models: https://docs.stagehand.dev/examples/custom_llms#llm-customization + + { + "mcpServers": { + "browserbase": { + "command": "npx", + "args": [ + "@browserbasehq/mcp", + "--modelName", "available-model", + "--modelApiKey", "your-api-key", + ], + "env": { + "BROWSERBASE_API_KEY": "your-browserbase-key", + "BROWSERBASE_PROJECT_ID": "your-project-id" + } + } + } + } + +The server will now attempt to start, but will likely fail without the API key... +`); + } + } -export async function startStdioTransport(serverList: ServerList) { const server = await serverList.create(); await server.connect(new StdioServerTransport()); } From 774c6d013d81873033f80e616a40a332bf66d104 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 17:22:12 -0700 Subject: [PATCH 25/32] smithery cli tools --- package.json | 2 ++ 1 file changed, 2 insertions(+) diff --git a/package.json b/package.json index ecbf7f2..469f831 100644 --- a/package.json +++ b/package.json @@ -22,6 +22,8 @@ "build": "tsc && shx chmod +x dist/*.js", "prepare": "husky", "watch": "tsc --watch", + "smithery": "npx @smithery/cli dev", + "inspector": "npx @modelcontextprotocol/inspector build/index.js", "lint": "eslint . --ext .ts", "prettier:check": "prettier --check .", "prettier:fix": "prettier --write .", From 5fd6b2f3270a6eba9fbcd405c42f30450addc58e Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 18:09:42 -0700 Subject: [PATCH 26/32] smithery yaml fix + smithery cli --- .gitignore | 10 +- package.json | 3 +- pnpm-lock.yaml | 293 +++++++++++++++++++++++++++++++++++++++++++++++++ smithery.yaml | 2 + 4 files changed, 298 insertions(+), 10 deletions(-) diff --git a/.gitignore b/.gitignore index 7a55993..15fe3ba 100644 --- a/.gitignore +++ b/.gitignore @@ -292,13 +292,5 @@ cython_debug/ .DS_Store -# PyCharm -# JetBrains specific template is maintained in a separate JetBrains.gitignore that can -# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore -# and can be added to the global gitignore or merged into this file. For a more nuclear -# option (not recommended) you can uncomment the following to ignore the entire idea folder. -#.idea/ - - # Smithery -/browserbase/.smithery \ No newline at end of file +/.smithery \ No newline at end of file diff --git a/package.json b/package.json index 469f831..b2bf7b6 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,7 @@ "build": "tsc && shx chmod +x dist/*.js", "prepare": "husky", "watch": "tsc --watch", - "smithery": "npx @smithery/cli dev", + "smithery": "npx @smithery/cli dev src/index.ts", "inspector": "npx @modelcontextprotocol/inspector build/index.js", "lint": "eslint . --ext .ts", "prettier:check": "prettier --check .", @@ -54,6 +54,7 @@ "lint-staged": "^16.1.2", "prettier": "^3.6.1", "shx": "^0.3.4", + "tsx": "^4.20.3", "typescript": "^5.6.2", "typescript-eslint": "^8.35.0" }, diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 888ac5f..e9cd0e5 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -54,6 +54,9 @@ importers: shx: specifier: ^0.3.4 version: 0.3.4 + tsx: + specifier: ^4.20.3 + version: 4.20.3 typescript: specifier: ^5.6.2 version: 5.8.3 @@ -174,6 +177,156 @@ packages: dotenv: ^16.4.5 zod: ^3.23.8 + '@esbuild/aix-ppc64@0.25.5': + resolution: {integrity: sha512-9o3TMmpmftaCMepOdA5k/yDw8SfInyzWWTjYTFCX3kPSDJMROQTb8jg+h9Cnwnmm1vOzvxN7gIfB5V2ewpjtGA==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [aix] + + '@esbuild/android-arm64@0.25.5': + resolution: {integrity: sha512-VGzGhj4lJO+TVGV1v8ntCZWJktV7SGCs3Pn1GRWI1SBFtRALoomm8k5E9Pmwg3HOAal2VDc2F9+PM/rEY6oIDg==} + engines: {node: '>=18'} + cpu: [arm64] + os: [android] + + '@esbuild/android-arm@0.25.5': + resolution: {integrity: sha512-AdJKSPeEHgi7/ZhuIPtcQKr5RQdo6OO2IL87JkianiMYMPbCtot9fxPbrMiBADOWWm3T2si9stAiVsGbTQFkbA==} + engines: {node: '>=18'} + cpu: [arm] + os: [android] + + '@esbuild/android-x64@0.25.5': + resolution: {integrity: sha512-D2GyJT1kjvO//drbRT3Hib9XPwQeWd9vZoBJn+bu/lVsOZ13cqNdDeqIF/xQ5/VmWvMduP6AmXvylO/PIc2isw==} + engines: {node: '>=18'} + cpu: [x64] + os: [android] + + '@esbuild/darwin-arm64@0.25.5': + resolution: {integrity: sha512-GtaBgammVvdF7aPIgH2jxMDdivezgFu6iKpmT+48+F8Hhg5J/sfnDieg0aeG/jfSvkYQU2/pceFPDKlqZzwnfQ==} + engines: {node: '>=18'} + cpu: [arm64] + os: [darwin] + + '@esbuild/darwin-x64@0.25.5': + resolution: {integrity: sha512-1iT4FVL0dJ76/q1wd7XDsXrSW+oLoquptvh4CLR4kITDtqi2e/xwXwdCVH8hVHU43wgJdsq7Gxuzcs6Iq/7bxQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [darwin] + + '@esbuild/freebsd-arm64@0.25.5': + resolution: {integrity: sha512-nk4tGP3JThz4La38Uy/gzyXtpkPW8zSAmoUhK9xKKXdBCzKODMc2adkB2+8om9BDYugz+uGV7sLmpTYzvmz6Sw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [freebsd] + + '@esbuild/freebsd-x64@0.25.5': + resolution: {integrity: sha512-PrikaNjiXdR2laW6OIjlbeuCPrPaAl0IwPIaRv+SMV8CiM8i2LqVUHFC1+8eORgWyY7yhQY+2U2fA55mBzReaw==} + engines: {node: '>=18'} + cpu: [x64] + os: [freebsd] + + '@esbuild/linux-arm64@0.25.5': + resolution: {integrity: sha512-Z9kfb1v6ZlGbWj8EJk9T6czVEjjq2ntSYLY2cw6pAZl4oKtfgQuS4HOq41M/BcoLPzrUbNd+R4BXFyH//nHxVg==} + engines: {node: '>=18'} + cpu: [arm64] + os: [linux] + + '@esbuild/linux-arm@0.25.5': + resolution: {integrity: sha512-cPzojwW2okgh7ZlRpcBEtsX7WBuqbLrNXqLU89GxWbNt6uIg78ET82qifUy3W6OVww6ZWobWub5oqZOVtwolfw==} + engines: {node: '>=18'} + cpu: [arm] + os: [linux] + + '@esbuild/linux-ia32@0.25.5': + resolution: {integrity: sha512-sQ7l00M8bSv36GLV95BVAdhJ2QsIbCuCjh/uYrWiMQSUuV+LpXwIqhgJDcvMTj+VsQmqAHL2yYaasENvJ7CDKA==} + engines: {node: '>=18'} + cpu: [ia32] + os: [linux] + + '@esbuild/linux-loong64@0.25.5': + resolution: {integrity: sha512-0ur7ae16hDUC4OL5iEnDb0tZHDxYmuQyhKhsPBV8f99f6Z9KQM02g33f93rNH5A30agMS46u2HP6qTdEt6Q1kg==} + engines: {node: '>=18'} + cpu: [loong64] + os: [linux] + + '@esbuild/linux-mips64el@0.25.5': + resolution: {integrity: sha512-kB/66P1OsHO5zLz0i6X0RxlQ+3cu0mkxS3TKFvkb5lin6uwZ/ttOkP3Z8lfR9mJOBk14ZwZ9182SIIWFGNmqmg==} + engines: {node: '>=18'} + cpu: [mips64el] + os: [linux] + + '@esbuild/linux-ppc64@0.25.5': + resolution: {integrity: sha512-UZCmJ7r9X2fe2D6jBmkLBMQetXPXIsZjQJCjgwpVDz+YMcS6oFR27alkgGv3Oqkv07bxdvw7fyB71/olceJhkQ==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [linux] + + '@esbuild/linux-riscv64@0.25.5': + resolution: {integrity: sha512-kTxwu4mLyeOlsVIFPfQo+fQJAV9mh24xL+y+Bm6ej067sYANjyEw1dNHmvoqxJUCMnkBdKpvOn0Ahql6+4VyeA==} + engines: {node: '>=18'} + cpu: [riscv64] + os: [linux] + + '@esbuild/linux-s390x@0.25.5': + resolution: {integrity: sha512-K2dSKTKfmdh78uJ3NcWFiqyRrimfdinS5ErLSn3vluHNeHVnBAFWC8a4X5N+7FgVE1EjXS1QDZbpqZBjfrqMTQ==} + engines: {node: '>=18'} + cpu: [s390x] + os: [linux] + + '@esbuild/linux-x64@0.25.5': + resolution: {integrity: sha512-uhj8N2obKTE6pSZ+aMUbqq+1nXxNjZIIjCjGLfsWvVpy7gKCOL6rsY1MhRh9zLtUtAI7vpgLMK6DxjO8Qm9lJw==} + engines: {node: '>=18'} + cpu: [x64] + os: [linux] + + '@esbuild/netbsd-arm64@0.25.5': + resolution: {integrity: sha512-pwHtMP9viAy1oHPvgxtOv+OkduK5ugofNTVDilIzBLpoWAM16r7b/mxBvfpuQDpRQFMfuVr5aLcn4yveGvBZvw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [netbsd] + + '@esbuild/netbsd-x64@0.25.5': + resolution: {integrity: sha512-WOb5fKrvVTRMfWFNCroYWWklbnXH0Q5rZppjq0vQIdlsQKuw6mdSihwSo4RV/YdQ5UCKKvBy7/0ZZYLBZKIbwQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [netbsd] + + '@esbuild/openbsd-arm64@0.25.5': + resolution: {integrity: sha512-7A208+uQKgTxHd0G0uqZO8UjK2R0DDb4fDmERtARjSHWxqMTye4Erz4zZafx7Di9Cv+lNHYuncAkiGFySoD+Mw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [openbsd] + + '@esbuild/openbsd-x64@0.25.5': + resolution: {integrity: sha512-G4hE405ErTWraiZ8UiSoesH8DaCsMm0Cay4fsFWOOUcz8b8rC6uCvnagr+gnioEjWn0wC+o1/TAHt+It+MpIMg==} + engines: {node: '>=18'} + cpu: [x64] + os: [openbsd] + + '@esbuild/sunos-x64@0.25.5': + resolution: {integrity: sha512-l+azKShMy7FxzY0Rj4RCt5VD/q8mG/e+mDivgspo+yL8zW7qEwctQ6YqKX34DTEleFAvCIUviCFX1SDZRSyMQA==} + engines: {node: '>=18'} + cpu: [x64] + os: [sunos] + + '@esbuild/win32-arm64@0.25.5': + resolution: {integrity: sha512-O2S7SNZzdcFG7eFKgvwUEZ2VG9D/sn/eIiz8XRZ1Q/DO5a3s76Xv0mdBzVM5j5R639lXQmPmSo0iRpHqUUrsxw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [win32] + + '@esbuild/win32-ia32@0.25.5': + resolution: {integrity: sha512-onOJ02pqs9h1iMJ1PQphR+VZv8qBMQ77Klcsqv9CNW2w6yLqoURLcgERAIurY6QE63bbLuqgP9ATqajFLK5AMQ==} + engines: {node: '>=18'} + cpu: [ia32] + os: [win32] + + '@esbuild/win32-x64@0.25.5': + resolution: {integrity: sha512-TXv6YnJ8ZMVdX+SXWVBo/0p8LTcrUYngpWjvm91TMjjBQii7Oz11Lw5lbDV5Y0TzuhSJHwiH4hEtC1I42mMS0g==} + engines: {node: '>=18'} + cpu: [x64] + os: [win32] + '@eslint-community/eslint-utils@4.7.0': resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} @@ -668,6 +821,11 @@ packages: resolution: {integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==} engines: {node: '>= 0.4'} + esbuild@0.25.5: + resolution: {integrity: sha512-P8OtKZRv/5J5hhz0cUAdu/cLuPIKXpQl1R9pZtvmHWQvrAUVd0UNIPT4IB4W3rNOqVO0rlqHmCIbSwxh/c9yUQ==} + engines: {node: '>=18'} + hasBin: true + escape-html@1.0.3: resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} @@ -838,6 +996,11 @@ packages: engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} os: [darwin] + fsevents@2.3.3: + resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} + engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} + os: [darwin] + function-bind@1.1.2: resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} @@ -872,6 +1035,9 @@ packages: resolution: {integrity: sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg==} engines: {node: '>= 0.4'} + get-tsconfig@4.10.1: + resolution: {integrity: sha512-auHyJ4AgMz7vgS8Hp3N6HXSmlMdUyhSUrfBF16w153rxtLIEOE+HGqaBppczZvnHLqQJfiHotCYpNhl0lUROFQ==} + glob-parent@5.1.2: resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} engines: {node: '>= 6'} @@ -1510,6 +1676,9 @@ packages: resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} engines: {node: '>=4'} + resolve-pkg-maps@1.0.0: + resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==} + resolve@1.22.10: resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} engines: {node: '>= 0.4'} @@ -1745,6 +1914,11 @@ packages: peerDependencies: typescript: '>=4.8.4' + tsx@4.20.3: + resolution: {integrity: sha512-qjbnuR9Tr+FJOMBqJCW5ehvIo/buZq7vH7qD7JziU98h6l3qGy0a/yPFjwO+y0/T7GFpNgNAvEcPPVfyT8rrPQ==} + engines: {node: '>=18.0.0'} + hasBin: true + type-check@0.4.0: resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} engines: {node: '>= 0.8.0'} @@ -2059,6 +2233,81 @@ snapshots: - supports-color - utf-8-validate + '@esbuild/aix-ppc64@0.25.5': + optional: true + + '@esbuild/android-arm64@0.25.5': + optional: true + + '@esbuild/android-arm@0.25.5': + optional: true + + '@esbuild/android-x64@0.25.5': + optional: true + + '@esbuild/darwin-arm64@0.25.5': + optional: true + + '@esbuild/darwin-x64@0.25.5': + optional: true + + '@esbuild/freebsd-arm64@0.25.5': + optional: true + + '@esbuild/freebsd-x64@0.25.5': + optional: true + + '@esbuild/linux-arm64@0.25.5': + optional: true + + '@esbuild/linux-arm@0.25.5': + optional: true + + '@esbuild/linux-ia32@0.25.5': + optional: true + + '@esbuild/linux-loong64@0.25.5': + optional: true + + '@esbuild/linux-mips64el@0.25.5': + optional: true + + '@esbuild/linux-ppc64@0.25.5': + optional: true + + '@esbuild/linux-riscv64@0.25.5': + optional: true + + '@esbuild/linux-s390x@0.25.5': + optional: true + + '@esbuild/linux-x64@0.25.5': + optional: true + + '@esbuild/netbsd-arm64@0.25.5': + optional: true + + '@esbuild/netbsd-x64@0.25.5': + optional: true + + '@esbuild/openbsd-arm64@0.25.5': + optional: true + + '@esbuild/openbsd-x64@0.25.5': + optional: true + + '@esbuild/sunos-x64@0.25.5': + optional: true + + '@esbuild/win32-arm64@0.25.5': + optional: true + + '@esbuild/win32-ia32@0.25.5': + optional: true + + '@esbuild/win32-x64@0.25.5': + optional: true + '@eslint-community/eslint-utils@4.7.0(eslint@9.29.0)': dependencies: eslint: 9.29.0 @@ -2680,6 +2929,34 @@ snapshots: is-date-object: 1.1.0 is-symbol: 1.1.1 + esbuild@0.25.5: + optionalDependencies: + '@esbuild/aix-ppc64': 0.25.5 + '@esbuild/android-arm': 0.25.5 + '@esbuild/android-arm64': 0.25.5 + '@esbuild/android-x64': 0.25.5 + '@esbuild/darwin-arm64': 0.25.5 + '@esbuild/darwin-x64': 0.25.5 + '@esbuild/freebsd-arm64': 0.25.5 + '@esbuild/freebsd-x64': 0.25.5 + '@esbuild/linux-arm': 0.25.5 + '@esbuild/linux-arm64': 0.25.5 + '@esbuild/linux-ia32': 0.25.5 + '@esbuild/linux-loong64': 0.25.5 + '@esbuild/linux-mips64el': 0.25.5 + '@esbuild/linux-ppc64': 0.25.5 + '@esbuild/linux-riscv64': 0.25.5 + '@esbuild/linux-s390x': 0.25.5 + '@esbuild/linux-x64': 0.25.5 + '@esbuild/netbsd-arm64': 0.25.5 + '@esbuild/netbsd-x64': 0.25.5 + '@esbuild/openbsd-arm64': 0.25.5 + '@esbuild/openbsd-x64': 0.25.5 + '@esbuild/sunos-x64': 0.25.5 + '@esbuild/win32-arm64': 0.25.5 + '@esbuild/win32-ia32': 0.25.5 + '@esbuild/win32-x64': 0.25.5 + escape-html@1.0.3: {} escape-string-regexp@4.0.0: {} @@ -2911,6 +3188,9 @@ snapshots: fsevents@2.3.2: optional: true + fsevents@2.3.3: + optional: true + function-bind@1.1.2: {} function.prototype.name@1.1.8: @@ -2970,6 +3250,10 @@ snapshots: es-errors: 1.3.0 get-intrinsic: 1.3.0 + get-tsconfig@4.10.1: + dependencies: + resolve-pkg-maps: 1.0.0 + glob-parent@5.1.2: dependencies: is-glob: 4.0.3 @@ -3622,6 +3906,8 @@ snapshots: resolve-from@4.0.0: {} + resolve-pkg-maps@1.0.0: {} + resolve@1.22.10: dependencies: is-core-module: 2.16.1 @@ -3909,6 +4195,13 @@ snapshots: dependencies: typescript: 5.8.3 + tsx@4.20.3: + dependencies: + esbuild: 0.25.5 + get-tsconfig: 4.10.1 + optionalDependencies: + fsevents: 2.3.3 + type-check@0.4.0: dependencies: prelude-ls: 1.2.1 diff --git a/smithery.yaml b/smithery.yaml index 322550e..14bf1b3 100644 --- a/smithery.yaml +++ b/smithery.yaml @@ -1 +1,3 @@ runtime: "typescript" +packageManager: "pnpm" +buildCommand: "pnpm build" \ No newline at end of file From b6e7dd1fc8948203ceed981f32052e40bdac86a5 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 20:49:02 -0700 Subject: [PATCH 27/32] rm sse + dockerfile update to support pnpm --- config.d.ts | 2 +- smithery.yaml | 5 +++-- src/index.ts | 2 +- src/program.ts | 2 +- src/transport.ts | 43 +------------------------------------------ 5 files changed, 7 insertions(+), 47 deletions(-) diff --git a/config.d.ts b/config.d.ts index 365b42e..fac210d 100644 --- a/config.d.ts +++ b/config.d.ts @@ -63,7 +63,7 @@ export type Config = { */ server?: { /** - * The port to listen on for SSE or MCP transport. + * The port to listen on for SHTTP or MCP transport. */ port?: number; /** diff --git a/smithery.yaml b/smithery.yaml index 14bf1b3..8ee266a 100644 --- a/smithery.yaml +++ b/smithery.yaml @@ -1,3 +1,4 @@ runtime: "typescript" -packageManager: "pnpm" -buildCommand: "pnpm build" \ No newline at end of file +build: + dockerfile: "Dockerfile" + dockerBuildPath: "." \ No newline at end of file diff --git a/src/index.ts b/src/index.ts index 900caa8..6a6d047 100644 --- a/src/index.ts +++ b/src/index.ts @@ -81,7 +81,7 @@ export const configSchema = z port: z .number() .optional() - .describe("The port to listen on for SSE or MCP transport"), + .describe("The port to listen on for SHTTP or MCP transport"), host: z .string() .optional() diff --git a/src/program.ts b/src/program.ts index 78abaf6..c931f94 100644 --- a/src/program.ts +++ b/src/program.ts @@ -46,7 +46,7 @@ program "Whether to persist the Browserbase context", true, ) - .option("--port ", "Port to listen on for SSE transport.") + .option("--port ", "Port to listen on for SHTTP transport.") .option( "--host ", "Host to bind server to. Default is localhost. Use 0.0.0.0 to bind to all interfaces.", diff --git a/src/transport.ts b/src/transport.ts index c1f9152..fecc861 100644 --- a/src/transport.ts +++ b/src/transport.ts @@ -4,7 +4,6 @@ import crypto from "node:crypto"; import { ServerList } from "./server.js"; import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js"; -import { SSEServerTransport } from "@modelcontextprotocol/sdk/server/sse.js"; import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js"; import type { Config } from "../config.js"; @@ -76,44 +75,6 @@ The server will now attempt to start, but will likely fail without the API key.. await server.connect(new StdioServerTransport()); } -async function handleSSE( - req: http.IncomingMessage, - res: http.ServerResponse, - url: URL, - serverList: ServerList, - sessions: Map, -) { - if (req.method === "POST") { - const sessionId = url.searchParams.get("sessionId"); - if (!sessionId) { - res.statusCode = 400; - return res.end("Missing sessionId"); - } - - const transport = sessions.get(sessionId); - if (!transport) { - res.statusCode = 404; - return res.end("Session not found"); - } - - return await transport.handlePostMessage(req, res); - } else if (req.method === "GET") { - const transport = new SSEServerTransport("/sse", res); - sessions.set(transport.sessionId, transport); - const server = await serverList.create(); - res.on("close", () => { - sessions.delete(transport.sessionId); - serverList.close(server).catch((e) => { - console.error(e); - }); - }); - return await server.connect(transport); - } - - res.statusCode = 405; - res.end("Method not allowed"); -} - async function handleStreamable( req: http.IncomingMessage, res: http.ServerResponse, @@ -155,7 +116,6 @@ export function startHttpTransport( hostname: string | undefined, serverList: ServerList, ) { - const sseSessions = new Map(); const streamableSessions = new Map(); const httpServer = http.createServer(async (req, res) => { if (!req.url) { @@ -166,7 +126,6 @@ export function startHttpTransport( const url = new URL(`http://localhost${req.url}`); if (url.pathname.startsWith("/mcp")) await handleStreamable(req, res, serverList, streamableSessions); - else await handleSSE(req, res, url, serverList, sseSessions); }); httpServer.listen(port, hostname, () => { const address = httpServer.address(); @@ -189,7 +148,7 @@ export function startHttpTransport( { mcpServers: { browserbase: { - url: `${url}/sse`, + url: `${url}/mcp`, }, }, }, From 85d9e96c4f8c32f9b6a5063987fae01efe0df3d5 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 21:42:57 -0700 Subject: [PATCH 28/32] dockerfile --- Dockerfile | 26 ++++++++++++++++++++++++++ smithery.yaml | 3 ++- 2 files changed, 28 insertions(+), 1 deletion(-) create mode 100644 Dockerfile diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..c784944 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,26 @@ +# ----- Build Stage ----- +FROM node:lts-alpine AS builder +WORKDIR /app + +# Copy package and configuration +COPY package.json pnpm-lock.yaml tsconfig.json ./ + +# Copy source code +COPY src ./src + +# Install dependencies and build +RUN corepack enable && pnpm install --frozen-lockfile && pnpm build + +# ----- Production Stage ----- +FROM node:lts-alpine +WORKDIR /app + +# Copy built artifacts and required files +COPY --from=builder /app/dist ./dist +COPY index.js config.d.ts index.d.ts cli.js ./ + +# Expose HTTP port +EXPOSE 8080 + +# Default command using CLI flags +CMD ["node", "cli.js", "--port", "8080"] \ No newline at end of file diff --git a/smithery.yaml b/smithery.yaml index 8ee266a..13d2f34 100644 --- a/smithery.yaml +++ b/smithery.yaml @@ -1,4 +1,5 @@ runtime: "typescript" build: dockerfile: "Dockerfile" - dockerBuildPath: "." \ No newline at end of file + dockerBuildPath: "." + dockerfilePath: "./Dockerfile" \ No newline at end of file From 0026cccfea91d6f4730218d4b9f12a149596588a Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Thu, 3 Jul 2025 21:52:20 -0700 Subject: [PATCH 29/32] switch to container deploy --- smithery.yaml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/smithery.yaml b/smithery.yaml index 13d2f34..757886b 100644 --- a/smithery.yaml +++ b/smithery.yaml @@ -1,5 +1,6 @@ -runtime: "typescript" +runtime: "container" build: dockerfile: "Dockerfile" dockerBuildPath: "." - dockerfilePath: "./Dockerfile" \ No newline at end of file +startCommand: + type: "http" \ No newline at end of file From 156fd639cae15e998b10ea5b33ae0160c6ee5fc2 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Fri, 4 Jul 2025 17:38:16 -0700 Subject: [PATCH 30/32] adjusting dockerfile and config imports --- Dockerfile | 9 ++++++++- src/config.ts | 2 +- src/context.ts | 2 +- src/index.ts | 2 +- src/sessionManager.ts | 2 +- src/stagehandStore.ts | 2 +- src/transport.ts | 2 +- 7 files changed, 14 insertions(+), 7 deletions(-) diff --git a/Dockerfile b/Dockerfile index c784944..8483657 100644 --- a/Dockerfile +++ b/Dockerfile @@ -8,6 +8,9 @@ COPY package.json pnpm-lock.yaml tsconfig.json ./ # Copy source code COPY src ./src +# Copy config files +COPY config.d.ts index.d.ts ./ + # Install dependencies and build RUN corepack enable && pnpm install --frozen-lockfile && pnpm build @@ -15,9 +18,13 @@ RUN corepack enable && pnpm install --frozen-lockfile && pnpm build FROM node:lts-alpine WORKDIR /app +# Copy package.json and install production dependencies +COPY package.json pnpm-lock.yaml ./ +RUN corepack enable && pnpm install --prod --frozen-lockfile --ignore-scripts + # Copy built artifacts and required files COPY --from=builder /app/dist ./dist -COPY index.js config.d.ts index.d.ts cli.js ./ +COPY index.js config.d.ts index.d.ts cli.js ./ # Expose HTTP port EXPOSE 8080 diff --git a/src/config.ts b/src/config.ts index 07d9368..25a82e1 100644 --- a/src/config.ts +++ b/src/config.ts @@ -1,5 +1,5 @@ import type { Cookie } from "playwright-core"; -import type { Config } from "../config.js"; +import type { Config } from "../config.d.ts"; import { AvailableModelSchema } from "@browserbasehq/stagehand"; export type ToolCapability = "core" | string; diff --git a/src/context.ts b/src/context.ts index ae18ad9..3b2abcc 100644 --- a/src/context.ts +++ b/src/context.ts @@ -1,6 +1,6 @@ import type { Stagehand } from "@browserbasehq/stagehand"; import { Server } from "@modelcontextprotocol/sdk/server/index.js"; -import type { Config } from "../config.js"; +import type { Config } from "../config.d.ts"; import { CallToolResult } from "@modelcontextprotocol/sdk/types.js"; import { listResources, readResource } from "./mcp/resources.js"; import { getSession, defaultSessionId } from "./sessionManager.js"; diff --git a/src/index.ts b/src/index.ts index 6a6d047..c6f04df 100644 --- a/src/index.ts +++ b/src/index.ts @@ -6,7 +6,7 @@ import { z } from "zod"; import type { MCPToolsArray } from "./types/types.js"; import { Context } from "./context.js"; -import type { Config } from "../config.js"; +import type { Config } from "../config.d.ts"; import { TOOLS } from "./tools/index.js"; import { AvailableModelSchema } from "@browserbasehq/stagehand"; import { PROMPTS, getPrompt } from "./mcp/prompts.js"; diff --git a/src/sessionManager.ts b/src/sessionManager.ts index 7150353..d58a608 100644 --- a/src/sessionManager.ts +++ b/src/sessionManager.ts @@ -1,6 +1,6 @@ import { Page } from "playwright-core"; import { BrowserContext } from "@browserbasehq/stagehand"; -import type { Config } from "../config.js"; +import type { Config } from "../config.d.ts"; import type { Cookie } from "playwright-core"; import { createStagehandInstance } from "./stagehandStore.js"; import type { BrowserSession } from "./types/types.js"; diff --git a/src/stagehandStore.ts b/src/stagehandStore.ts index 0224ba0..0c9c534 100644 --- a/src/stagehandStore.ts +++ b/src/stagehandStore.ts @@ -2,7 +2,7 @@ import { randomUUID } from "crypto"; import { Stagehand, AvailableModel } from "@browserbasehq/stagehand"; import { Page } from "playwright-core"; import { StagehandSession, CreateSessionParams } from "./types/types.js"; -import type { Config } from "../config.js"; +import type { Config } from "../config.d.ts"; // Store for all active sessions const store = new Map(); diff --git a/src/transport.ts b/src/transport.ts index fecc861..aae5354 100644 --- a/src/transport.ts +++ b/src/transport.ts @@ -5,7 +5,7 @@ import crypto from "node:crypto"; import { ServerList } from "./server.js"; import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js"; import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js"; -import type { Config } from "../config.js"; +import type { Config } from "../config.d.ts"; export async function startStdioTransport( serverList: ServerList, From f7f48853c27cfdba406b6ace67ea92b55a88d130 Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Fri, 4 Jul 2025 18:01:07 -0700 Subject: [PATCH 31/32] smithery yaml update --- smithery.yaml | 36 +++++++++++++++++++++++++++++++++++- 1 file changed, 35 insertions(+), 1 deletion(-) diff --git a/smithery.yaml b/smithery.yaml index 757886b..a4d9ee1 100644 --- a/smithery.yaml +++ b/smithery.yaml @@ -3,4 +3,38 @@ build: dockerfile: "Dockerfile" dockerBuildPath: "." startCommand: - type: "http" \ No newline at end of file + type: "http" + configSchema: + type: "object" + required: ["browserbaseApiKey", "browserbaseProjectId"] + properties: + browserbaseApiKey: + type: "string" + title: "Browserbase API Key" + description: "The Browserbase API Key to use" + browserbaseProjectId: + type: "string" + title: "Browserbase Project ID" + description: "The Browserbase Project ID to use" + proxies: + type: "boolean" + default: false + description: "Whether or not to use Browserbase proxies" + advancedStealth: + type: "boolean" + default: false + description: "Use advanced stealth mode. Only available to Browserbase Scale Plan users" + modelApiKey: + type: "string" + description: "API key for the custom model provider (e.g., GEMINI_API_KEY)" + modelName: + type: "string" + default: "google/gemini-2.0-flash" + description: "The model to use for Stagehand" + exampleConfig: + browserbaseApiKey: "bb_api_key_example" + browserbaseProjectId: "bb_project_id_example" + proxies: false + advancedStealth: false + modelApiKey: "your_gemini_api_key" + modelName: "google/gemini-2.0-flash" \ No newline at end of file From 970dc551e0d9013c711b658cb00686d2146d898a Mon Sep 17 00:00:00 2001 From: Kylejeong2 Date: Sat, 5 Jul 2025 20:49:01 -1000 Subject: [PATCH 32/32] await session cleanup --- package.json | 11 ++++++++++- src/sessionManager.ts | 8 +++++++- src/tools/session.ts | 2 +- 3 files changed, 18 insertions(+), 3 deletions(-) diff --git a/package.json b/package.json index b2bf7b6..80ff510 100644 --- a/package.json +++ b/package.json @@ -28,7 +28,14 @@ "prettier:check": "prettier --check .", "prettier:fix": "prettier --write .", "clean": "rm -rf dist", - "prepublishOnly": "pnpm clean && pnpm build" + "prepublishOnly": "pnpm clean && pnpm build", + "test": "bash tests/run-tests.sh", + "test:minimal": "bash tests/run-tests.sh --type minimal", + "test:advanced": "bash tests/run-tests.sh --type advanced --llm", + "test:all": "bash tests/run-tests.sh --type all", + "test:debug": "bash tests/run-tests.sh --debug", + "test:install": "npm install @mcpvals chalk", + "test:runner": "tsx tests/run-evals.ts" }, "lint-staged": { "*.{js,jsx,ts,tsx,json,css,scss,md}": [ @@ -47,6 +54,8 @@ }, "devDependencies": { "@eslint/js": "^9.29.0", + "@mcpvals": "^0.1.0", + "chalk": "^5.3.0", "eslint": "^9.29.0", "eslint-plugin-react": "^7.37.5", "globals": "^16.2.0", diff --git a/src/sessionManager.ts b/src/sessionManager.ts index d58a608..5bbc00b 100644 --- a/src/sessionManager.ts +++ b/src/sessionManager.ts @@ -324,9 +324,15 @@ export async function getSession( * This is called after a browser is closed to ensure proper cleanup. * @param sessionId The session ID to clean up */ -export function cleanupSession(sessionId: string): void { +export async function cleanupSession(sessionId: string): Promise { process.stderr.write(`[SessionManager] Cleaning up session: ${sessionId}\n`); + // Get the session to close it gracefully + const session = browsers.get(sessionId); + if (session) { + await closeBrowserGracefully(session, sessionId); + } + // Remove from browsers map browsers.delete(sessionId); diff --git a/src/tools/session.ts b/src/tools/session.ts index cc0069f..c5c4e6a 100644 --- a/src/tools/session.ts +++ b/src/tools/session.ts @@ -161,7 +161,7 @@ async function handleCloseSession(context: Context): Promise { ); // Clean up the session from tracking - cleanupSession(previousSessionId); + await cleanupSession(previousSessionId); if (browserbaseSessionId) { process.stderr.write(

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 O|L9#eyjG@V9r=IP9=qNE diff --git a/browserbase/.npmignore b/browserbase/.npmignore deleted file mode 100644 index 24c1dd0..0000000 --- a/browserbase/.npmignore +++ /dev/null @@ -1,15 +0,0 @@ -# Ignore node_modules, build output, logs, env files, etc. -node_modules -dist -*.log -.env* - -# Ignore IDE/editor files -.vscode -.idea -*.swp -*.swo - -# Ignore OS files -.DS_Store -Thumbs.db \ No newline at end of file diff --git a/browserbase/README.md b/browserbase/README.md deleted file mode 100644 index e30f58a..0000000 --- a/browserbase/README.md +++ /dev/null @@ -1,316 +0,0 @@ -# Playwright Browserbase MCP Server - -![cover](../assets/browserbase-mcp.png) - -The Model Context Protocol (MCP) is an open protocol that enables seamless integration between LLM applications and external data sources and tools. Whether you’re building an AI-powered IDE, enhancing a chat interface, or creating custom AI workflows, MCP provides a standardized way to connect LLMs with the context they need. - -