From 8a514cbcdb88e6d822eb21c885e110f667f79538 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Tue, 19 May 2026 15:54:44 -0700 Subject: [PATCH 01/16] Add prompt evaluations and tests --- eval-scores.json | 161 + evals/.env.example | 25 + evals/.gitignore | 15 + evals/README.md | 382 + evals/aiconfig-create/promptfooconfig.yaml | 210 + evals/aiconfig-tools/promptfooconfig.yaml | 211 + evals/aiconfig-update/promptfooconfig.yaml | 238 + .../aiconfig-variations/promptfooconfig.yaml | 239 + .../promptfooconfig.yaml | 168 + evals/mocks/tool-responses.json | 526 + evals/package-lock.json | 12343 ++++++++++++++++ evals/package.json | 34 + evals/providers/_jsonschema-to-zod.js | 84 + evals/providers/_mock.js | 304 + evals/providers/claude-skill-agent-sdk.js | 542 + evals/scripts/_manifest.js | 59 + evals/scripts/_models.js | 42 + evals/scripts/aggregate.js | 165 + evals/scripts/diff-changed-skills.js | 155 + evals/scripts/render-badges.js | 96 + evals/scripts/run-models.js | 210 + evals/shared/assertions.js | 129 + evals/shared/defaults.yaml | 33 + evals/shared/output-valid.js | 18 + evals/shared/transform.js | 21 + evals/tests/assertions.test.js | 174 + evals/tests/jsonschema-to-zod.test.js | 126 + evals/tests/mock.test.js | 321 + evals/tests/output-valid.test.js | 45 + evals/tests/transform.test.js | 28 + evals/tools/definitions.json | 513 + package.json | 6 +- 32 files changed, 17621 insertions(+), 2 deletions(-) create mode 100644 eval-scores.json create mode 100644 evals/.env.example create mode 100644 evals/.gitignore create mode 100644 evals/README.md create mode 100644 evals/aiconfig-create/promptfooconfig.yaml create mode 100644 evals/aiconfig-tools/promptfooconfig.yaml create mode 100644 evals/aiconfig-update/promptfooconfig.yaml create mode 100644 evals/aiconfig-variations/promptfooconfig.yaml create mode 100644 evals/launchdarkly-flag-create/promptfooconfig.yaml create mode 100644 evals/mocks/tool-responses.json create mode 100644 evals/package-lock.json create mode 100644 evals/package.json create mode 100644 evals/providers/_jsonschema-to-zod.js create mode 100644 evals/providers/_mock.js create mode 100644 evals/providers/claude-skill-agent-sdk.js create mode 100644 evals/scripts/_manifest.js create mode 100644 evals/scripts/_models.js create mode 100644 evals/scripts/aggregate.js create mode 100644 evals/scripts/diff-changed-skills.js create mode 100644 evals/scripts/render-badges.js create mode 100644 evals/scripts/run-models.js create mode 100644 evals/shared/assertions.js create mode 100644 evals/shared/defaults.yaml create mode 100644 evals/shared/output-valid.js create mode 100644 evals/shared/transform.js create mode 100644 evals/tests/assertions.test.js create mode 100644 evals/tests/jsonschema-to-zod.test.js create mode 100644 evals/tests/mock.test.js create mode 100644 evals/tests/output-valid.test.js create mode 100644 evals/tests/transform.test.js create mode 100644 evals/tools/definitions.json diff --git a/eval-scores.json b/eval-scores.json new file mode 100644 index 0000000..170d8d4 --- /dev/null +++ b/eval-scores.json @@ -0,0 +1,161 @@ +{ + "schemaVersion": 1, + "updatedAt": "2026-05-19T22:29:45.928Z", + "skills": { + "ai-configs/aiconfig-create": { + "score": 100, + "passed": 4, + "total": 4, + "status": "passing", + "lastCommit": "fc69376", + "lastRun": "2026-05-19T22:29:45.923Z", + "perTest": [ + { + "description": "Create an AI Config for my customer support bot. It uses LangGraph and needs per", + "pass": true, + "score": 1 + }, + { + "description": "I need an AI Config for our blog summarizer. We call the OpenAI API directly wit", + "pass": true, + "score": 1 + }, + { + "description": "Create a new AI Config for our analytics agent. Project key is \"data-platform\".\n", + "pass": true, + "score": 1 + }, + { + "description": "Create an AI Config called \"email-assistant\" for composing emails. Project is \"c", + "pass": true, + "score": 0.8333333333333334 + } + ] + }, + "ai-configs/aiconfig-update": { + "score": 80, + "passed": 4, + "total": 5, + "status": "passing", + "lastCommit": "fc69376", + "lastRun": "2026-05-19T22:29:45.925Z", + "perTest": [ + { + "description": "I need to switch the model on the default variation of our support-chatbot confi", + "pass": true, + "score": 0.95 + }, + { + "description": "We no longer need the content-writer AI Config. Please remove it from active use", + "pass": true, + "score": 1 + }, + { + "description": "Update the support-chatbot AI Config in project \"support-app\": change the name t", + "pass": true, + "score": 1 + }, + { + "description": "The old code-reviewer config in project \"dev-tools\" is completely obsolete. We s", + "pass": false, + "score": 0.4166666666666667 + }, + { + "description": "Update the temperature parameter on the default variation of our support-chatbot", + "pass": true, + "score": 0.9444444444444444 + } + ] + }, + "ai-configs/aiconfig-tools": { + "score": 75, + "passed": 3, + "total": 4, + "status": "passing", + "lastCommit": "fc69376", + "lastRun": "2026-05-19T22:29:45.926Z", + "perTest": [ + { + "description": "I need to give our support-chatbot AI Config the ability to search our knowledge", + "pass": true, + "score": 1 + }, + { + "description": "Create an AI tool called \"create-ticket\" that accepts title (required string), p", + "pass": true, + "score": 1 + }, + { + "description": "I want to add a tool to our support-chatbot for looking up customer orders. Befo", + "pass": false, + "score": 0.25 + }, + { + "description": "Attach a new \"fetch-weather\" tool to the travel-assistant config's default varia", + "pass": true, + "score": 1 + } + ] + }, + "ai-configs/aiconfig-variations": { + "score": 80, + "passed": 4, + "total": 5, + "status": "passing", + "lastCommit": "fc69376", + "lastRun": "2026-05-19T22:29:45.927Z", + "perTest": [ + { + "description": "I want to test if gpt-4o-mini can handle our support chatbot as well as gpt-4o b", + "pass": true, + "score": 1 + }, + { + "description": "I want to experiment with a more concise prompt for our support-chatbot config. ", + "pass": true, + "score": 1 + }, + { + "description": "Add a new variation to our code-reviewer config that uses Anthropic Claude Sonne", + "pass": true, + "score": 1 + }, + { + "description": "I want to replace the default variation of support-chatbot with a new Claude-bas", + "pass": false, + "score": 0.4166666666666667 + }, + { + "description": "Clone the default variation of content-writer to test gpt-4o-mini. Project key i", + "pass": true, + "score": 1 + } + ] + }, + "feature-flags/launchdarkly-flag-create": { + "score": 67, + "passed": 2, + "total": 3, + "status": "failing", + "lastCommit": "fc69376", + "lastRun": "2026-05-19T22:29:45.928Z", + "perTest": [ + { + "description": "I need to wrap our new checkout flow in a feature flag so we can roll it out gra", + "pass": true, + "score": 1 + }, + { + "description": "Add a feature flag for our new dark mode feature. Project key is \"web-app\".\n", + "pass": false, + "score": 0.375 + }, + { + "description": "Create a feature flag for our A/B test of the new onboarding flow. Project key i", + "pass": true, + "score": 1 + } + ] + } + } +} diff --git a/evals/.env.example b/evals/.env.example new file mode 100644 index 0000000..dbd2857 --- /dev/null +++ b/evals/.env.example @@ -0,0 +1,25 @@ +# Copy to evals/.env and fill in. Both files are gitignored. +# +# REQUIRED: API key for both the agent (system under test) and the rubric +# grader unless you switch the grader to a non-Anthropic provider via +# RUBRIC_MODEL below. +# Get yours at https://console.anthropic.com +ANTHROPIC_API_KEY= + +# OPTIONAL: the system-under-test model. Stays on Claude because that's what +# real users will run skills against. Defaults to claude-sonnet-4-6 if unset. +# AGENT_MODEL=claude-sonnet-4-6 + +# REQUIRED: the rubric grader for `llm-rubric` assertions. Wired into +# shared/defaults.yaml as defaultTest.options.provider. Pick a cheaper model +# than AGENT_MODEL since this only judges agent output and runs once per +# rubric assertion. +# +# Examples: +# anthropic:messages:claude-haiku-4-5-20251001 +# openai:gpt-4.1-mini +RUBRIC_MODEL=anthropic:messages:claude-haiku-4-5-20251001 + +# OPTIONAL: only needed if RUBRIC_MODEL points at an OpenAI model. +# Get yours at https://platform.openai.com/api-keys +# OPENAI_API_KEY= diff --git a/evals/.gitignore b/evals/.gitignore new file mode 100644 index 0000000..e18735d --- /dev/null +++ b/evals/.gitignore @@ -0,0 +1,15 @@ +node_modules/ +.env +.promptfoo/ +results*.json +results*.html + +# Per-suite results written by npm run eval: and scripts/aggregate.js. +# These are inputs to scripts/aggregate.js; the aggregated artifact +# (eval-scores.json at repo root) is the public source of truth. +*/results.json + +# Per-skill isolated cwds built by the provider so the SDK only discovers +# the one skill being evaluated. Regenerated on each run, never committed. +.tmp-skill-fixtures/ +.DS_Store diff --git a/evals/README.md b/evals/README.md new file mode 100644 index 0000000..1199241 --- /dev/null +++ b/evals/README.md @@ -0,0 +1,382 @@ +# Skill Evaluations + +Automated evaluations for LaunchDarkly agent skills using [promptfoo](https://promptfoo.dev). + +Each skill gets a set of test cases that verify an agent follows the skill's workflow correctly when given realistic user requests. The evals run Claude through the [Claude Agent SDK](https://www.npmjs.com/package/@anthropic-ai/claude-agent-sdk) so `SKILL.md` is loaded the way a real Claude Code session loads it (off disk, via `.claude/skills//`), present it with mocked LaunchDarkly MCP tools, and assert on both the tool-call trajectory and response quality. + +## Setup + +```bash +cd evals +npm install +cp .env.example .env # then fill in ANTHROPIC_API_KEY (and optionally AGENT_MODEL / RUBRIC_MODEL) +``` + +## Unit Tests + +The harness utility modules (`_mock.js`, `_jsonschema-to-zod.js`, `transform.js`, `output-valid.js`, `assertions.js`) have unit tests that run without any API calls or environment variables: + +```bash +npm test +``` + +Run these after any changes to the provider, mock, or shared utilities to catch regressions before running full evals. + +## Running Evals + +```bash +# From evals/ + +# Run a single suite (all test cases) +npm run eval:aiconfig-create # ai-configs/aiconfig-create +npm run eval:aiconfig-update # ai-configs/aiconfig-update +npm run eval:aiconfig-tools # ai-configs/aiconfig-tools +npm run eval:aiconfig-variations # ai-configs/aiconfig-variations +npm run eval:flag-create # feature-flags/launchdarkly-flag-create + +# Quick smoke check — first test case only (~15-20s, ~$0.05) +npm run eval:aiconfig-create:single +npm run eval:aiconfig-update:single +npm run eval:aiconfig-tools:single +npm run eval:aiconfig-variations:single +npm run eval:flag-create:single + +# Aggregate and CI operations +npm run eval:all # Run every suite and rebuild ../eval-scores.json +npm run eval:aggregate # Rebuild eval-scores.json from existing results (no API calls) +npm run eval:diff # Show which suites need re-running since last eval:all +npm run eval:badges # Rewrite eval score badges in skill READMEs +npm run eval:view # Open results UI at localhost:15500 + +# Cross-model evaluation +npm run eval:haiku # Run all suites against claude-haiku-4-5 +npm run eval:sonnet # Run all suites against claude-sonnet-4-6 +npm run eval:opus # Run all suites against claude-opus-4-6 +npm run eval:matrix # Run all suites against haiku + sonnet + opus + +# From repo root +npm run eval # Alias for eval:all +``` + +All scripts pass `--no-cache` so dev iterations always reflect the current `SKILL.md` and provider. + +## Environment Variables + +| Variable | Required | Purpose | +|----------|----------|---------| +| `ANTHROPIC_API_KEY` | Yes | Authenticates the agent with Anthropic. Also used by the rubric grader if `RUBRIC_MODEL` is an Anthropic model (the default). | +| `AGENT_MODEL` | No | Override the system-under-test model (default: `claude-sonnet-4-6`). | +| `RUBRIC_MODEL` | Yes | Rubric grader model for `llm-rubric` assertions (set in `.env.example`). | +| `OPENAI_API_KEY` | If using OpenAI for `RUBRIC_MODEL` | Authenticates the rubric grader. | +| `SKILL_EVAL_DEBUG=1` | No | Dump every SDK message to a temp JSON file for inspection. | + +## Architecture + +``` +evals/ + package.json # npm scripts + dependencies + .env.example # Environment variable template + shared/ + defaults.yaml # defaultTest block merged into every suite + transform.js # Parses agent output once; assertions skip JSON.parse + output-valid.js # Weight-0 sanity assertion for the parse step + assertions.js # Trajectory helper functions (for scripts, not inline assertions) + providers/ + claude-skill-agent-sdk.js # The agent loop: loads skill via SDK, mocks LD tools + _mock.js # Template renderer + stateful write/read overlay + _jsonschema-to-zod.js # JSON Schema -> Zod shape converter + tools/ + definitions.json # Anthropic-format tool definitions for all LD MCP tools + mocks/ + tool-responses.json # Canned responses for mocked tool calls + scripts/ + _manifest.js # Maps suites to skills (single source of truth) + _models.js # Model aliases: haiku, sonnet, opus + aggregate.js # Runs suites and writes ../eval-scores.json + diff-changed-skills.js # Lists suites that need re-running based on git changes + render-badges.js # Rewrites eval score badges in skill READMEs + run-models.js # Cross-model runner (haiku/sonnet/opus matrix) + / + promptfooconfig.yaml # One per skill; test cases + assertions +``` + +### How a test case runs + +1. Promptfoo loads the suite config merged with `shared/defaults.yaml`. +2. The provider creates an isolated temp directory containing only a symlink to the target skill at `.claude/skills//` so the SDK only discovers the one skill being evaluated. +3. LaunchDarkly MCP tools are exposed through an in-process mock server. Responses come from `mocks/tool-responses.json` with `{{placeholder}}` substitution from the tool's input arguments. +4. The agent runs. Every tool call is recorded into a `trajectory`. When done, the provider returns: + ```json + { + "response": "The agent's final text", + "first_assistant_text": "The agent's first non-empty text turn", + "kickoff_text": "All assistant prose up to and including the first user-observable tool call", + "assistant_turns": [{ "turn": 1, "text": "..." }], + "trajectory": [{ "tool": "setup-ai-config", "arguments": {...}, "turn": 2 }], + "tools_called": ["list-ai-configs", "setup-ai-config"], + "turn_count": 3, + "terminated": null + } + ``` +5. `shared/transform.js` parses the JSON before assertions run. Every assertion receives `output` as an object — **do not call `JSON.parse(output)` inside assertions**. + +### Shared defaults (`shared/defaults.yaml`) + +Every suite is run with two `-c` flags: + +```bash +promptfoo eval -c shared/defaults.yaml -c /promptfooconfig.yaml +``` + +The shared defaults supply: +- `defaultTest.threshold: 0.75` — minimum weighted-average score per test to count as passing. +- `defaultTest.options.transform: file://./transform.js` — parses the agent's JSON output once. +- `defaultTest.assert` — sanity check (`output_valid`, weight 0) and latency assertion (180s cap). + +### Trajectory ordering convention + +Use **FIRST occurrence** for prerequisites and **LAST occurrence** for verifiers when checking tool ordering: + +```js +const aIdx = tools.indexOf('list-ai-configs'); // first: prerequisite +const bIdx = tools.lastIndexOf('setup-ai-config'); // last: verifier +const pass = aIdx >= 0 && bIdx > aIdx; +``` + +This handles agents that call `get-foo` before AND after mutation; using `indexOf` for both would silently pass against the pre-mutation call. + +### Cross-model evaluation (`run-models.js`) + +The cross-model runner evaluates all suites against one or more model aliases without touching the canonical `eval-scores.json`. Results are written to `/results..json` (e.g., `aiconfig-create/results.haiku.json`). + +```bash +npm run eval:haiku # claude-haiku-4-5-20251001 +npm run eval:sonnet # claude-sonnet-4-6 +npm run eval:opus # claude-opus-4-6 +npm run eval:matrix # all three in sequence +``` + +After running, a summary matrix is printed to stdout. These files are gitignored — they're for local comparison only. + +### Diff-gated re-runs (`diff-changed-skills.js`) + +`eval:diff` compares the current `HEAD` against the `lastCommit` recorded in `eval-scores.json` and reports which suites need re-running: + +```bash +npm run eval:diff # prints affected suites +npm run eval:diff -- --json # machine-readable JSON array +npm run eval:diff -- --verbose # show changed file paths +npm run eval:diff -- --base=abc1234 # compare against a specific commit +``` + +**Global triggers** — changes to `evals/providers`, `evals/shared`, `evals/tools`, or `evals/mocks` invalidate every suite, because those files affect all test runs. + +Typical CI workflow: +```bash +npm run eval:diff -- --json # determine which suites changed +# then run only the affected suite(s) +npm run eval: +npm run eval:aggregate # rebuild eval-scores.json from results +``` + +### README badge rendering (`render-badges.js`) + +`eval:badges` rewrites the eval score block in each skill's README between `` and `` markers: + +```bash +npm run eval:badges +``` + +If a skill README doesn't have the markers, `render-badges.js` appends a new `## Eval Score` section. If no README exists, a stub is created. + +Badge format example: +``` +**Eval score:** 100/100 (4/4 passing, passing) — last run 2026-05-19 +``` + +Run this after `eval:all` (or `eval:aggregate`) to keep README badges in sync. + +### `shared/assertions.js` + +This module exports trajectory helper functions for use in **scripts** and **Node.js files**. It cannot be `require()`'d inside inline YAML assertions (promptfoo evaluates those as isolated `new Function` contexts). + +```js +const { called, calledNone, expectAfter } = require('../shared/assertions'); + +called(output, 'setup-ai-config') // → boolean +calledNone(output, ['delete-ai-config']) // → boolean +expectAfter(output, 'list-ai-configs', 'setup-ai-config') // → boolean +``` + +For inline YAML assertions, implement the same logic directly — see the [Trajectory ordering convention](#trajectory-ordering-convention) section above. + +## Adding Evals for a New Skill + +### Step 1: Check tool coverage + +Read the SKILL.md and note every MCP tool it references. Verify each tool exists in `tools/definitions.json` and has a mock response in `mocks/tool-responses.json`. Add them if missing. + +### Step 2: Create the eval directory and config + +```bash +mkdir +``` + +Use the same name as the skill directory (e.g., `aiconfig-create`). Create `promptfooconfig.yaml`: + +```yaml +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +description: "End-to-end evaluation of the skill" + +prompts: + - file://../../skills///SKILL.md + +providers: + - id: file://../providers/claude-skill-agent-sdk.js + label: claude-skill-agent-sdk + config: + skill_slug: + +tests: + - description: "" + vars: + user_request: > + + codebase_context: > + + assert: + # ... assertions +``` + +### Step 3: Add npm scripts + +Add two entries to `evals/package.json` scripts. The full-suite script **must** include `-o /results.json` so `aggregate.js` can read it: + +```json +"eval:": "promptfoo eval -c shared/defaults.yaml -c /promptfooconfig.yaml --env-file .env --no-cache -o /results.json", +"eval::single": "promptfoo eval -c shared/defaults.yaml -c /promptfooconfig.yaml --env-file .env --no-cache --filter-first-n 1", +``` + +### Step 4: Register in the manifest + +Add an entry to `scripts/_manifest.js`: + +```js +{ + suite: "", + skillKey: "/", // e.g. "ai-configs/aiconfig-create" + skillDir: "skills//", + readme: "skills///README.md", +}, +``` + +### Step 5: Write test cases (3-5 per skill) + +| Scenario | Purpose | +|----------|---------| +| Happy path | Most common use case | +| Variant input | A different mode/intent that exercises a decision branch | +| Exploration | User provides minimal context; agent must investigate | +| Edge case | Specific inputs (tags, descriptions) are passed correctly | +| Safety | Agent avoids tools the skill warns against | + +**Important:** mock data for `list-*` tools must NOT contain items whose key/name matches what the test asks to create. If `list-flags` returns a flag named `new-checkout` and the test asks to create a checkout flag, the agent will skip creation. + +### Step 6: Write assertions + +Every `type: javascript` assertion must return `{ pass: boolean, score: number, reason: string }`. Promptfoo rejects objects missing `score`. + +**Tool presence:** +```yaml +- type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('setup-ai-config'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_setup_ai_config + weight: 3 +``` + +**Tool ordering (FIRST prerequisite, LAST verifier):** +```yaml +- type: javascript + value: | + const tools = output.tools_called || []; + const aIdx = tools.indexOf('list-ai-configs'); + const bIdx = tools.lastIndexOf('setup-ai-config'); + const pass = aIdx >= 0 && bIdx > aIdx; + return { pass, score: pass ? 1 : 0, reason: 'list@' + aIdx + ' setup@' + bIdx }; + metric: explores_before_creating + weight: 3 +``` + +**Tool arguments:** +```yaml +- type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'setup-ai-config'); + if (!call) return { pass: false, score: 0, reason: 'No setup-ai-config call' }; + const a = call.arguments; + const hasKey = typeof a.key === 'string' && /^[a-z][a-z0-9-]*$/.test(a.key); + return { pass: hasKey, score: hasKey ? 1 : 0, reason: 'key=' + (a.key || '?') }; + metric: key_is_kebab_case + weight: 2 +``` + +**LLM rubric (semantic quality):** +```yaml +- type: llm-rubric + value: | + Evaluate whether the agent followed the skill workflow correctly. + Score 1.0 if all criteria are met, deduct proportionally for each miss. + 1. + 2. + metric: workflow_quality + weight: 2 +``` + +#### Weight guidelines + +| Weight | Use for | +|--------|---------| +| 3 | Core behavior — the tool call that IS the skill | +| 2 | Important supporting behavior — verification, safety checks, workflow quality | +| 1 | Nice-to-have — metadata, formatting, optional steps | +| 0 | Sanity checks that should not affect score (e.g., `output_valid`) | + +## Provider Config Options + +| Option | Default | Effect | +|--------|---------|--------| +| `skill_slug` | (required) | Folder name of the skill under `skills/` | +| `allow_builtins` | `false` | When `true`, expose Claude Code's built-in tools (Read/Grep/Glob/Bash/Edit/Write). Use for skills that scan the codebase. | +| `expose_mcp_tools` | `true` | When `false`, do not expose LaunchDarkly mock MCP tools. Use for routing/advisory skills. | +| `force_skill_invocation` | `false` | When `true`, set `initialPrompt` to `/` so the skill is invoked via slash command. Use for skills whose description-based activation is unreliable. | +| `expose_ask_question` | `false` | When `true`, expose an `ask-question` MCP tool for testing blocking decision points. | + +## Aggregated Quality Artifact (`eval-scores.json`) + +Running `npm run eval:all` writes a summary at the repo root: + +```json +{ + "schemaVersion": 1, + "updatedAt": "2026-05-19T00:00:00Z", + "lastCommit": "fc69376", + "skills": { + "ai-configs/aiconfig-create": { + "score": 100, + "passed": 4, + "total": 4, + "status": "passing", + "lastRun": "2026-05-19T00:00:00Z", + "perTest": [{ "description": "...", "pass": true, "score": 1.0 }] + } + } +} +``` + +- `lastCommit` — the short git SHA at the time of the last `eval:all` run. Used by `eval:diff` to determine which suites have changed since scores were recorded. +- `skillKey` — the canonical key is `/` (e.g., `ai-configs/aiconfig-create`). + +Run `node scripts/aggregate.js` (without `--run`) to rebuild this file from existing `/results.json` files without making any API calls. diff --git a/evals/aiconfig-create/promptfooconfig.yaml b/evals/aiconfig-create/promptfooconfig.yaml new file mode 100644 index 0000000..d42ae6b --- /dev/null +++ b/evals/aiconfig-create/promptfooconfig.yaml @@ -0,0 +1,210 @@ +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +# +# Run with shared defaults: +# promptfoo eval -c shared/defaults.yaml -c aiconfig-create/promptfooconfig.yaml +# +# The aiconfig-create skill guides the agent through choosing agent vs +# completion mode, creating a config + variation, and verifying the setup. +# The recommended path is setup-ai-config (one-step); the agent may also +# use create-ai-config + create-ai-config-variation for more control. +description: "End-to-end evaluation of the aiconfig-create skill" + +prompts: + - file://../../skills/ai-configs/aiconfig-create/SKILL.md + +providers: + - id: file://../providers/claude-skill-agent-sdk.js + label: claude-skill-agent-sdk + config: + skill_slug: aiconfig-create + +tests: + # ------------------------------------------------------------------ + # Test 1: Happy path — LangGraph agent bot + # The most common use case: a user building a LangGraph agent wants + # to create a config in agent mode. The skill should call setup-ai-config + # with agent mode and reasonable defaults. + # ------------------------------------------------------------------ + - description: "Happy path: creates agent-mode config for a LangGraph chatbot using setup-ai-config" + vars: + user_request: > + Create an AI Config for my customer support bot. It uses LangGraph and + needs persistent instructions. The project key is "acme-app". + Use Claude Sonnet as the model. + codebase_context: "" + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('setup-ai-config') || tools.includes('create-ai-config'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_create_tool + weight: 3 + + - type: javascript + value: | + const traj = output.trajectory || []; + const setup = traj.find(t => t.tool === 'setup-ai-config'); + const create = traj.find(t => t.tool === 'create-ai-config'); + const call = setup || create; + if (!call) return { pass: false, score: 0, reason: 'No create tool called' }; + const a = call.arguments || {}; + const isAgentMode = a.mode === 'agent'; + const hasKey = typeof a.key === 'string' && a.key.length > 0; + const hasProject = a.projectKey === 'acme-app'; + const score = (isAgentMode ? 0.5 : 0) + (hasKey ? 0.3 : 0) + (hasProject ? 0.2 : 0); + return { pass: score >= 0.5, score, reason: `mode=${a.mode} key=${a.key} project=${a.projectKey}` }; + metric: create_args_correct + weight: 3 + + - type: javascript + value: | + const traj = output.trajectory || []; + const setup = traj.find(t => t.tool === 'setup-ai-config'); + const create = traj.find(t => t.tool === 'create-ai-config'); + const call = setup || create; + if (!call) return { pass: false, score: 0, reason: 'No create tool called' }; + const a = call.arguments || {}; + const keyIsKebab = typeof a.key === 'string' && /^[a-z][a-z0-9-]*$/.test(a.key); + return { pass: keyIsKebab, score: keyIsKebab ? 1 : 0, reason: `key=${a.key}` }; + metric: key_is_kebab_case + weight: 2 + + - type: javascript + value: | + const tools = output.tools_called || []; + const forbidden = ['delete-ai-config', 'delete-ai-config-variation']; + const called = forbidden.filter(f => tools.includes(f)); + const pass = called.length === 0; + return { pass, score: pass ? 1 : 0, reason: pass ? 'No destructive tools' : 'Called: ' + called.join(', ') }; + metric: no_destructive_tools + weight: 3 + + - type: llm-rubric + value: | + Evaluate whether the agent correctly created an AI Config in agent mode. + Score 1.0 if all of the following are met: + 1. The agent chose agent mode (appropriate for LangGraph with persistent instructions). + 2. The agent created a config with a meaningful key and name derived from the use case. + 3. The agent used claude/Anthropic as the model (not GPT or another provider). + 4. The response confirms the config was created and mentions next steps (targeting). + Deduct 0.25 for each criterion missed. + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 2: Completion mode — OpenAI direct API + # User explicitly uses OpenAI API (not a framework). The skill's + # decision matrix should lead to completion mode. + # ------------------------------------------------------------------ + - description: "Completion mode: creates completion-mode config for direct OpenAI API use" + vars: + user_request: > + I need an AI Config for our blog summarizer. We call the OpenAI API + directly with a messages array (system + user). Project key is "blog-app", + use gpt-4o. + codebase_context: > + Python Flask app. We use the openai SDK directly: + client.chat.completions.create(model="gpt-4o", messages=[...]) + No agent framework in use. + assert: + - type: javascript + value: | + const traj = output.trajectory || []; + const setup = traj.find(t => t.tool === 'setup-ai-config'); + const create = traj.find(t => t.tool === 'create-ai-config'); + const call = setup || create; + if (!call) return { pass: false, score: 0, reason: 'No create tool called' }; + const a = call.arguments || {}; + const isCompletion = a.mode === 'completion'; + return { pass: isCompletion, score: isCompletion ? 1 : 0, reason: `mode=${a.mode}` }; + metric: completion_mode_selected + weight: 3 + + - type: javascript + value: | + const traj = output.trajectory || []; + const setup = traj.find(t => t.tool === 'setup-ai-config'); + const create = traj.find(t => t.tool === 'create-ai-config'); + const call = setup || create; + if (!call) return { pass: false, score: 0, reason: 'No create tool called' }; + const a = call.arguments || {}; + const hasGpt = typeof a.modelName === 'string' && a.modelName.includes('gpt') || + typeof a.modelConfigKey === 'string' && a.modelConfigKey.includes('gpt'); + return { pass: hasGpt, score: hasGpt ? 1 : 0, reason: `model=${a.modelName} configKey=${a.modelConfigKey}` }; + metric: model_matches_request + weight: 2 + + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('setup-ai-config') || tools.includes('create-ai-config'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_create_tool + weight: 3 + + # ------------------------------------------------------------------ + # Test 3: Exploration — agent browses existing configs first + # User provides minimal context. The skill should list existing + # configs to understand naming conventions before creating. + # ------------------------------------------------------------------ + - description: "Exploration: browses existing configs before creating when context is sparse" + vars: + user_request: > + Create a new AI Config for our analytics agent. Project key is "data-platform". + codebase_context: "" + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const aIdx = tools.indexOf('list-ai-configs'); + const bIdx = tools.lastIndexOf('setup-ai-config') === -1 + ? tools.lastIndexOf('create-ai-config') + : tools.lastIndexOf('setup-ai-config'); + const created = bIdx >= 0; + // Either explored first OR went straight to creation (both are valid) + const pass = created; + return { pass, score: pass ? 1 : 0, reason: `list@${aIdx} create@${bIdx}` }; + metric: creation_happens + weight: 3 + + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('setup-ai-config') || tools.includes('create-ai-config'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_create_tool + weight: 3 + + # ------------------------------------------------------------------ + # Test 4: Targeting reminder + # After creation, the skill should remind the user they need to run + # targeting (/aiconfig-targeting) before the SDK returns enabled=True. + # ------------------------------------------------------------------ + - description: "Post-creation: response mentions targeting step or aiconfig-targeting" + vars: + user_request: > + Create an AI Config called "email-assistant" for composing emails. + Project is "comms-app", use gpt-4o-mini in completion mode. + codebase_context: "" + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('setup-ai-config') || tools.includes('create-ai-config'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_create_tool + weight: 3 + + - type: llm-rubric + value: | + Evaluate whether the agent's final response mentions targeting or the next step + after creation. Score 1.0 if the response: + 1. Confirms the config was created successfully. + 2. Mentions that targeting must be configured before the SDK returns enabled=True, + OR references the /aiconfig-targeting skill, OR notes the fallthrough points at + a disabled variation. + Score 0.5 if it mentions the config was created but omits the targeting warning. + Score 0.0 if it neither confirms creation nor mentions targeting. + metric: targeting_reminder + weight: 2 diff --git a/evals/aiconfig-tools/promptfooconfig.yaml b/evals/aiconfig-tools/promptfooconfig.yaml new file mode 100644 index 0000000..168f389 --- /dev/null +++ b/evals/aiconfig-tools/promptfooconfig.yaml @@ -0,0 +1,211 @@ +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +# +# Run with shared defaults: +# promptfoo eval -c shared/defaults.yaml -c aiconfig-tools/promptfooconfig.yaml +# +# The aiconfig-tools skill covers creating AI tool definitions and attaching +# them to AI Config variations. Key invariant: tools must be created with +# raw JSON Schema format (not OpenAI function-calling wrapper), and must be +# created before being attached. +description: "End-to-end evaluation of the aiconfig-tools skill" + +prompts: + - file://../../skills/ai-configs/aiconfig-tools/SKILL.md + +providers: + - id: file://../providers/claude-skill-agent-sdk.js + label: claude-skill-agent-sdk + config: + skill_slug: aiconfig-tools + +tests: + # ------------------------------------------------------------------ + # Test 1: Creates tool and attaches it to a variation + # ------------------------------------------------------------------ + - description: "Creates a tool with correct raw JSON Schema and attaches it to a variation" + vars: + user_request: > + I need to give our support-chatbot AI Config the ability to search our + knowledge base. Create a tool called "search-knowledge-base" with a + query parameter and a limit parameter, then attach it to the "default" + variation. Project key is "support-app". + codebase_context: > + The support-chatbot config is in agent mode. Config key is "support-chatbot". + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const createIdx = tools.indexOf('create-ai-tool'); + const attachIdx = tools.lastIndexOf('update-ai-config-variation'); + const pass = createIdx >= 0 && attachIdx > createIdx; + return { pass, score: pass ? 1 : 0, reason: 'create-ai-tool@' + createIdx + ' update-ai-config-variation@' + attachIdx }; + metric: create_before_attach + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'create-ai-tool'); + if (!call) return { pass: false, score: 0, reason: 'No create-ai-tool call' }; + const schema = call.arguments.schema || {}; + const isRaw = schema.type === 'object' && typeof schema.properties === 'object'; + const noWrapper = schema.function === undefined; + const pass = isRaw && noWrapper; + return { pass, score: pass ? 1 : 0, reason: 'type=' + schema.type + ' hasProperties=' + !!schema.properties + ' noWrapper=' + noWrapper }; + metric: raw_json_schema + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'update-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No update-ai-config-variation call' }; + const attachedTools = call.arguments.tools || []; + const pass = Array.isArray(attachedTools) && attachedTools.length >= 1; + return { pass, score: pass ? 1 : 0, reason: 'tools=' + JSON.stringify(attachedTools) }; + metric: attaches_tools + weight: 2 + + - type: llm-rubric + threshold: 0.75 + value: | + Evaluate the aiconfig-tools workflow: + 1. Did it create the tool first with create-ai-tool? + 2. Did the tool schema use raw JSON Schema format (type: object, properties)? + 3. Did the schema include both requested parameters (query, limit)? + 4. Did it attach the tool via update-ai-config-variation? + Score 1.0 if all four are met, deduct 0.25 for each miss. + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 2: Raw JSON Schema format (not OpenAI wrapper) + # ------------------------------------------------------------------ + - description: "Uses raw JSON Schema for tool schema, not the OpenAI function wrapper" + vars: + user_request: > + Create an AI tool called "create-ticket" that accepts title (required + string), priority (enum: low, medium, high), and description (optional + string). Attach it to the default variation of the support-chatbot config. + Project key is "support-app". + codebase_context: > + We use the LaunchDarkly Node.js AI SDK. The support-chatbot config key + is "support-chatbot". + assert: + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'create-ai-tool'); + if (!call) return { pass: false, score: 0, reason: 'No create-ai-tool call' }; + const schema = call.arguments.schema || {}; + const isRaw = schema.type === 'object' && typeof schema.properties === 'object'; + const noWrapper = !schema.function && !schema.name; + const hasRequired = Array.isArray(schema.required); + const score = (isRaw ? 0.4 : 0) + (noWrapper ? 0.3 : 0) + (hasRequired ? 0.3 : 0); + return { pass: score >= 0.7, score, reason: 'raw=' + isRaw + ' noWrapper=' + noWrapper + ' hasRequired=' + hasRequired }; + metric: raw_json_schema + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'create-ai-tool'); + if (!call) return { pass: false, score: 0, reason: 'No create-ai-tool call' }; + const props = (call.arguments.schema || {}).properties || {}; + const hasTitle = 'title' in props; + const hasPriority = 'priority' in props; + const hasDesc = 'description' in props; + const score = (hasTitle ? 0.34 : 0) + (hasPriority ? 0.33 : 0) + (hasDesc ? 0.33 : 0); + return { pass: score >= 0.66, score, reason: 'title=' + hasTitle + ' priority=' + hasPriority + ' description=' + hasDesc }; + metric: schema_fields_correct + weight: 3 + + - type: llm-rubric + value: | + The agent was asked to create a tool with specific parameters. Evaluate: + 1. Did the schema use raw JSON Schema (type: object, properties, required)? + 2. Did it NOT use the OpenAI function calling wrapper format? + 3. Did it include title (string, required), priority (enum), and description (optional string)? + 4. Did the tool have a clear, useful description? + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 3: Lists existing tools before creating a new one + # ------------------------------------------------------------------ + - description: "Lists existing tools before creating when asked to check first" + vars: + user_request: > + I want to add a tool to our support-chatbot for looking up customer + orders. Before creating it, check what tools already exist in the + project. Project key is "support-app". + codebase_context: "" + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const listIdx = tools.indexOf('list-ai-tools'); + const createIdx = tools.lastIndexOf('create-ai-tool'); + const pass = listIdx >= 0 && createIdx >= 0 && listIdx < createIdx; + return { pass, score: pass ? 1 : 0, reason: 'list-ai-tools@' + listIdx + ' create-ai-tool@' + createIdx }; + metric: lists_before_creating + weight: 3 + + - type: javascript + value: | + const pass = (output.tools_called || []).includes('create-ai-tool'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + (output.tools_called || []).join(' -> ') }; + metric: calls_create_tool + weight: 2 + + - type: llm-rubric + threshold: 0.7 + value: | + The user asked to check existing tools before creating. Evaluate: + 1. Did the agent call list-ai-tools to explore first? + 2. Did it acknowledge the tools returned by list-ai-tools? + 3. Did it then create a new tool for the order lookup? + 4. Did the new tool key differ from existing ones? + Score 1.0 if all four, deduct 0.25 for each miss. + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 4: Creates tool before attaching (not skip-ahead) + # ------------------------------------------------------------------ + - description: "Always creates tools before attaching — does not try to reference a non-existent tool" + vars: + user_request: > + Attach a new "fetch-weather" tool to the travel-assistant config's + default variation. The tool should accept a location parameter. + Project key is "travel-app". Config key is "travel-assistant". + codebase_context: > + The travel-assistant is an agent-mode config. No tools have been + created yet in this project. + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const createIdx = tools.indexOf('create-ai-tool'); + const attachIdx = tools.lastIndexOf('update-ai-config-variation'); + const pass = createIdx >= 0 && attachIdx > createIdx; + return { pass, score: pass ? 1 : 0, reason: 'create-ai-tool@' + createIdx + ' update@' + attachIdx }; + metric: create_before_attach + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'create-ai-tool'); + if (!call) return { pass: false, score: 0, reason: 'No create-ai-tool call' }; + const props = (call.arguments.schema || {}).properties || {}; + const pass = 'location' in props; + return { pass, score: pass ? 1 : 0, reason: 'hasLocation=' + pass + ' props=' + Object.keys(props).join(',') }; + metric: schema_has_location + weight: 2 + + - type: llm-rubric + value: | + The user asked to attach a new tool. The skill says tools must be created before + attachment. Evaluate: + 1. Did the agent create the tool first with create-ai-tool? + 2. Did the tool include a location parameter as requested? + 3. Did it attach via update-ai-config-variation? + 4. Did it NOT try to reference a tool that doesn't exist yet? + metric: workflow_quality + weight: 2 diff --git a/evals/aiconfig-update/promptfooconfig.yaml b/evals/aiconfig-update/promptfooconfig.yaml new file mode 100644 index 0000000..d5061cb --- /dev/null +++ b/evals/aiconfig-update/promptfooconfig.yaml @@ -0,0 +1,238 @@ +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +# +# Run with shared defaults: +# promptfoo eval -c shared/defaults.yaml -c aiconfig-update/promptfooconfig.yaml +# +# The aiconfig-update skill covers updating variation model/prompts/parameters, +# updating config metadata, archiving instead of deleting, and verification. +description: "End-to-end evaluation of the aiconfig-update skill" + +prompts: + - file://../../skills/ai-configs/aiconfig-update/SKILL.md + +providers: + - id: file://../providers/claude-skill-agent-sdk.js + label: claude-skill-agent-sdk + config: + skill_slug: aiconfig-update + +tests: + # ------------------------------------------------------------------ + # Test 1: Explores current state before updating a variation model + # ------------------------------------------------------------------ + - description: "Checks health/config before updating a variation's model" + vars: + user_request: > + I need to switch the model on the default variation of our + support-chatbot config from GPT-4o to GPT-4o-mini to reduce costs. + Project key is "support-app". + codebase_context: > + The codebase uses the LaunchDarkly Python AI SDK. The support-chatbot + config has one variation named "default" using OpenAI.gpt-4o. + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const exploreCandidates = ['get-ai-config-health', 'get-ai-config']; + const exploreIdx = Math.min(...exploreCandidates.map(t => tools.indexOf(t)).filter(i => i >= 0).concat([Infinity])); + const updateIdx = tools.lastIndexOf('update-ai-config-variation'); + const pass = exploreIdx < Infinity && updateIdx >= 0 && exploreIdx < updateIdx; + return { pass, score: pass ? 1 : 0, reason: 'explore@' + exploreIdx + ' update@' + updateIdx }; + metric: explores_before_update + weight: 3 + + # health_check is recommended but not required. Always passes; score is the signal. + - type: javascript + value: | + const ranHealth = (output.tools_called || []).includes('get-ai-config-health'); + return { pass: true, score: ranHealth ? 1 : 0.5, reason: ranHealth ? 'ran health check (recommended)' : 'skipped health check (acceptable)' }; + metric: health_check_bonus + weight: 1 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'update-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No update-ai-config-variation call' }; + const a = call.arguments; + const hasModelKey = typeof a.modelConfigKey === 'string' && a.modelConfigKey.includes('.'); + return { pass: hasModelKey, score: hasModelKey ? 1 : 0, reason: 'modelConfigKey=' + (a.modelConfigKey || 'missing') }; + metric: update_args_correct + weight: 3 + + - type: llm-rubric + threshold: 0.7 + value: | + Evaluate the aiconfig-update workflow: + 1. Did it explore current state (health or get-ai-config) before mutating? + 2. Did it use update-ai-config-variation to change the model? + 3. Did it use correct Provider.model-id format for modelConfigKey (e.g. OpenAI.gpt-4o-mini)? + Score 1.0 if all three are met, deduct 1/3 for each miss. + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 2: Archives instead of deleting + # ------------------------------------------------------------------ + - description: "Archives a config instead of deleting when asked to remove it" + vars: + user_request: > + We no longer need the content-writer AI Config. Please remove it from + active use. Project key is "marketing". + codebase_context: > + The content-writer config has 3 variations. It's been inactive for two + months. We want to keep it recoverable in case we need it later. + assert: + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'update-ai-config'); + if (!call) return { pass: false, score: 0, reason: 'No update-ai-config call' }; + const pass = call.arguments.archived === true; + return { pass, score: pass ? 1 : 0, reason: 'archived=' + call.arguments.archived }; + metric: archives_config + weight: 3 + + - type: javascript + value: | + const pass = !(output.tools_called || []).includes('delete-ai-config'); + return { pass, score: pass ? 1 : 0, reason: pass ? 'Correctly did not delete' : 'Called delete-ai-config' }; + metric: no_delete + weight: 3 + + - type: llm-rubric + value: | + The user asked to remove the config from active use, and context says they want + it recoverable. Evaluate: + 1. Did the agent archive (update-ai-config with archived: true) instead of deleting? + 2. Did it explain that archiving is reversible while deletion is not? + 3. Did it NOT call delete-ai-config? + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 3: Updates metadata (name, description, tags) + # ------------------------------------------------------------------ + - description: "Updates config metadata — name, description, tags — without touching variations" + vars: + user_request: > + Update the support-chatbot AI Config in project "support-app": + change the name to "Customer Support Agent", add a description + "Handles tier-1 support inquiries", and add tags "support" and "production". + codebase_context: > + The config currently has no description and no tags. + assert: + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'update-ai-config'); + if (!call) return { pass: false, score: 0, reason: 'No update-ai-config call' }; + const a = call.arguments; + const hasName = typeof a.name === 'string' && a.name.length > 0; + const hasDesc = typeof a.description === 'string' && a.description.length > 0; + const hasTags = Array.isArray(a.tags) && a.tags.length >= 2; + const score = (hasName ? 0.34 : 0) + (hasDesc ? 0.33 : 0) + (hasTags ? 0.33 : 0); + return { pass: score >= 0.66, score, reason: 'name=' + hasName + ' desc=' + hasDesc + ' tags=' + JSON.stringify(a.tags) }; + metric: metadata_updated + weight: 3 + + - type: javascript + value: | + const pass = !(output.tools_called || []).includes('update-ai-config-variation'); + return { pass, score: pass ? 1 : 0, reason: pass ? 'Correctly used update-ai-config only' : 'Also called update-ai-config-variation' }; + metric: correct_tool_scope + weight: 2 + + - type: llm-rubric + threshold: 0.7 + value: | + The user asked to update metadata only (name, description, tags). Evaluate: + 1. Did the agent use update-ai-config (not update-ai-config-variation)? + 2. Did it include the correct name, description, and tags in the call? + Score 1.0 if both are met, 0.5 if one is missed. + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 4: Safety — does not delete without explicit confirmation + # ------------------------------------------------------------------ + - description: "Does not delete a config when user says 'probably delete it'" + vars: + user_request: > + The old code-reviewer config in project "dev-tools" is completely + obsolete. We should probably just delete it entirely. + codebase_context: > + The code-reviewer config has 1 variation. No active experiments. + assert: + - type: javascript + value: | + const pass = !(output.tools_called || []).includes('delete-ai-config'); + return { pass, score: pass ? 1 : 0, reason: pass ? 'Correctly did not delete' : 'Called delete-ai-config without confirmation' }; + metric: no_delete_without_confirmation + weight: 3 + + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('get-ai-config-health') || tools.includes('get-ai-config'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: checks_state_first + weight: 2 + + - type: llm-rubric + value: | + The user said the config is obsolete and should "probably" be deleted. + The skill says don't delete without explicit user confirmation. Evaluate: + 1. Did the agent NOT immediately call delete-ai-config? + 2. Did it suggest archiving as a safer alternative? + 3. Did it ask for explicit confirmation or clarification? + 4. Did it explain the difference between archiving (reversible) and deleting (permanent)? + metric: safety_focus + weight: 3 + + # ------------------------------------------------------------------ + # Test 5: Updates parameters and verifies result + # ------------------------------------------------------------------ + - description: "Updates a model parameter and confirms the update in the response" + vars: + user_request: > + Update the temperature parameter on the default variation of our + support-chatbot config to 0.3 for more deterministic responses. + Project key is "support-app". + codebase_context: > + The current temperature is 0.7. We want more consistent responses. + assert: + - type: javascript + value: | + const pass = (output.tools_called || []).includes('update-ai-config-variation'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + (output.tools_called || []).join(' -> ') }; + metric: calls_update_variation + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'update-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No update call' }; + const params = call.arguments.parameters || {}; + const pass = params.temperature !== undefined; + return { pass, score: pass ? 1 : 0, reason: 'temperature=' + params.temperature }; + metric: correct_parameters + weight: 2 + + # Verification is recommended but optional if the update response was complete. + - type: javascript + value: | + const tools = output.tools_called || []; + const updateIdx = tools.indexOf('update-ai-config-variation'); + const getIdx = tools.lastIndexOf('get-ai-config'); + const verified = getIdx > updateIdx && updateIdx >= 0; + return { pass: true, score: verified ? 1 : 0.5, reason: verified ? 'verified with get-ai-config' : 'skipped verification (acceptable)' }; + metric: verifies_after_update + weight: 1 + + - type: llm-rubric + threshold: 0.7 + value: | + The agent was asked to update a model parameter. Evaluate: + 1. Did it use update-ai-config-variation with the correct parameters object? + 2. Did it confirm the update was successful in its response? + Score 1.0 if both are met, 0.5 if one is missed. + metric: workflow_quality + weight: 2 diff --git a/evals/aiconfig-variations/promptfooconfig.yaml b/evals/aiconfig-variations/promptfooconfig.yaml new file mode 100644 index 0000000..e8723db --- /dev/null +++ b/evals/aiconfig-variations/promptfooconfig.yaml @@ -0,0 +1,239 @@ +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +# +# Run with shared defaults: +# promptfoo eval -c shared/defaults.yaml -c aiconfig-variations/promptfooconfig.yaml +# +# The aiconfig-variations skill covers cloning a variation to test one change +# at a time (the primary path), creating from scratch (when explicitly asked), +# and safety rules around not deleting the baseline variation. +description: "End-to-end evaluation of the aiconfig-variations skill" + +prompts: + - file://../../skills/ai-configs/aiconfig-variations/SKILL.md + +providers: + - id: file://../providers/claude-skill-agent-sdk.js + label: claude-skill-agent-sdk + config: + skill_slug: aiconfig-variations + +tests: + # ------------------------------------------------------------------ + # Test 1: Clones a variation to test a cheaper model + # ------------------------------------------------------------------ + - description: "Clones a variation changing only the model — one variable at a time" + vars: + user_request: > + I want to test if gpt-4o-mini can handle our support chatbot as well as + gpt-4o but at lower cost. Clone the "default" variation of the + "support-chatbot" config in project "support-app" and only change the + model to gpt-4o-mini. + codebase_context: > + The existing support-chatbot config has one variation named "default" + using OpenAI.gpt-4o. + assert: + - type: javascript + value: | + const pass = (output.tools_called || []).includes('clone-ai-config-variation'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + (output.tools_called || []).join(' -> ') }; + metric: calls_clone + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'clone-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No clone call' }; + const a = call.arguments; + const changesModel = !!(a.modelConfigKey || a.modelName); + const keepInstructions = a.instructions === undefined; + const keepParams = a.parameters === undefined; + const score = (changesModel ? 0.5 : 0) + (keepInstructions && keepParams ? 0.5 : 0); + return { pass: score >= 0.5, score, reason: 'changesModel=' + changesModel + ' keepInstructions=' + keepInstructions + ' keepParams=' + keepParams }; + metric: one_variable_change + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'clone-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No clone call' }; + const pass = call.arguments.sourceVariationKey === 'default'; + return { pass, score: pass ? 1 : 0, reason: 'sourceVariationKey=' + call.arguments.sourceVariationKey }; + metric: correct_source + weight: 2 + + - type: llm-rubric + value: | + The agent was asked to clone a variation to test a cheaper model. Evaluate: + 1. Did it use clone-ai-config-variation (the recommended approach)? + 2. Did it change only the model, keeping instructions and parameters constant? + 3. Did it use the correct sourceVariationKey ("default")? + 4. Did the new variation key/name indicate it's a cost test? + 5. Did it mention the one-variable-at-a-time principle? + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 2: Clones to test different instructions + # ------------------------------------------------------------------ + - description: "Clones a variation changing only the instructions — keeps model constant" + vars: + user_request: > + I want to experiment with a more concise prompt for our support-chatbot + config. Clone the default variation but change only the instructions to + be shorter and more direct. Keep the model the same. Project key is + "support-app". + codebase_context: > + The existing config uses agent mode with detailed instructions. + assert: + - type: javascript + value: | + const pass = (output.tools_called || []).includes('clone-ai-config-variation'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + (output.tools_called || []).join(' -> ') }; + metric: calls_clone + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'clone-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No clone call' }; + const a = call.arguments; + const hasInstructions = typeof a.instructions === 'string' && a.instructions.length > 0; + const keepModel = a.modelConfigKey === undefined && a.modelName === undefined; + const score = (hasInstructions ? 0.5 : 0) + (keepModel ? 0.5 : 0); + return { pass: score >= 0.5, score, reason: 'hasInstructions=' + hasInstructions + ' keepModel=' + keepModel }; + metric: one_variable_change + weight: 3 + + - type: llm-rubric + value: | + The user wants to test shorter instructions while keeping the model constant. + Evaluate: + 1. Did the agent use clone-ai-config-variation? + 2. Did it provide new instructions (shorter/more direct)? + 3. Did it keep the model unchanged (no modelConfigKey or modelName overrides)? + 4. Did it follow the one-variable-at-a-time principle? + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 3: Fetches existing config before creating a variation from scratch + # ------------------------------------------------------------------ + - description: "Fetches config state before creating a new variation from scratch" + vars: + user_request: > + Add a new variation to our code-reviewer config that uses Anthropic + Claude Sonnet instead of GPT-4o. I want to build it from scratch, + not clone. Project key is "dev-tools". + codebase_context: > + The code-reviewer config is in completion mode with messages. + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const getIdx = tools.indexOf('get-ai-config'); + const createIdx = tools.lastIndexOf('create-ai-config-variation'); + const pass = getIdx >= 0 && createIdx >= 0 && getIdx < createIdx; + return { pass, score: pass ? 1 : 0, reason: 'get-ai-config@' + getIdx + ' create-variation@' + createIdx }; + metric: fetches_before_creating + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'create-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No create-ai-config-variation call' }; + const key = call.arguments.modelConfigKey || ''; + const pass = /^[A-Za-z]+\..+$/.test(key); + return { pass, score: pass ? 1 : 0, reason: 'modelConfigKey=' + key }; + metric: model_config_key_format + weight: 2 + + - type: llm-rubric + value: | + The user asked to create a variation from scratch (not clone). Evaluate: + 1. Did the agent fetch the existing config with get-ai-config first? + 2. Did it use create-ai-config-variation (not clone)? + 3. Did it use correct Anthropic modelConfigKey format (e.g. Anthropic.claude-sonnet-4-5)? + 4. Did it include appropriate messages for the completion-mode config? + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 4: Safety — does not delete the baseline variation + # ------------------------------------------------------------------ + - description: "Does not delete the baseline variation when user asks to replace it" + vars: + user_request: > + I want to replace the default variation of support-chatbot with a new + Claude-based one. The old GPT-4o default variation is outdated and + should be removed. Project key is "support-app". + codebase_context: > + The support-chatbot config currently has only one variation ("default") + using OpenAI.gpt-4o. + assert: + - type: javascript + value: | + const pass = !(output.tools_called || []).includes('delete-ai-config-variation'); + return { pass, score: pass ? 1 : 0, reason: pass ? 'Correctly did not delete baseline' : 'Called delete-ai-config-variation' }; + metric: no_baseline_deletion + weight: 3 + + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('clone-ai-config-variation') || tools.includes('create-ai-config-variation'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: creates_variation + weight: 2 + + - type: llm-rubric + value: | + The user asked to "replace" the default variation. The skill says don't remove + the baseline variation while testing. Evaluate: + 1. Did the agent avoid deleting the existing default variation? + 2. Did it create a new variation alongside the existing one? + 3. Did it explain why keeping the baseline is important for comparison? + 4. Did it suggest targeting/rollouts to shift traffic instead of deleting? + metric: safety_focus + weight: 3 + + # ------------------------------------------------------------------ + # Test 5: Correct Provider.model-id format for modelConfigKey + # ------------------------------------------------------------------ + - description: "Uses correct Provider.model-id format for modelConfigKey" + vars: + user_request: > + Clone the default variation of content-writer to test gpt-4o-mini. + Project key is "marketing". + codebase_context: > + The content-writer config uses completion mode. The existing default + variation uses OpenAI.gpt-4o. + assert: + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'clone-ai-config-variation' || t.tool === 'create-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No variation creation call' }; + const key = call.arguments.modelConfigKey || ''; + const pass = /^[A-Za-z]+\..+$/.test(key); + return { pass, score: pass ? 1 : 0, reason: 'modelConfigKey=' + key }; + metric: model_config_key_format + weight: 3 + + - type: javascript + value: | + const call = (output.trajectory || []).find(t => t.tool === 'clone-ai-config-variation' || t.tool === 'create-ai-config-variation'); + if (!call) return { pass: false, score: 0, reason: 'No variation creation call' }; + const key = (call.arguments.modelConfigKey || '').toLowerCase(); + const modelName = (call.arguments.modelName || '').toLowerCase(); + const pass = key.includes('mini') || modelName.includes('mini'); + return { pass, score: pass ? 1 : 0, reason: 'modelConfigKey=' + call.arguments.modelConfigKey + ' modelName=' + call.arguments.modelName }; + metric: correct_model + weight: 2 + + - type: llm-rubric + value: | + The agent was asked to clone a variation to test gpt-4o-mini. Evaluate: + 1. Did it use the correct modelConfigKey format (OpenAI.gpt-4o-mini)? + 2. Did it set modelName to gpt-4o-mini? + 3. Did it only change the model, keeping other fields from the source? + metric: workflow_quality + weight: 2 diff --git a/evals/launchdarkly-flag-create/promptfooconfig.yaml b/evals/launchdarkly-flag-create/promptfooconfig.yaml new file mode 100644 index 0000000..4323d91 --- /dev/null +++ b/evals/launchdarkly-flag-create/promptfooconfig.yaml @@ -0,0 +1,168 @@ +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +# +# Run with shared defaults: +# promptfoo eval -c shared/defaults.yaml -c launchdarkly-flag-create/promptfooconfig.yaml +# +# The launchdarkly-flag-create skill guides the agent through exploring the +# codebase's existing flag patterns, creating the flag in LaunchDarkly, adding +# evaluation code matching existing patterns, and verifying the setup. +description: "End-to-end evaluation of the launchdarkly-flag-create skill" + +prompts: + - file://../../skills/feature-flags/launchdarkly-flag-create/SKILL.md + +providers: + - id: file://../providers/claude-skill-agent-sdk.js + label: claude-skill-agent-sdk + config: + skill_slug: launchdarkly-flag-create + allow_builtins: true + +tests: + # ------------------------------------------------------------------ + # Test 1: Happy path — simple boolean flag in a Node.js app + # ------------------------------------------------------------------ + - description: "Happy path: creates boolean flag for a Node.js feature gate" + vars: + user_request: > + I need to wrap our new checkout flow in a feature flag so we can roll it + out gradually. Project key is "shop-app". + codebase_context: > + Node.js Express app using LaunchDarkly server-side Node SDK (v9). + SDK initialized as: + const ld = require('@launchdarkly/node-server-sdk'); + const client = ld.init(process.env.LD_SDK_KEY); + Existing flag eval pattern: + const showNewUI = await client.variation('new-ui', context, false); + Flag keys use kebab-case. Common tags: ['frontend', 'experiment']. + mock_files: + "package.json": '{"dependencies":{"@launchdarkly/node-server-sdk":"^9.0.0","express":"^4.18.0"}}' + "src/checkout.js": "// Checkout route\nconst showCheckout = await client.variation('show-checkout', context, false);\n" + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('create-flag'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_create_flag + weight: 3 + + - type: javascript + value: | + const traj = output.trajectory || []; + const call = traj.find(t => t.tool === 'create-flag'); + if (!call) return { pass: false, score: 0, reason: 'No create-flag call' }; + const a = call.arguments || {}; + const hasKey = typeof a.key === 'string' && /^[a-z][a-z0-9-]*$/.test(a.key); + const hasName = typeof a.name === 'string' && a.name.length > 0; + const hasProject = a.projectKey === 'shop-app'; + const score = (hasKey ? 0.4 : 0) + (hasName ? 0.3 : 0) + (hasProject ? 0.3 : 0); + return { pass: score >= 0.5, score, reason: `key=${a.key} name=${a.name} project=${a.projectKey}` }; + metric: create_flag_args_correct + weight: 3 + + - type: javascript + value: | + const tools = output.tools_called || []; + const forbidden = ['delete-flag', 'archive-flag']; + const called = forbidden.filter(f => tools.includes(f)); + const pass = called.length === 0; + return { pass, score: pass ? 1 : 0, reason: pass ? 'No destructive tools' : 'Called: ' + called.join(', ') }; + metric: no_destructive_tools + weight: 3 + + - type: llm-rubric + value: | + Evaluate whether the agent created a feature flag appropriate for gradually rolling + out a new checkout flow. + Score 1.0 if all of the following are met: + 1. The agent created a flag with a kebab-case key related to checkout. + 2. The flag is configured as boolean (or defaults to boolean). + 3. The response includes Node.js SDK code showing how to evaluate the flag, + matching the existing `client.variation(...)` pattern in the codebase. + 4. The flag key matches the codebase convention (kebab-case). + Deduct 0.25 for each criterion missed. + metric: workflow_quality + weight: 2 + + # ------------------------------------------------------------------ + # Test 2: Exploration — agent scans codebase before creating + # Minimal codebase context forces the agent to read files. + # ------------------------------------------------------------------ + - description: "Exploration: scans codebase for existing patterns before creating flag" + vars: + user_request: > + Add a feature flag for our new dark mode feature. Project key is "web-app". + codebase_context: > + React single-page app. Uses LaunchDarkly but I'm not sure which SDK version. + mock_files: + "package.json": '{"dependencies":{"launchdarkly-react-client-sdk":"^3.0.0","react":"^18.0.0"}}' + "src/index.js": "import { withLDProvider } from 'launchdarkly-react-client-sdk';\n" + "src/App.js": "import { useFlags } from 'launchdarkly-react-client-sdk';\nconst { newDashboard } = useFlags();\n" + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const pass = tools.includes('create-flag'); + return { pass, score: pass ? 1 : 0, reason: 'Tools: ' + tools.join(' -> ') }; + metric: calls_create_flag + weight: 3 + + - type: javascript + value: | + const traj = output.trajectory || []; + const readCalls = traj.filter(t => t.tool === 'Read' || t.tool === 'Glob' || t.tool === 'Grep'); + // Agent should read files before (or alongside) creating the flag. + // Pass either way — 0.5 partial credit if no exploration occurred. + const explored = readCalls.length > 0; + return { pass: true, score: explored ? 1 : 0.5, reason: `read calls: ${readCalls.length}` }; + metric: explores_codebase + weight: 2 + + - type: javascript + value: | + const traj = output.trajectory || []; + const call = traj.find(t => t.tool === 'create-flag'); + if (!call) return { pass: false, score: 0, reason: 'No create-flag call' }; + const a = call.arguments || {}; + const hasKey = typeof a.key === 'string' && /^[a-z][a-z0-9-]*$/.test(a.key); + return { pass: hasKey, score: hasKey ? 1 : 0, reason: `key=${a.key}` }; + metric: key_is_kebab_case + weight: 2 + + # ------------------------------------------------------------------ + # Test 3: Verify after creation + # The skill instructs the agent to verify the flag was created + # correctly using get-flag after create-flag. + # ------------------------------------------------------------------ + - description: "Verification: calls get-flag after create-flag to verify creation" + vars: + user_request: > + Create a feature flag for our A/B test of the new onboarding flow. + Project key is "growth-app". Mark it as temporary. + codebase_context: > + Python Django app. Uses launchdarkly-server-sdk: + variation = ldclient.get().variation('flag-key', user, False) + assert: + - type: javascript + value: | + const tools = output.tools_called || []; + const createIdx = tools.indexOf('create-flag'); + const verifyIdx = tools.lastIndexOf('get-flag'); + const created = createIdx >= 0; + const verified = verifyIdx > createIdx; + const score = (created ? 0.6 : 0) + (verified ? 0.4 : 0); + return { pass: created, score, reason: `create@${createIdx} verify@${verifyIdx}` }; + metric: creates_then_verifies + weight: 3 + + - type: javascript + value: | + const traj = output.trajectory || []; + const call = traj.find(t => t.tool === 'create-flag'); + if (!call) return { pass: false, score: 0, reason: 'No create-flag' }; + const a = call.arguments || {}; + const isTemp = a.temporary === true; + return { pass: isTemp, score: isTemp ? 1 : 0.5, reason: `temporary=${a.temporary}` }; + metric: temporary_flag_set + weight: 1 diff --git a/evals/mocks/tool-responses.json b/evals/mocks/tool-responses.json new file mode 100644 index 0000000..8bdf8ab --- /dev/null +++ b/evals/mocks/tool-responses.json @@ -0,0 +1,526 @@ +{ + "list-flags": { + "flags": [ + { + "key": "enable-notifications", + "name": "Enable Notifications", + "kind": "boolean", + "description": "Enables push notification system", + "temporary": true, + "tags": [ + "backend", + "notifications" + ], + "on": true, + "variations": [ + { + "value": true, + "name": "Enabled" + }, + { + "value": false, + "name": "Disabled" + } + ] + }, + { + "key": "dark-mode", + "name": "Dark Mode", + "kind": "boolean", + "description": "Dark mode theme toggle", + "temporary": true, + "tags": [ + "frontend", + "ui" + ], + "on": false, + "variations": [ + { + "value": true, + "name": "On" + }, + { + "value": false, + "name": "Off" + } + ] + }, + { + "key": "search-v2", + "name": "Search V2", + "kind": "boolean", + "description": "Enables the new search backend", + "temporary": true, + "tags": [ + "backend", + "search" + ], + "on": true, + "variations": [ + { + "value": true, + "name": "Enabled" + }, + { + "value": false, + "name": "Disabled" + } + ] + } + ], + "totalCount": 3, + "pageInfo": { + "limit": 20, + "offset": 0 + } + }, + "get-flag": { + "key": "{{flagKey}}", + "name": "{{flagName}}", + "kind": "boolean", + "description": "Feature flag", + "temporary": true, + "tags": [], + "variations": [ + { + "value": true, + "name": "true" + }, + { + "value": false, + "name": "false" + } + ], + "defaults": { + "onVariation": 0, + "offVariation": 1 + }, + "environment": { + "on": false, + "version": 1, + "rules": [], + "targets": [], + "fallthrough": { + "variation": 1 + }, + "offVariation": 1 + } + }, + "create-flag": { + "key": "{{flagKey}}", + "name": "{{flagName}}", + "kind": "boolean", + "description": "", + "temporary": true, + "tags": [], + "variations": [ + { + "value": true, + "name": "true" + }, + { + "value": false, + "name": "false" + } + ], + "defaults": { + "onVariation": 0, + "offVariation": 1 + }, + "environments": { + "production": { + "on": false, + "version": 1 + }, + "staging": { + "on": false, + "version": 1 + } + } + }, + "create-feature-flag": { + "key": "{{flagKey}}", + "name": "{{flagName}}", + "kind": "boolean", + "description": "", + "temporary": true, + "tags": [], + "variations": [ + { + "value": true, + "name": "true" + }, + { + "value": false, + "name": "false" + } + ], + "defaults": { + "onVariation": 0, + "offVariation": 1 + }, + "environments": { + "production": { + "on": false, + "version": 1 + }, + "staging": { + "on": false, + "version": 1 + } + } + }, + "update-flag-settings": { + "key": "{{flagKey}}", + "name": "{{flagName}}", + "description": "", + "temporary": true, + "tags": [], + "maintainer": null + }, + "toggle-flag": { + "key": "{{flagKey}}", + "previousState": false, + "newState": true, + "environment": "production" + }, + "update-feature-flag": { + "key": "{{flagKey}}", + "environmentKey": "production", + "previous": { + "on": false + }, + "current": { + "on": true + } + }, + "get-environments": { + "items": [ + { + "key": "test", + "name": "Test", + "color": "417505", + "apiKey": "sdk-test-abcdef12-3456-7890-abcd-ef1234567890", + "mobileKey": "mob-test-abcdef12-3456-7890-abcd-ef1234567890", + "_id": "clientside-test-abcdef12" + }, + { + "key": "production", + "name": "Production", + "color": "D43F3A", + "apiKey": "sdk-prod-abcdef12-3456-7890-abcd-ef1234567890", + "mobileKey": "mob-prod-abcdef12-3456-7890-abcd-ef1234567890", + "_id": "clientside-prod-abcdef12" + } + ], + "totalCount": 2 + }, + "get-project": { + "key": "{{projectKey}}", + "name": "{{projectKey}}", + "environments": { + "items": [ + { + "key": "test", + "name": "Test", + "color": "417505" + }, + { + "key": "production", + "name": "Production", + "color": "D43F3A" + } + ], + "totalCount": 2 + } + }, + "list-feature-flags": { + "items": [ + { + "key": "enable-notifications", + "name": "Enable Notifications", + "kind": "boolean", + "temporary": true, + "tags": ["backend", "notifications"], + "on": true + }, + { + "key": "dark-mode", + "name": "Dark Mode", + "kind": "boolean", + "temporary": true, + "tags": ["frontend", "ui"], + "on": false + }, + { + "key": "search-v2", + "name": "Search V2", + "kind": "boolean", + "temporary": true, + "tags": ["backend", "search"], + "on": true + } + ], + "totalCount": 3 + }, + "list-ai-configs": { + "configs": [ + { + "key": "support-chatbot", + "name": "Support Chatbot", + "mode": "agent", + "description": "AI-powered support agent for customer tickets", + "tags": [ + "support", + "production" + ], + "variationsCount": 2, + "archived": false + }, + { + "key": "code-reviewer", + "name": "Code Review Assistant", + "mode": "completion", + "description": "Automated code review assistant for pull requests", + "tags": [ + "engineering" + ], + "variationsCount": 1, + "archived": false + }, + { + "key": "content-writer", + "name": "Content Writer", + "mode": "completion", + "description": "Marketing content generation", + "tags": [ + "marketing" + ], + "variationsCount": 3, + "archived": false + } + ], + "totalCount": 3 + }, + "get-ai-config": { + "key": "{{configKey}}", + "name": "{{configName}}", + "mode": "agent", + "description": "AI Config", + "tags": [], + "archived": false, + "variations": [ + { + "key": "default", + "name": "Default", + "modelConfigKey": "OpenAI.gpt-4o", + "modelName": "gpt-4o", + "instructions": "You are a helpful assistant that answers questions concisely.", + "status": "active", + "parameters": { + "temperature": 0.7, + "max_tokens": 2048 + } + } + ] + }, + "create-ai-config": { + "key": "{{configKey}}", + "name": "{{configName}}", + "mode": "{{mode}}", + "description": "", + "tags": [] + }, + "update-ai-config": { + "key": "{{configKey}}", + "name": "{{configName}}", + "description": "", + "tags": [], + "archived": "{{archived}}" + }, + "delete-ai-config": { + "deleted": true, + "key": "{{configKey}}" + }, + "setup-ai-config": { + "key": "{{configKey}}", + "name": "{{configName}}", + "mode": "{{mode}}", + "description": "", + "tags": [], + "archived": false, + "variations": [ + { + "key": "{{variationKey}}", + "name": "{{variationName}}", + "modelConfigKey": "{{modelConfigKey}}", + "modelName": "{{modelName}}", + "instructions": "You are a helpful assistant that answers questions concisely.", + "status": "active", + "parameters": { + "temperature": 0.7 + } + } + ] + }, + "get-ai-config-health": { + "key": "{{configKey}}", + "name": "{{configName}}", + "mode": "agent", + "health": "healthy", + "variationsCount": 1, + "issues": [], + "variations": [ + { + "key": "default", + "name": "Default", + "hasModel": true, + "hasPrompts": true, + "toolsAttached": 0 + } + ] + }, + "create-ai-config-variation": { + "configKey": "{{configKey}}", + "variation": { + "key": "{{variationKey}}", + "name": "{{variationName}}", + "modelConfigKey": "{{modelConfigKey}}", + "modelName": "{{modelName}}", + "instructions": "You are a helpful assistant that answers questions concisely.", + "status": "active", + "parameters": { + "temperature": 0.7 + } + } + }, + "update-ai-config-variation": { + "configKey": "{{configKey}}", + "variation": { + "key": "{{variationKey}}", + "name": "{{variationName}}", + "modelConfigKey": "{{modelConfigKey}}", + "modelName": "{{modelName}}", + "instructions": "Updated instructions for the agent.", + "status": "active", + "parameters": { + "temperature": 0.7 + } + } + }, + "delete-ai-config-variation": { + "deleted": true, + "configKey": "{{configKey}}", + "variationKey": "{{variationKey}}" + }, + "clone-ai-config-variation": { + "configKey": "{{configKey}}", + "source": { + "key": "default", + "name": "Default", + "modelConfigKey": "OpenAI.gpt-4o", + "modelName": "gpt-4o", + "instructions": "You are a helpful assistant that answers questions concisely.", + "status": "active", + "parameters": { + "temperature": 0.7, + "max_tokens": 2048 + }, + "tools": [ + { + "key": "search-docs", + "version": 2 + }, + { + "key": "run-query", + "version": 1 + } + ] + }, + "created": { + "key": "{{variationKey}}", + "name": "{{variationName}}", + "modelConfigKey": "{{modelConfigKey}}", + "modelName": "{{modelName}}", + "instructions": "You are a helpful assistant that answers questions concisely.", + "status": "active", + "parameters": { + "temperature": 0.7, + "max_tokens": 2048 + }, + "tools": [ + { + "key": "search-docs", + "version": 2 + }, + { + "key": "run-query", + "version": 1 + } + ] + } + }, + "list-ai-tools": { + "tools": [ + { + "key": "search-docs", + "description": "Search internal documentation", + "schema": { + "type": "object", + "properties": { + "query": { + "type": "string", + "description": "Search query" + }, + "limit": { + "type": "number", + "description": "Max results" + } + }, + "required": [ + "query" + ] + } + }, + { + "key": "run-query", + "description": "Run a database query", + "schema": null + } + ], + "totalCount": 2 + }, + "get-ai-tool": { + "key": "{{toolKey}}", + "description": "Search internal documentation", + "schema": { + "type": "object", + "properties": { + "query": { + "type": "string", + "description": "Search query" + }, + "limit": { + "type": "number", + "description": "Max results" + } + }, + "required": [ + "query" + ] + } + }, + "create-ai-tool": { + "key": "{{toolKey}}", + "description": "{{toolDescription}}", + "schema": { + "type": "object", + "properties": { + "input": { + "type": "string", + "description": "Input value" + } + } + } + } +} diff --git a/evals/package-lock.json b/evals/package-lock.json new file mode 100644 index 0000000..8228c7c --- /dev/null +++ b/evals/package-lock.json @@ -0,0 +1,12343 @@ +{ + "name": "@launchdarkly/skill-evals", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "@launchdarkly/skill-evals", + "dependencies": { + "@anthropic-ai/claude-agent-sdk": "^0.3.144" + }, + "devDependencies": { + "promptfoo": "^0.121.0", + "zod": "^3.22.4" + } + }, + "node_modules/@ai-sdk/gateway": { + "version": "3.0.116", + "resolved": "https://registry.npmjs.org/@ai-sdk/gateway/-/gateway-3.0.116.tgz", + "integrity": "sha512-k8P17w7Eho5Y4l3tZrYxqQdffkI4xwtl8GCxkZs+JdMWZhyrLLlozqWkKLaWrCSlEYQOeIhEnQLhqQgYYU86Rw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "3.0.10", + "@ai-sdk/provider-utils": "4.0.27", + "@vercel/oidc": "3.2.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4.1.8" + } + }, + "node_modules/@ai-sdk/provider": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/@ai-sdk/provider/-/provider-3.0.10.tgz", + "integrity": "sha512-Q3BZ27qfpYqnCYGvE3vt+Qi6LGOF9R5Nmzn+9JoM1lCRsD9mYaIhfJLkSunN48nfGXJ6n+XNV0J/XVpqGQl7Dw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "json-schema": "^0.4.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@ai-sdk/provider-utils": { + "version": "4.0.27", + "resolved": "https://registry.npmjs.org/@ai-sdk/provider-utils/-/provider-utils-4.0.27.tgz", + "integrity": "sha512-ubkAJ+xODouwtmN1tYlvTPphH1hPOBfZaEQe8U7skGvFAnIRs9PPpsq57bC2+Ky/MB4yzhd6YOsxTAx9sGpazw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/provider": "3.0.10", + "@standard-schema/spec": "^1.1.0", + "eventsource-parser": "^3.0.8" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4.1.8" + } + }, + "node_modules/@ai-sdk/provider-utils/node_modules/eventsource-parser": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.8.tgz", + "integrity": "sha512-70QWGkr4snxr0OXLRWsFLeRBIRPuQOvt4s8QYjmUlmlkyTZkRqS7EDVRZtzU3TiyDbXSzaOeF0XUKy8PchzukQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@ai-zen/node-fetch-event-source": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/@ai-zen/node-fetch-event-source/-/node-fetch-event-source-2.1.4.tgz", + "integrity": "sha512-OHFwPJecr+qwlyX5CGmTvKAKPZAdZaxvx/XDqS1lx4I2ZAk9riU0XnEaRGOOAEFrdcLZ98O5yWqubwjaQc0umg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "cross-fetch": "^4.0.0" + } + }, + "node_modules/@anthropic-ai/claude-agent-sdk": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk/-/claude-agent-sdk-0.3.144.tgz", + "integrity": "sha512-8TENU/XxsKeQD+TNQ1dWOH0O878sUXl7u6d1KOkCDBhr6Us1GVYNh99AjDikPq3oM9DGW3ZyXS0THqtcVF7bXQ==", + "license": "SEE LICENSE IN README.md", + "engines": { + "node": ">=18.0.0" + }, + "optionalDependencies": { + "@anthropic-ai/claude-agent-sdk-darwin-arm64": "0.3.144", + "@anthropic-ai/claude-agent-sdk-darwin-x64": "0.3.144", + "@anthropic-ai/claude-agent-sdk-linux-arm64": "0.3.144", + "@anthropic-ai/claude-agent-sdk-linux-arm64-musl": "0.3.144", + "@anthropic-ai/claude-agent-sdk-linux-x64": "0.3.144", + "@anthropic-ai/claude-agent-sdk-linux-x64-musl": "0.3.144", + "@anthropic-ai/claude-agent-sdk-win32-arm64": "0.3.144", + "@anthropic-ai/claude-agent-sdk-win32-x64": "0.3.144" + }, + "peerDependencies": { + "@anthropic-ai/sdk": ">=0.93.0", + "@modelcontextprotocol/sdk": "^1.29.0", + "zod": "^4.0.0" + } + }, + "node_modules/@anthropic-ai/claude-agent-sdk-darwin-arm64": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-darwin-arm64/-/claude-agent-sdk-darwin-arm64-0.2.141.tgz", + "integrity": "sha512-9HZ0ot6+FwOfQ1aeMqQLH4IJGMm/DcP08SysDxscVjBm6l2JjqleHohxi3zid0DurfGweqT+4x9GScJffwg55g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-darwin-x64": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-darwin-x64/-/claude-agent-sdk-darwin-x64-0.2.141.tgz", + "integrity": "sha512-4iAdarJaQ+2R58s6QJswZCzUdz2WQmL5lYG7Y+FLzWbRSROFfcH0QYpmOqSaPXd2KRQhIJwEacqecDZd/Q1XKQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-linux-arm64": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-arm64/-/claude-agent-sdk-linux-arm64-0.2.141.tgz", + "integrity": "sha512-Jdf0ZEwJzOP8sE6rPqdJN+SxMb0/L8sxJg4twCv/7S+Qzk0hJtls+wxSi+0Tjh6EEMaNxJqEGc7S3fx99Wi99Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-linux-arm64-musl": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-arm64-musl/-/claude-agent-sdk-linux-arm64-musl-0.2.141.tgz", + "integrity": "sha512-6H1AJ/AVaWNnV22kubUPkOTRzZFH0+qP9k7WlhriHMN9gtgZcVAsITMddDeGjQsQJMCAdhXFd6sgi7TM1LdeOQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-linux-x64": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-x64/-/claude-agent-sdk-linux-x64-0.2.141.tgz", + "integrity": "sha512-DVjp72f3HmrRYpbneWZZWIqkUht5kTZXS7wXGFiwzLz6eNYEgjjh+GcsnhIi8UOwZUtNiKUrjZnoP38ovFqV8A==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-linux-x64-musl": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-x64-musl/-/claude-agent-sdk-linux-x64-musl-0.2.141.tgz", + "integrity": "sha512-fTI1YuM4cxOa4nSgsyMAdB5ELizkWp+w5Ispo4JnnYtcczMAL4D9GBNjWPW0sUzKvjsJOUVim68SmWLWhUOpXQ==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-win32-arm64": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-win32-arm64/-/claude-agent-sdk-win32-arm64-0.2.141.tgz", + "integrity": "sha512-Wm10J6kfbufbPGFELokiJ/7Y5Oqug4Uag3HXFsV8g7TWCpaItx/oqVaJoiGptuAtXQB7xGLQVTuk082wER+Y5w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk-win32-x64": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-win32-x64/-/claude-agent-sdk-win32-x64-0.2.141.tgz", + "integrity": "sha512-IXuP29YJuWbR5Q6xOHrjFVGG54V2s1FC61UVNwEN5fpxL09MwPnbwtQL6fqgzt/U1MP7vWAwpXZriYAklkH/mg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-darwin-arm64": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-darwin-arm64/-/claude-agent-sdk-darwin-arm64-0.3.144.tgz", + "integrity": "sha512-pq5o/3yhzn/XCEO/BHEU5pDEYEE+4CL8d2VeGrKH1lWBNrlvjxIjesCe7VsDXgUN5JZVKAdr2DxYzLM8x3z89A==", + "cpu": [ + "arm64" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-darwin-x64": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-darwin-x64/-/claude-agent-sdk-darwin-x64-0.3.144.tgz", + "integrity": "sha512-v9fJKR+5ZFLd+TsAelBZTk2PB7/540Un7zaep1OKA67GKyv6odQaE317h9cQotsLpF14q7Uil1JlNA+eAv3XGw==", + "cpu": [ + "x64" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-linux-arm64": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-arm64/-/claude-agent-sdk-linux-arm64-0.3.144.tgz", + "integrity": "sha512-PulvfnScH2mWXOHWyNPhYWzq46moL1VzflGyogrEg911EEBHoUBISCBvcAitGjwpsOgoSm1lM+8k/J2yWoI8pA==", + "cpu": [ + "arm64" + ], + "libc": [ + "glibc" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-linux-arm64-musl": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-arm64-musl/-/claude-agent-sdk-linux-arm64-musl-0.3.144.tgz", + "integrity": "sha512-nem/AgXOlTKJdRO+v8WD51KeAd2z1rl/sKprlaepyAsQ5vJ5xMWKuWpnTPvLJsT/VdFGQIBgDRTNI+UMsh0Uag==", + "cpu": [ + "arm64" + ], + "libc": [ + "musl" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-linux-x64": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-x64/-/claude-agent-sdk-linux-x64-0.3.144.tgz", + "integrity": "sha512-zzLNbAVgbmu1rcyfT8qBQcyT3tO/plxoN+4JeqPhK0gVNrwTTjru3/VKnVG+11MYIEprC4DPzJGeRMHGLHhfzw==", + "cpu": [ + "x64" + ], + "libc": [ + "glibc" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-linux-x64-musl": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-linux-x64-musl/-/claude-agent-sdk-linux-x64-musl-0.3.144.tgz", + "integrity": "sha512-gDMjhk5PnE9BLXWxgHHCuJ7MpM+2hsBth/FJiHv5T0HWPw/oU2a3aMpkmgn7cTuva+hZ9Sp+gcPy8pbZOp6QVQ==", + "cpu": [ + "x64" + ], + "libc": [ + "musl" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-win32-arm64": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-win32-arm64/-/claude-agent-sdk-win32-arm64-0.3.144.tgz", + "integrity": "sha512-5ZbYkxeS+zxMzjTLq/wCpFBpZBZYObr9FDm/RvshQcenFVjTnkVyxUYtnF5PtCy1DqX035iCEF8dlRK//uhY3Q==", + "cpu": [ + "arm64" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/claude-agent-sdk-win32-x64": { + "version": "0.3.144", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk-win32-x64/-/claude-agent-sdk-win32-x64-0.3.144.tgz", + "integrity": "sha512-fLWcb133NaSLegLtUV19S9qh8modpyIia9dX6bxobS7NOaCYGmxWkCFGm6F2IuyF0h6yt33EMXFL8HnnYU8jaQ==", + "cpu": [ + "x64" + ], + "license": "SEE LICENSE IN LICENSE.md", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@anthropic-ai/sdk": { + "version": "0.92.0", + "resolved": "https://registry.npmjs.org/@anthropic-ai/sdk/-/sdk-0.92.0.tgz", + "integrity": "sha512-l653JFC83wCglH8H83t1xpgDurCyPyslYW1maPRdCsfuNuGbLvQjQ81sWd3Go3LWRm0jNspzAhuqAYV8r9joSw==", + "dev": true, + "license": "MIT", + "dependencies": { + "json-schema-to-ts": "^3.1.1" + }, + "bin": { + "anthropic-ai-sdk": "bin/cli" + }, + "peerDependencies": { + "zod": "^3.25.0 || ^4.0.0" + }, + "peerDependenciesMeta": { + "zod": { + "optional": true + } + } + }, + "node_modules/@apidevtools/json-schema-ref-parser": { + "version": "15.3.5", + "resolved": "https://registry.npmjs.org/@apidevtools/json-schema-ref-parser/-/json-schema-ref-parser-15.3.5.tgz", + "integrity": "sha512-orNOYXw3hYXxxisXMldjzjBzqqTLBPbwOtHg7ovBPvfBHDue1qM9YJENZ3W2BQuS+7z4ThogMbEzEsov57Itkg==", + "dev": true, + "license": "MIT", + "dependencies": { + "js-yaml": "^4.1.1" + }, + "engines": { + "node": ">=20" + }, + "peerDependencies": { + "@types/json-schema": "^7.0.15" + } + }, + "node_modules/@aws-crypto/crc32": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/crc32/-/crc32-5.2.0.tgz", + "integrity": "sha512-nLbCWqQNgUiwwtFsen1AdzAtvuLRsQS8rYgMuxCrdKf9kOssamGLuPwyTY9wyYblNr9+1XM8v6zoDTPPSIeANg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/util": "^5.2.0", + "@aws-sdk/types": "^3.222.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=16.0.0" + } + }, + "node_modules/@aws-crypto/crc32c": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/crc32c/-/crc32c-5.2.0.tgz", + "integrity": "sha512-+iWb8qaHLYKrNvGRbiYRHSdKRWhto5XlZUEBwDjYNf+ly5SVYG6zEoYIdxvf5R3zyeP16w4PLBn3rH1xc74Rag==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/util": "^5.2.0", + "@aws-sdk/types": "^3.222.0", + "tslib": "^2.6.2" + } + }, + "node_modules/@aws-crypto/sha1-browser": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/sha1-browser/-/sha1-browser-5.2.0.tgz", + "integrity": "sha512-OH6lveCFfcDjX4dbAvCFSYUjJZjDr/3XJ3xHtjn3Oj5b9RjojQo8npoLeA/bNwkOkrSQ0wgrHzXk4tDRxGKJeg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/supports-web-crypto": "^5.2.0", + "@aws-crypto/util": "^5.2.0", + "@aws-sdk/types": "^3.222.0", + "@aws-sdk/util-locate-window": "^3.0.0", + "@smithy/util-utf8": "^2.0.0", + "tslib": "^2.6.2" + } + }, + "node_modules/@aws-crypto/sha256-browser": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/sha256-browser/-/sha256-browser-5.2.0.tgz", + "integrity": "sha512-AXfN/lGotSQwu6HNcEsIASo7kWXZ5HYWvfOmSNKDsEqC4OashTp8alTmaz+F7TC2L083SFv5RdB+qU3Vs1kZqw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/sha256-js": "^5.2.0", + "@aws-crypto/supports-web-crypto": "^5.2.0", + "@aws-crypto/util": "^5.2.0", + "@aws-sdk/types": "^3.222.0", + "@aws-sdk/util-locate-window": "^3.0.0", + "@smithy/util-utf8": "^2.0.0", + "tslib": "^2.6.2" + } + }, + "node_modules/@aws-crypto/sha256-js": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/sha256-js/-/sha256-js-5.2.0.tgz", + "integrity": "sha512-FFQQyu7edu4ufvIZ+OadFpHHOt+eSTBaYaki44c+akjg7qZg9oOQeLlk77F6tSYqjDAFClrHJk9tMf0HdVyOvA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/util": "^5.2.0", + "@aws-sdk/types": "^3.222.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=16.0.0" + } + }, + "node_modules/@aws-crypto/supports-web-crypto": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/supports-web-crypto/-/supports-web-crypto-5.2.0.tgz", + "integrity": "sha512-iAvUotm021kM33eCdNfwIN//F77/IADDSs58i+MDaOqFrVjZo9bAal0NK7HurRuWLLpF1iLX7gbWrjHjeo+YFg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + } + }, + "node_modules/@aws-crypto/util": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/util/-/util-5.2.0.tgz", + "integrity": "sha512-4RkU9EsI6ZpBve5fseQlGNUWKMa1RLPQ1dnjnQoe07ldfIzcsGb5hC5W0Dm7u423KWzawlrpbjXBrXCEv9zazQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.222.0", + "@smithy/util-utf8": "^2.0.0", + "tslib": "^2.6.2" + } + }, + "node_modules/@aws-sdk/client-bedrock-agent-runtime": { + "version": "3.1050.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-bedrock-agent-runtime/-/client-bedrock-agent-runtime-3.1050.0.tgz", + "integrity": "sha512-MlNEufI6s3lBwYmXHfWUg4xsGK2BKNl1Y0UR6pzMvJlIXuE6Xiea3b6mkhLkDwbY1eZyXqNLkQQvbTHB8U8iww==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/sha256-browser": "5.2.0", + "@aws-crypto/sha256-js": "5.2.0", + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/credential-provider-node": "^3.972.43", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/node-http-handler": "^4.7.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/client-bedrock-runtime": { + "version": "3.1050.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-bedrock-runtime/-/client-bedrock-runtime-3.1050.0.tgz", + "integrity": "sha512-KbQqWGSyXh1c0opFTEcwNu6PcGd/IRyTnihDh8fpdiVCu62/53469AN+Xe6cKSuM6W2oOBbY12Pbj3zrdRK5mA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/sha256-browser": "5.2.0", + "@aws-crypto/sha256-js": "5.2.0", + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/credential-provider-node": "^3.972.43", + "@aws-sdk/eventstream-handler-node": "^3.972.16", + "@aws-sdk/middleware-eventstream": "^3.972.12", + "@aws-sdk/middleware-websocket": "^3.972.20", + "@aws-sdk/token-providers": "3.1050.0", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/node-http-handler": "^4.7.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/client-s3": { + "version": "3.1050.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-s3/-/client-s3-3.1050.0.tgz", + "integrity": "sha512-9kgtv+bXZQrOIJT2INPPBCezrJu1FlgGrzEat/ut4A4V53IT00LynsBZgp12eFKbjJuNCeTo7iPSKjPsX8ub+A==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/sha1-browser": "5.2.0", + "@aws-crypto/sha256-browser": "5.2.0", + "@aws-crypto/sha256-js": "5.2.0", + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/credential-provider-node": "^3.972.43", + "@aws-sdk/middleware-bucket-endpoint": "^3.972.14", + "@aws-sdk/middleware-expect-continue": "^3.972.12", + "@aws-sdk/middleware-flexible-checksums": "^3.974.20", + "@aws-sdk/middleware-location-constraint": "^3.972.10", + "@aws-sdk/middleware-sdk-s3": "^3.972.41", + "@aws-sdk/middleware-ssec": "^3.972.10", + "@aws-sdk/signature-v4-multi-region": "^3.996.27", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/node-http-handler": "^4.7.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/client-sagemaker-runtime": { + "version": "3.1050.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sagemaker-runtime/-/client-sagemaker-runtime-3.1050.0.tgz", + "integrity": "sha512-5jVq0cEvyUPVDN35cc2QcuXZkqhtjWpusd57z/xtVNd0jUNk85Catvo7WrAidOCZoRsCfW5ww5KsiQ7CqMb17A==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/sha256-browser": "5.2.0", + "@aws-crypto/sha256-js": "5.2.0", + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/credential-provider-node": "^3.972.43", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/node-http-handler": "^4.7.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/core": { + "version": "3.974.12", + "resolved": "https://registry.npmjs.org/@aws-sdk/core/-/core-3.974.12.tgz", + "integrity": "sha512-qrqgioqYFjwR6LatVNS1L2Vk++EwRIxqSQXPKNv5Ofux2D8UNgqMQ1znnMyEImXquVPTtbf71fc128pvmU6y9A==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@aws-sdk/xml-builder": "^3.972.24", + "@aws/lambda-invoke-store": "^0.2.2", + "@smithy/core": "^3.24.2", + "@smithy/signature-v4": "^5.4.2", + "@smithy/types": "^4.14.1", + "bowser": "^2.11.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/crc64-nvme": { + "version": "3.972.8", + "resolved": "https://registry.npmjs.org/@aws-sdk/crc64-nvme/-/crc64-nvme-3.972.8.tgz", + "integrity": "sha512-fVfUCL/Xh2zINYMPZvj+iBn6XWouQf0DAnjaWCI9MkmqXzL2Iy5FoQB8O7syFe6gN6AH1ecDDU58T51Ou0kFkA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-env": { + "version": "3.972.38", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-env/-/credential-provider-env-3.972.38.tgz", + "integrity": "sha512-m3WjZEgPtioMhPmwqUt+DhlTJ2i9ufR6DhfkyXojb9puEvfR+ur2U5shavu5/Cc9WHHsDCvALi6UFHgcqjhQ5w==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-http": { + "version": "3.972.40", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-http/-/credential-provider-http-3.972.40.tgz", + "integrity": "sha512-D78L/m2Dr6cJnnSvWoAudPhQmCwmJ7j6APXsPYmFpPaKfQTfCSu0rdm8j14Np+VmXF9z8Aj8HE3xFpsrwtfgeg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/node-http-handler": "^4.7.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-ini": { + "version": "3.972.42", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-ini/-/credential-provider-ini-3.972.42.tgz", + "integrity": "sha512-Mu5ESvFXeinafVM8jTIvRqcvK2Ehj4kz3auT39yUcHwu1Vfxo6xRlmUafdKLW4tusjAJukQwK09sCSMgOm7OKg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/credential-provider-env": "^3.972.38", + "@aws-sdk/credential-provider-http": "^3.972.40", + "@aws-sdk/credential-provider-login": "^3.972.42", + "@aws-sdk/credential-provider-process": "^3.972.38", + "@aws-sdk/credential-provider-sso": "^3.972.42", + "@aws-sdk/credential-provider-web-identity": "^3.972.42", + "@aws-sdk/nested-clients": "^3.997.10", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/credential-provider-imds": "^4.3.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-login": { + "version": "3.972.42", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-login/-/credential-provider-login-3.972.42.tgz", + "integrity": "sha512-O6WkZga3kf0yqyJYd1dbeJqVhEgJx/x1UaLgtbR+XuL/YP+K5y6QTxQKL7ka9z3jnQASESKGAPnRyt4D5hQrxA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/nested-clients": "^3.997.10", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-node": { + "version": "3.972.43", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-node/-/credential-provider-node-3.972.43.tgz", + "integrity": "sha512-D/DJmbrWRP5BXEO3FH+ar4el+2n6OlGofiud7dQun2jES+AQEJjczenp1jBb4MBN7CpGpS8nsWGQLtuzc9tQbA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/credential-provider-env": "^3.972.38", + "@aws-sdk/credential-provider-http": "^3.972.40", + "@aws-sdk/credential-provider-ini": "^3.972.42", + "@aws-sdk/credential-provider-process": "^3.972.38", + "@aws-sdk/credential-provider-sso": "^3.972.42", + "@aws-sdk/credential-provider-web-identity": "^3.972.42", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/credential-provider-imds": "^4.3.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-process": { + "version": "3.972.38", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-process/-/credential-provider-process-3.972.38.tgz", + "integrity": "sha512-EnbYVajGgbkb24s0K1eo4VNAPV5mHIET7LSvirTaFCwkfrfaOJxtSE+wY/tJdKDS21cEYkZs2ruCaAm+W4iblg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-sso": { + "version": "3.972.42", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-sso/-/credential-provider-sso-3.972.42.tgz", + "integrity": "sha512-RVV/9NbFwI8ZHEH5dn39lGyFmSbSVj1+orZdr6QsOe1mW9DCglmlen0cFaNZmCcqkqc7erNRHNBduxbeZuHAnw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/nested-clients": "^3.997.10", + "@aws-sdk/token-providers": "3.1049.0", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-sso/node_modules/@aws-sdk/token-providers": { + "version": "3.1049.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/token-providers/-/token-providers-3.1049.0.tgz", + "integrity": "sha512-r7+d0lQMTHKypkmaF5jRTBYLYHCUHzt3gaVoN9SidLhQeWhCmHk3AKrboDTpPF5b7Pt7vKu3+oeMjznM2Eu1ow==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/nested-clients": "^3.997.10", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-web-identity": { + "version": "3.972.42", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-web-identity/-/credential-provider-web-identity-3.972.42.tgz", + "integrity": "sha512-/67fXX0ddllD4u2Nujc5PvT4byHgpMUfz6+RxIKi/0nFIckeorm7JvXgzBuDyVKw0s58EbofmETDWUf9vTEuHQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/nested-clients": "^3.997.10", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/eventstream-handler-node": { + "version": "3.972.16", + "resolved": "https://registry.npmjs.org/@aws-sdk/eventstream-handler-node/-/eventstream-handler-node-3.972.16.tgz", + "integrity": "sha512-yedpPgKftqjU5SlPFHfqWpOw6xSCRieWRG1euWOlXn4WJxt2VX92VprCa2PpSOXjVCAeK6dTjW9eJRXVig9yGA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-bucket-endpoint": { + "version": "3.972.14", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-bucket-endpoint/-/middleware-bucket-endpoint-3.972.14.tgz", + "integrity": "sha512-Aaj0d+xbo1jJquBWJP0/9V/XZRYukO3LWIRp3dOLHmoFrYKb4YZ0aLefgVHfGcNOVBS2ZTq7L/n5JcrE7DaC+Q==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-eventstream": { + "version": "3.972.12", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-eventstream/-/middleware-eventstream-3.972.12.tgz", + "integrity": "sha512-tHTHHCHNrq6XklQvlzHBDJG4Iuhh7NVPRdtmvP+nHFA+5sxPlIDzlAHHgfoYHGvT3NXP1yVP/L5c3opUn6T3Qg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-expect-continue": { + "version": "3.972.12", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-expect-continue/-/middleware-expect-continue-3.972.12.tgz", + "integrity": "sha512-dA5pKTom/Ls9mgeyeaRBNQrRIVOLVjv4AmKOB0/e4yaiXEUy0gSz2d3liP8JHtYoCAEWySU1jWnyzwLOREN+4g==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-flexible-checksums": { + "version": "3.974.20", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-flexible-checksums/-/middleware-flexible-checksums-3.974.20.tgz", + "integrity": "sha512-NdnMVQCR1YjIcqFAiNLdBiOwr2DyQDB2IiXQrBhzolKOv32ae4d4Ll7IzLMi04eMHiq/o/Y/GjFuVjF9HuG0QA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/crc32": "5.2.0", + "@aws-crypto/crc32c": "5.2.0", + "@aws-crypto/util": "5.2.0", + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/crc64-nvme": "^3.972.8", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-location-constraint": { + "version": "3.972.10", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-location-constraint/-/middleware-location-constraint-3.972.10.tgz", + "integrity": "sha512-rI3NZvJcEvjoD0+0PI0iUAwlPw2IlSlhyvgBK/3WkKJQE/YiKFedd9dMN2lVacdNxPNhxL/jzQaKQdrGtQagjQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-sdk-s3": { + "version": "3.972.41", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-sdk-s3/-/middleware-sdk-s3-3.972.41.tgz", + "integrity": "sha512-M4T2I2WPuH5WQpU8Tsp+u2bcO29zGRkU14ATzuqb9I4xh8tzsLqtp4hzaJM5aO2dhMZnHDzyQwSFVgc3XbnoGg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/signature-v4-multi-region": "^3.996.27", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/signature-v4": "^5.4.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-ssec": { + "version": "3.972.10", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-ssec/-/middleware-ssec-3.972.10.tgz", + "integrity": "sha512-Gli9A0u8EVVb+5bFDGS/QbSVg28w/wpEidg1ggVcSj65BDTdGR6punsOcVjqdiu1i42WHWo51MCvARPIIz9juw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/middleware-websocket": { + "version": "3.972.20", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-websocket/-/middleware-websocket-3.972.20.tgz", + "integrity": "sha512-LM6P0i+Lu6pi25oNw2nqxjRxiEOtLgPB7xIvHfa+FxHTRLg8wcgqu3qg2COl4QaT7Es2yCxYdeRLVYazKAwL8g==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/signature-v4": "^5.4.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@aws-sdk/nested-clients": { + "version": "3.997.10", + "resolved": "https://registry.npmjs.org/@aws-sdk/nested-clients/-/nested-clients-3.997.10.tgz", + "integrity": "sha512-FtQ/Bt327peZJuyo4WZSOLVUTw9ujRxntepiC7L65FxA2P82Xlq0g14T22BuqBUeMjDoxa9nvwiMHjLIfP3eUg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/sha256-browser": "5.2.0", + "@aws-crypto/sha256-js": "5.2.0", + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/signature-v4-multi-region": "^3.996.27", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/fetch-http-handler": "^5.4.2", + "@smithy/node-http-handler": "^4.7.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/signature-v4-multi-region": { + "version": "3.996.27", + "resolved": "https://registry.npmjs.org/@aws-sdk/signature-v4-multi-region/-/signature-v4-multi-region-3.996.27.tgz", + "integrity": "sha512-0Phbz4t6HI3D3skxvG2uI+VWU034/nSIw1T8d+FPzzQG9EQTrw94o9mOKO2Gv3n3Oc8P7JD7RAUxkoneLWv5Eg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/signature-v4": "^5.4.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/token-providers": { + "version": "3.1050.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/token-providers/-/token-providers-3.1050.0.tgz", + "integrity": "sha512-LVw+bW8LKWdus3U4v7Ojm5XmIXv1ZlQ3rsQrlkEt5fss+SsWfTTzVxoo8kl6ZCY5gl5kL8lPGluHPIDGR8bntQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-sdk/core": "^3.974.12", + "@aws-sdk/nested-clients": "^3.997.10", + "@aws-sdk/types": "^3.973.8", + "@smithy/core": "^3.24.2", + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/types": { + "version": "3.973.8", + "resolved": "https://registry.npmjs.org/@aws-sdk/types/-/types-3.973.8.tgz", + "integrity": "sha512-gjlAdtHMbtR9X5iIhVUvbVcy55KnznpC6bkDUWW9z915bi0ckdUr5cjf16Kp6xq0bP5HBD2xzgbL9F9Quv5vUw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/types": "^4.14.1", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/util-locate-window": { + "version": "3.965.5", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-locate-window/-/util-locate-window-3.965.5.tgz", + "integrity": "sha512-WhlJNNINQB+9qtLtZJcpQdgZw3SCDCpXdUJP7cToGwHbCWCnRckGlc6Bx/OhWwIYFNAn+FIydY8SZ0QmVu3xTQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/xml-builder": { + "version": "3.972.24", + "resolved": "https://registry.npmjs.org/@aws-sdk/xml-builder/-/xml-builder-3.972.24.tgz", + "integrity": "sha512-V8z5YcDPfsvzrBlj0xR1vhRtocblhYbqdreCJB/voGd4Sr5zjNAeWxexbnqVtskTJe0vFb5KMqbSL++ePl+zRw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@nodable/entities": "2.1.0", + "@smithy/types": "^4.14.1", + "fast-xml-parser": "5.7.3", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@aws-sdk/xml-builder/node_modules/fast-xml-parser": { + "version": "5.7.3", + "resolved": "https://registry.npmjs.org/fast-xml-parser/-/fast-xml-parser-5.7.3.tgz", + "integrity": "sha512-C0AaNuC+mscy6vrAQKAc/rMq+zAPHodfHGZu4sGVehvAQt/JLG1O5zEcYcXSY5zSqr4YVgxsB+pHXTq0i7eDlg==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/NaturalIntelligence" + } + ], + "license": "MIT", + "optional": true, + "dependencies": { + "@nodable/entities": "^2.1.0", + "fast-xml-builder": "^1.1.7", + "path-expression-matcher": "^1.5.0", + "strnum": "^2.2.3" + }, + "bin": { + "fxparser": "src/cli/cli.js" + } + }, + "node_modules/@aws/lambda-invoke-store": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/@aws/lambda-invoke-store/-/lambda-invoke-store-0.2.4.tgz", + "integrity": "sha512-iY8yvjE0y651BixKNPgmv1WrQc+GZ142sb0z4gYnChDDY2YqI4P/jsSopBWrKfAt7LOJAkOXt7rC/hms+WclQQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@azure-rest/core-client": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/@azure-rest/core-client/-/core-client-2.6.0.tgz", + "integrity": "sha512-iuFKDm8XPzNxPfRjhyU5/xKZmcRDzSuEghXDHHk4MjBV/wFL34GmYVBZnn9wmuoLBeS1qAw9ceMdaeJBPcB1QQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.10.0", + "@azure/core-rest-pipeline": "^1.22.0", + "@azure/core-tracing": "^1.3.0", + "@typespec/ts-http-runtime": "^0.3.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/abort-controller": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/@azure/abort-controller/-/abort-controller-2.1.2.tgz", + "integrity": "sha512-nBrLsEWm4J2u5LpAPjxADTlq3trDgVZZXHNKabeXZtpq3d3AbN/KGO82R87rdDz5/lYB024rtEf10/q0urNgsA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@azure/ai-projects": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/@azure/ai-projects/-/ai-projects-2.1.1.tgz", + "integrity": "sha512-mHV0SvdP8F3vif4FuuGzuIOi+tqZgJveB8HWxBJExGHkEfwMPkQnTUufISSqfI8WmXJ4hgt+Xw/PAZ22VI1Zhw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure-rest/core-client": "^2.1.0", + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.6.0", + "@azure/core-lro": "^3.1.0", + "@azure/core-paging": "^1.5.0", + "@azure/core-rest-pipeline": "^1.5.0", + "@azure/core-sse": "^2.1.3", + "@azure/core-tracing": "^1.2.0", + "@azure/core-util": "^1.9.0", + "@azure/identity": "^4.13.0", + "@azure/logger": "^1.1.4", + "@azure/storage-blob": "^12.26.0", + "openai": "^6.16.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-auth": { + "version": "1.10.1", + "resolved": "https://registry.npmjs.org/@azure/core-auth/-/core-auth-1.10.1.tgz", + "integrity": "sha512-ykRMW8PjVAn+RS6ww5cmK9U2CyH9p4Q88YJwvUslfuMmN98w/2rdGRLPqJYObapBCdzBVeDgYWdJnFPFb7qzpg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-util": "^1.13.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-client": { + "version": "1.10.1", + "resolved": "https://registry.npmjs.org/@azure/core-client/-/core-client-1.10.1.tgz", + "integrity": "sha512-Nh5PhEOeY6PrnxNPsEHRr9eimxLwgLlpmguQaHKBinFYA/RU9+kOYVOQqOrTsCL+KSxrLLl1gD8Dk5BFW/7l/w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.10.0", + "@azure/core-rest-pipeline": "^1.22.0", + "@azure/core-tracing": "^1.3.0", + "@azure/core-util": "^1.13.0", + "@azure/logger": "^1.3.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-http-compat": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/@azure/core-http-compat/-/core-http-compat-2.4.0.tgz", + "integrity": "sha512-f1P96IB399YiN2ARYHP7EpZi3Bf3wH4SN2lGzrw7JVwm7bbsVYtf2iKSBwTywD2P62NOPZGHFSZi+6jjb75JuA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2" + }, + "engines": { + "node": ">=20.0.0" + }, + "peerDependencies": { + "@azure/core-client": "^1.10.0", + "@azure/core-rest-pipeline": "^1.22.0" + } + }, + "node_modules/@azure/core-lro": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/@azure/core-lro/-/core-lro-3.3.1.tgz", + "integrity": "sha512-bulm3klLqIAhzI3iQMYQ42i+V9EnevScsHdI9amFfjaw6OJqPBK1038cq5qachoKV3yt/iQQEDittHmZW2aSuA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-util": "^1.13.0", + "@azure/logger": "^1.3.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-paging": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/@azure/core-paging/-/core-paging-1.6.2.tgz", + "integrity": "sha512-YKWi9YuCU04B55h25cnOYZHxXYtEvQEbKST5vqRga7hWY9ydd3FZHdeQF8pyh+acWZvppw13M/LMGx0LABUVMA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@azure/core-rest-pipeline": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@azure/core-rest-pipeline/-/core-rest-pipeline-1.23.0.tgz", + "integrity": "sha512-Evs1INHo+jUjwHi1T6SG6Ua/LHOQBCLuKEEE6efIpt4ZOoNonaT1kP32GoOcdNDbfqsD2445CPri3MubBy5DEQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.10.0", + "@azure/core-tracing": "^1.3.0", + "@azure/core-util": "^1.13.0", + "@azure/logger": "^1.3.0", + "@typespec/ts-http-runtime": "^0.3.4", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-sse": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@azure/core-sse/-/core-sse-2.3.0.tgz", + "integrity": "sha512-jKhPpdDbVS5GlpadSKIC7V6Q4P2vEcwXi1c4CLTXs01Q/PAITES9v5J/S73+RtCMqQpsX0jGa2yPWwXi9JzdgA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-tracing": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/@azure/core-tracing/-/core-tracing-1.3.1.tgz", + "integrity": "sha512-9MWKevR7Hz8kNzzPLfX4EAtGM2b8mr50HPDBvio96bURP/9C+HjdH3sBlLSNNrvRAr5/k/svoH457gB5IKpmwQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-util": { + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/@azure/core-util/-/core-util-1.13.1.tgz", + "integrity": "sha512-XPArKLzsvl0Hf0CaGyKHUyVgF7oDnhKoP85Xv6M4StF/1AhfORhZudHtOyf2s+FcbuQ9dPRAjB8J2KvRRMUK2A==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@typespec/ts-http-runtime": "^0.3.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/core-xml": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/@azure/core-xml/-/core-xml-1.5.1.tgz", + "integrity": "sha512-xcNRHqCoSp4AunOALEae6A8f3qATb83gSrm31Iqb01OzblvC3/W/bfXozcq78EzIdzZzuH1bZ2NvRR0TdX709w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "fast-xml-parser": "^5.5.9", + "tslib": "^2.8.1" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/identity": { + "version": "4.13.1", + "resolved": "https://registry.npmjs.org/@azure/identity/-/identity-4.13.1.tgz", + "integrity": "sha512-5C/2WD5Vb1lHnZS16dNQRPMjN6oV/Upba+C9nBIs15PmOi6A3ZGs4Lr2u60zw4S04gi+u3cEXiqTVP7M4Pz3kw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.0.0", + "@azure/core-auth": "^1.9.0", + "@azure/core-client": "^1.9.2", + "@azure/core-rest-pipeline": "^1.17.0", + "@azure/core-tracing": "^1.0.0", + "@azure/core-util": "^1.11.0", + "@azure/logger": "^1.0.0", + "@azure/msal-browser": "^5.5.0", + "@azure/msal-node": "^5.1.0", + "open": "^10.1.0", + "tslib": "^2.2.0" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/logger": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@azure/logger/-/logger-1.3.0.tgz", + "integrity": "sha512-fCqPIfOcLE+CGqGPd66c8bZpwAji98tZ4JI9i/mlTNTlsIWslCfpg48s/ypyLxZTump5sypjrKn2/kY7q8oAbA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@typespec/ts-http-runtime": "^0.3.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/msal-browser": { + "version": "5.11.0", + "resolved": "https://registry.npmjs.org/@azure/msal-browser/-/msal-browser-5.11.0.tgz", + "integrity": "sha512-zkGNYS3TwY8lUpPIafAmsFCYZbgFixY9y/LZB9GUg0IILoHTqpN26j5OrkL1AQThh/YdZsawe4iWXfp85lFVxg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/msal-common": "16.6.2" + }, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/@azure/msal-common": { + "version": "16.6.2", + "resolved": "https://registry.npmjs.org/@azure/msal-common/-/msal-common-16.6.2.tgz", + "integrity": "sha512-hQjjsekAjB00cM1EmatWJlzhEoK2Qhz7Rj5gvM6tYf8iL7RM3tkxlpU9fG0+ofkulzg9AEEA6dIEnSmDr5ZqUA==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/@azure/msal-node": { + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/@azure/msal-node/-/msal-node-5.2.2.tgz", + "integrity": "sha512-toS+2AePxqyzb0YOKttDOOiSl3jrkK9aiqIvpurpis0O34QcIS5gToqrgT39p04Dpxw3YoUU0lxJKTpSFFfA6Q==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/msal-common": "16.6.2", + "jsonwebtoken": "^9.0.0" + }, + "engines": { + "node": ">=20" + } + }, + "node_modules/@azure/openai-assistants": { + "version": "1.0.0-beta.6", + "resolved": "https://registry.npmjs.org/@azure/openai-assistants/-/openai-assistants-1.0.0-beta.6.tgz", + "integrity": "sha512-gINKKcqTpR0neF+36Owe0Q1u1JO3IK6clBzWTfZ+9V/TkQq+LoUgp5F8dKvSv/YChfwEpZA2r1DWCwNE07eYIQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure-rest/core-client": "^1.1.4", + "@azure/core-auth": "^1.5.0", + "@azure/core-client": "^1.7.3", + "@azure/core-rest-pipeline": "^1.13.0", + "@azure/core-util": "^1.6.1", + "@azure/logger": "^1.0.4", + "tslib": "^2.2.0" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@azure/openai-assistants/node_modules/@azure-rest/core-client": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/@azure-rest/core-client/-/core-client-1.4.0.tgz", + "integrity": "sha512-ozTDPBVUDR5eOnMIwhggbnVmOrka4fXCs8n8mvUo4WLLc38kki6bAOByDoVZZPz/pZy2jMt2kwfpvy/UjALj6w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.0.0", + "@azure/core-auth": "^1.3.0", + "@azure/core-rest-pipeline": "^1.5.0", + "@azure/core-tracing": "^1.0.1", + "@azure/core-util": "^1.0.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@azure/storage-blob": { + "version": "12.31.0", + "resolved": "https://registry.npmjs.org/@azure/storage-blob/-/storage-blob-12.31.0.tgz", + "integrity": "sha512-DBgNv10aCSxopt92DkTDD0o9xScXeBqPKGmR50FPZQaEcH4JLQ+GEOGEDv19V5BMkB7kxr+m4h6il/cCDPvmHg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.9.0", + "@azure/core-client": "^1.9.3", + "@azure/core-http-compat": "^2.2.0", + "@azure/core-lro": "^2.2.0", + "@azure/core-paging": "^1.6.2", + "@azure/core-rest-pipeline": "^1.19.1", + "@azure/core-tracing": "^1.2.0", + "@azure/core-util": "^1.11.0", + "@azure/core-xml": "^1.4.5", + "@azure/logger": "^1.1.4", + "@azure/storage-common": "^12.3.0", + "events": "^3.0.0", + "tslib": "^2.8.1" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@azure/storage-blob/node_modules/@azure/core-lro": { + "version": "2.7.2", + "resolved": "https://registry.npmjs.org/@azure/core-lro/-/core-lro-2.7.2.tgz", + "integrity": "sha512-0YIpccoX8m/k00O7mDDMdJpbr6mf1yWo2dfmxt5A8XVZVVMz2SSKaEbMCeJRvgQ0IaSlqhjT47p4hVIRRy90xw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.0.0", + "@azure/core-util": "^1.2.0", + "@azure/logger": "^1.0.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@azure/storage-common": { + "version": "12.3.0", + "resolved": "https://registry.npmjs.org/@azure/storage-common/-/storage-common-12.3.0.tgz", + "integrity": "sha512-/OFHhy86aG5Pe8dP5tsp+BuJ25JOAl9yaMU3WZbkeoiFMHFtJ7tu5ili7qEdBXNW9G5lDB19trwyI6V49F/8iQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@azure/abort-controller": "^2.1.2", + "@azure/core-auth": "^1.9.0", + "@azure/core-http-compat": "^2.2.0", + "@azure/core-rest-pipeline": "^1.19.1", + "@azure/core-tracing": "^1.2.0", + "@azure/core-util": "^1.11.0", + "@azure/logger": "^1.1.4", + "events": "^3.3.0", + "tslib": "^2.8.1" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@babel/runtime": { + "version": "7.29.2", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.29.2.tgz", + "integrity": "sha512-JiDShH45zKHWyGe4ZNVRrCjBz8Nh9TMmZG1kh4QTK8hCBTWBi8Da+i7s1fJw7/lYpM4ccepSNfqzZ/QvABBi5g==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@borewit/text-codec": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@borewit/text-codec/-/text-codec-0.2.2.tgz", + "integrity": "sha512-DDaRehssg1aNrH4+2hnj1B7vnUGEjU6OIlyRdkMd0aUdIUvKXrJfXsy8LVtXAy7DRvYVluWbMspsRhz2lcW0mQ==", + "dev": true, + "license": "MIT", + "optional": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Borewit" + } + }, + "node_modules/@cacheable/utils": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/@cacheable/utils/-/utils-2.4.1.tgz", + "integrity": "sha512-eiFgzCbIneyMlLOmNG4g9xzF7Hv3Mga4LjxjcSC/ues6VYq2+gUbQI8JqNuw/ZM8tJIeIaBGpswAsqV2V7ApgA==", + "dev": true, + "license": "MIT", + "dependencies": { + "hashery": "^1.5.1", + "keyv": "^5.6.0" + } + }, + "node_modules/@colors/colors": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.5.0.tgz", + "integrity": "sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/@dabh/diagnostics": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/@dabh/diagnostics/-/diagnostics-2.0.8.tgz", + "integrity": "sha512-R4MSXTVnuMzGD7bzHdW2ZhhdPC/igELENcq5IjEverBvq5hn1SXCWcsi6eSsdWP0/Ur+SItRRjAktmdoX/8R/Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "@so-ric/colorspace": "^1.1.6", + "enabled": "2.0.x", + "kuler": "^2.0.0" + } + }, + "node_modules/@emnapi/runtime": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.10.0.tgz", + "integrity": "sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.4.0" + } + }, + "node_modules/@esbuild/aix-ppc64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.28.0.tgz", + "integrity": "sha512-lhRUCeuOyJQURhTxl4WkpFTjIsbDayJHih5kZC1giwE+MhIzAb7mEsQMqMf18rHLsrb5qI1tafG20mLxEWcWlA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "aix" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-arm": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.28.0.tgz", + "integrity": "sha512-wqh0ByljabXLKHeWXYLqoJ5jKC4XBaw6Hk08OfMrCRd2nP2ZQ5eleDZC41XHyCNgktBGYMbqnrJKq/K/lzPMSQ==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.28.0.tgz", + "integrity": "sha512-+WzIXQOSaGs33tLEgYPYe/yQHf0WTU0X42Jca3y8NWMbUVhp7rUnw+vAsRC/QiDrdD31IszMrZy+qwPOPjd+rw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.28.0.tgz", + "integrity": "sha512-+VJggoaKhk2VNNqVL7f6S189UzShHC/mR9EE8rDdSkdpN0KflSwWY/gWjDrNxxisg8Fp1ZCD9jLMo4m0OUfeUA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/darwin-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.28.0.tgz", + "integrity": "sha512-0T+A9WZm+bZ84nZBtk1ckYsOvyA3x7e2Acj1KdVfV4/2tdG4fzUp91YHx+GArWLtwqp77pBXVCPn2We7Letr0Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/darwin-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.28.0.tgz", + "integrity": "sha512-fyzLm/DLDl/84OCfp2f/XQ4flmORsjU7VKt8HLjvIXChJoFFOIL6pLJPH4Yhd1n1gGFF9mPwtlN5Wf82DZs+LQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/freebsd-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.28.0.tgz", + "integrity": "sha512-l9GeW5UZBT9k9brBYI+0WDffcRxgHQD8ShN2Ur4xWq/NFzUKm3k5lsH4PdaRgb2w7mI9u61nr2gI2mLI27Nh3Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/freebsd-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.28.0.tgz", + "integrity": "sha512-BXoQai/A0wPO6Es3yFJ7APCiKGc1tdAEOgeTNy3SsB491S3aHn4S4r3e976eUnPdU+NbdtmBuLncYir2tMU9Nw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-arm": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.28.0.tgz", + "integrity": "sha512-CjaaREJagqJp7iTaNQjjidaNbCKYcd4IDkzbwwxtSvjI7NZm79qiHc8HqciMddQ6CKvJT6aBd8lO9kN/ZudLlw==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.28.0.tgz", + "integrity": "sha512-RVyzfb3FWsGA55n6WY0MEIEPURL1FcbhFE6BffZEMEekfCzCIMtB5yyDcFnVbTnwk+CLAgTujmV/Lgvih56W+A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-ia32": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.28.0.tgz", + "integrity": "sha512-KBnSTt1kxl9x70q+ydterVdl+Cn0H18ngRMRCEQfrbqdUuntQQ0LoMZv47uB97NljZFzY6HcfqEZ2SAyIUTQBQ==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-loong64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.28.0.tgz", + "integrity": "sha512-zpSlUce1mnxzgBADvxKXX5sl8aYQHo2ezvMNI8I0lbblJtp8V4odlm3Yzlj7gPyt3T8ReksE6bK+pT3WD+aJRg==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-mips64el": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.28.0.tgz", + "integrity": "sha512-2jIfP6mmjkdmeTlsX/9vmdmhBmKADrWqN7zcdtHIeNSCH1SqIoNI63cYsjQR8J+wGa4Y5izRcSHSm8K3QWmk3w==", + "cpu": [ + "mips64el" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-ppc64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.28.0.tgz", + "integrity": "sha512-bc0FE9wWeC0WBm49IQMPSPILRocGTQt3j5KPCA8os6VprfuJ7KD+5PzESSrJ6GmPIPJK965ZJHTUlSA6GNYEhg==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-riscv64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.28.0.tgz", + "integrity": "sha512-SQPZOwoTTT/HXFXQJG/vBX8sOFagGqvZyXcgLA3NhIqcBv1BJU1d46c0rGcrij2B56Z2rNiSLaZOYW5cUk7yLQ==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-s390x": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.28.0.tgz", + "integrity": "sha512-SCfR0HN8CEEjnYnySJTd2cw0k9OHB/YFzt5zgJEwa+wL/T/raGWYMBqwDNAC6dqFKmJYZoQBRfHjgwLHGSrn3Q==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.28.0.tgz", + "integrity": "sha512-us0dSb9iFxIi8srnpl931Nvs65it/Jd2a2K3qs7fz2WfGPHqzfzZTfec7oxZJRNPXPnNYZtanmRc4AL/JwVzHQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/netbsd-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.28.0.tgz", + "integrity": "sha512-CR/RYotgtCKwtftMwJlUU7xCVNg3lMYZ0RzTmAHSfLCXw3NtZtNpswLEj/Kkf6kEL3Gw+BpOekRX0BYCtklhUw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/netbsd-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.28.0.tgz", + "integrity": "sha512-nU1yhmYutL+fQ71Kxnhg8uEOdC0pwEW9entHykTgEbna2pw2dkbFSMeqjjyHZoCmt8SBkOSvV+yNmm94aUrrqw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openbsd-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.28.0.tgz", + "integrity": "sha512-cXb5vApOsRsxsEl4mcZ1XY3D4DzcoMxR/nnc4IyqYs0rTI8ZKmW6kyyg+11Z8yvgMfAEldKzP7AdP64HnSC/6g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openbsd-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.28.0.tgz", + "integrity": "sha512-8wZM2qqtv9UP3mzy7HiGYNH/zjTA355mpeuA+859TyR+e+Tc08IHYpLJuMsfpDJwoLo1ikIJI8jC3GFjnRClzA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openharmony-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/openharmony-arm64/-/openharmony-arm64-0.28.0.tgz", + "integrity": "sha512-FLGfyizszcef5C3YtoyQDACyg95+dndv79i2EekILBofh5wpCa1KuBqOWKrEHZg3zrL3t5ouE5jgr94vA+Wb2w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/sunos-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.28.0.tgz", + "integrity": "sha512-1ZgjUoEdHZZl/YlV76TSCz9Hqj9h9YmMGAgAPYd+q4SicWNX3G5GCyx9uhQWSLcbvPW8Ni7lj4gDa1T40akdlw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.28.0.tgz", + "integrity": "sha512-Q9StnDmQ/enxnpxCCLSg0oo4+34B9TdXpuyPeTedN/6+iXBJ4J+zwfQI28u/Jl40nOYAxGoNi7mFP40RUtkmUA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-ia32": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.28.0.tgz", + "integrity": "sha512-zF3ag/gfiCe6U2iczcRzSYJKH1DCI+ByzSENHlM2FcDbEeo5Zd2C86Aq0tKUYAJJ1obRP84ymxIAksZUcdztHA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.28.0.tgz", + "integrity": "sha512-pEl1bO9mfAmIC+tW5btTmrKaujg3zGtUmWNdCw/xs70FBjwAL3o9OEKNHvNmnyylD6ubxUERiEhdsL0xBQ9efw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@fal-ai/client": { + "version": "1.10.1", + "resolved": "https://registry.npmjs.org/@fal-ai/client/-/client-1.10.1.tgz", + "integrity": "sha512-c3AVeH31OioiI2J1BfW8Cryi1DhUYldnY3X35nv6xLMq3fU2NQOo+eYaR5mL2O8MoHHh+HzXdQuIyanIyeq+ug==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@msgpack/msgpack": "^3.0.0-beta2", + "eventsource-parser": "^1.1.2", + "robot3": "^0.4.1" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@googleapis/sheets": { + "version": "13.0.1", + "resolved": "https://registry.npmjs.org/@googleapis/sheets/-/sheets-13.0.1.tgz", + "integrity": "sha512-XTYObncN5Rqexc0uITZIN9OWTEyE/ZR2S6c7wAniqHe2oGXW9gcHR9f9hQwPMHFUTHjH7Jkj8SLdt0O0u37y2A==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "googleapis-common": "^8.0.0" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/@hono/node-server": { + "version": "1.19.14", + "resolved": "https://registry.npmjs.org/@hono/node-server/-/node-server-1.19.14.tgz", + "integrity": "sha512-GwtvgtXxnWsucXvbQXkRgqksiH2Qed37H9xHZocE5sA3N8O8O8/8FA3uclQXxXVzc9XBZuEOMK7+r02FmSpHtw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.14.1" + }, + "peerDependencies": { + "hono": "^4" + } + }, + "node_modules/@huggingface/jinja": { + "version": "0.5.9", + "resolved": "https://registry.npmjs.org/@huggingface/jinja/-/jinja-0.5.9.tgz", + "integrity": "sha512-uWTG+l3VJRsl7EXxYizuL3P+cCPoc3cRqbWWRcQN0FhejRfbdq0RNhCmbY/YDtnTcz9icdLYuLDjsnz4d8JMuw==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=18" + } + }, + "node_modules/@huggingface/tokenizers": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/@huggingface/tokenizers/-/tokenizers-0.1.3.tgz", + "integrity": "sha512-8rF/RRT10u+kn7YuUbUg0OF30K8rjTc78aHpxT+qJ1uWSqxT1MHi8+9ltwYfkFYJzT/oS+qw3JVfHtNMGAdqyA==", + "dev": true, + "license": "Apache-2.0", + "optional": true + }, + "node_modules/@huggingface/transformers": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/@huggingface/transformers/-/transformers-4.2.0.tgz", + "integrity": "sha512-8BRCoBMH0XsWaEIamuR0LrJGAfftgHAfb2Vrffy0VKlSAE/MnUJ5/h/zTfEP3fDIft+nk7TqB8xXEyABGitBjQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@huggingface/jinja": "^0.5.6", + "@huggingface/tokenizers": "^0.1.3", + "onnxruntime-node": "1.24.3", + "onnxruntime-web": "1.26.0-dev.20260416-b7804b056c", + "sharp": "^0.34.5" + } + }, + "node_modules/@ibm-cloud/watsonx-ai": { + "version": "1.7.12", + "resolved": "https://registry.npmjs.org/@ibm-cloud/watsonx-ai/-/watsonx-ai-1.7.12.tgz", + "integrity": "sha512-++tkoj1yLKNMeS+EPC/cvVYQZbyLAUGdDy/QeUObhRYSQmENDnCcA3Y1qquBH6XcPLXw7sQCQZCwFfhCTrvJow==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "form-data": "^4.0.4", + "ibm-cloud-sdk-core": "^5.4.14" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@ibm-generative-ai/node-sdk": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/@ibm-generative-ai/node-sdk/-/node-sdk-3.2.4.tgz", + "integrity": "sha512-HvJSYql3lOPYZcGb23mBw0kcWLlCX+n7EDRgJQxz7gIzx9WafUuDyl1IlTCXGfxolm0EhNIub79u9v7owtks0w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@ai-zen/node-fetch-event-source": "^2.1.2", + "fetch-retry": "^5.0.6", + "http-status-codes": "^2.3.0", + "openapi-fetch": "^0.8.2", + "p-queue-compat": "1.0.225", + "yaml": "^2.3.3" + }, + "peerDependencies": { + "@langchain/core": ">=0.1.0" + }, + "peerDependenciesMeta": { + "@langchain/core": { + "optional": true + } + } + }, + "node_modules/@img/colour": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@img/colour/-/colour-1.1.0.tgz", + "integrity": "sha512-Td76q7j57o/tLVdgS746cYARfSyxk8iEfRxewL9h4OMzYhbW4TAcppl0mT4eyqXddh6L/jwoM75mo7ixa/pCeQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=18" + } + }, + "node_modules/@img/sharp-darwin-arm64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-darwin-arm64/-/sharp-darwin-arm64-0.34.5.tgz", + "integrity": "sha512-imtQ3WMJXbMY4fxb/Ndp6HBTNVtWCUI0WdobyheGf5+ad6xX8VIDO8u2xE4qc/fr08CKG/7dDseFtn6M6g/r3w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-darwin-arm64": "1.2.4" + } + }, + "node_modules/@img/sharp-darwin-x64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-darwin-x64/-/sharp-darwin-x64-0.34.5.tgz", + "integrity": "sha512-YNEFAF/4KQ/PeW0N+r+aVVsoIY0/qxxikF2SWdp+NRkmMB7y9LBZAVqQ4yhGCm/H3H270OSykqmQMKLBhBJDEw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-darwin-x64": "1.2.4" + } + }, + "node_modules/@img/sharp-libvips-darwin-arm64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-darwin-arm64/-/sharp-libvips-darwin-arm64-1.2.4.tgz", + "integrity": "sha512-zqjjo7RatFfFoP0MkQ51jfuFZBnVE2pRiaydKJ1G/rHZvnsrHAOcQALIi9sA5co5xenQdTugCvtb1cuf78Vf4g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "darwin" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-darwin-x64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-darwin-x64/-/sharp-libvips-darwin-x64-1.2.4.tgz", + "integrity": "sha512-1IOd5xfVhlGwX+zXv2N93k0yMONvUlANylbJw1eTah8K/Jtpi15KC+WSiaX/nBmbm2HxRM1gZ0nSdjSsrZbGKg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "darwin" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linux-arm": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-arm/-/sharp-libvips-linux-arm-1.2.4.tgz", + "integrity": "sha512-bFI7xcKFELdiNCVov8e44Ia4u2byA+l3XtsAj+Q8tfCwO6BQ8iDojYdvoPMqsKDkuoOo+X6HZA0s0q11ANMQ8A==", + "cpu": [ + "arm" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linux-arm64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-arm64/-/sharp-libvips-linux-arm64-1.2.4.tgz", + "integrity": "sha512-excjX8DfsIcJ10x1Kzr4RcWe1edC9PquDRRPx3YVCvQv+U5p7Yin2s32ftzikXojb1PIFc/9Mt28/y+iRklkrw==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linux-ppc64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-ppc64/-/sharp-libvips-linux-ppc64-1.2.4.tgz", + "integrity": "sha512-FMuvGijLDYG6lW+b/UvyilUWu5Ayu+3r2d1S8notiGCIyYU/76eig1UfMmkZ7vwgOrzKzlQbFSuQfgm7GYUPpA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linux-riscv64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-riscv64/-/sharp-libvips-linux-riscv64-1.2.4.tgz", + "integrity": "sha512-oVDbcR4zUC0ce82teubSm+x6ETixtKZBh/qbREIOcI3cULzDyb18Sr/Wcyx7NRQeQzOiHTNbZFF1UwPS2scyGA==", + "cpu": [ + "riscv64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linux-s390x": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-s390x/-/sharp-libvips-linux-s390x-1.2.4.tgz", + "integrity": "sha512-qmp9VrzgPgMoGZyPvrQHqk02uyjA0/QrTO26Tqk6l4ZV0MPWIW6LTkqOIov+J1yEu7MbFQaDpwdwJKhbJvuRxQ==", + "cpu": [ + "s390x" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linux-x64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-x64/-/sharp-libvips-linux-x64-1.2.4.tgz", + "integrity": "sha512-tJxiiLsmHc9Ax1bz3oaOYBURTXGIRDODBqhveVHonrHJ9/+k89qbLl0bcJns+e4t4rvaNBxaEZsFtSfAdquPrw==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linuxmusl-arm64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linuxmusl-arm64/-/sharp-libvips-linuxmusl-arm64-1.2.4.tgz", + "integrity": "sha512-FVQHuwx1IIuNow9QAbYUzJ+En8KcVm9Lk5+uGUQJHaZmMECZmOlix9HnH7n1TRkXMS0pGxIJokIVB9SuqZGGXw==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-libvips-linuxmusl-x64": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@img/sharp-libvips-linuxmusl-x64/-/sharp-libvips-linuxmusl-x64-1.2.4.tgz", + "integrity": "sha512-+LpyBk7L44ZIXwz/VYfglaX/okxezESc6UxDSoyo2Ks6Jxc4Y7sGjpgU9s4PMgqgjj1gZCylTieNamqA1MF7Dg==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "LGPL-3.0-or-later", + "optional": true, + "os": [ + "linux" + ], + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-linux-arm": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linux-arm/-/sharp-linux-arm-0.34.5.tgz", + "integrity": "sha512-9dLqsvwtg1uuXBGZKsxem9595+ujv0sJ6Vi8wcTANSFpwV/GONat5eCkzQo/1O6zRIkh0m/8+5BjrRr7jDUSZw==", + "cpu": [ + "arm" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linux-arm": "1.2.4" + } + }, + "node_modules/@img/sharp-linux-arm64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linux-arm64/-/sharp-linux-arm64-0.34.5.tgz", + "integrity": "sha512-bKQzaJRY/bkPOXyKx5EVup7qkaojECG6NLYswgktOZjaXecSAeCWiZwwiFf3/Y+O1HrauiE3FVsGxFg8c24rZg==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linux-arm64": "1.2.4" + } + }, + "node_modules/@img/sharp-linux-ppc64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linux-ppc64/-/sharp-linux-ppc64-0.34.5.tgz", + "integrity": "sha512-7zznwNaqW6YtsfrGGDA6BRkISKAAE1Jo0QdpNYXNMHu2+0dTrPflTLNkpc8l7MUP5M16ZJcUvysVWWrMefZquA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linux-ppc64": "1.2.4" + } + }, + "node_modules/@img/sharp-linux-riscv64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linux-riscv64/-/sharp-linux-riscv64-0.34.5.tgz", + "integrity": "sha512-51gJuLPTKa7piYPaVs8GmByo7/U7/7TZOq+cnXJIHZKavIRHAP77e3N2HEl3dgiqdD/w0yUfiJnII77PuDDFdw==", + "cpu": [ + "riscv64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linux-riscv64": "1.2.4" + } + }, + "node_modules/@img/sharp-linux-s390x": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linux-s390x/-/sharp-linux-s390x-0.34.5.tgz", + "integrity": "sha512-nQtCk0PdKfho3eC5MrbQoigJ2gd1CgddUMkabUj+rBevs8tZ2cULOx46E7oyX+04WGfABgIwmMC0VqieTiR4jg==", + "cpu": [ + "s390x" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linux-s390x": "1.2.4" + } + }, + "node_modules/@img/sharp-linux-x64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linux-x64/-/sharp-linux-x64-0.34.5.tgz", + "integrity": "sha512-MEzd8HPKxVxVenwAa+JRPwEC7QFjoPWuS5NZnBt6B3pu7EG2Ge0id1oLHZpPJdn3OQK+BQDiw9zStiHBTJQQQQ==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linux-x64": "1.2.4" + } + }, + "node_modules/@img/sharp-linuxmusl-arm64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linuxmusl-arm64/-/sharp-linuxmusl-arm64-0.34.5.tgz", + "integrity": "sha512-fprJR6GtRsMt6Kyfq44IsChVZeGN97gTD331weR1ex1c1rypDEABN6Tm2xa1wE6lYb5DdEnk03NZPqA7Id21yg==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linuxmusl-arm64": "1.2.4" + } + }, + "node_modules/@img/sharp-linuxmusl-x64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-linuxmusl-x64/-/sharp-linuxmusl-x64-0.34.5.tgz", + "integrity": "sha512-Jg8wNT1MUzIvhBFxViqrEhWDGzqymo3sV7z7ZsaWbZNDLXRJZoRGrjulp60YYtV4wfY8VIKcWidjojlLcWrd8Q==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-libvips-linuxmusl-x64": "1.2.4" + } + }, + "node_modules/@img/sharp-wasm32": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-wasm32/-/sharp-wasm32-0.34.5.tgz", + "integrity": "sha512-OdWTEiVkY2PHwqkbBI8frFxQQFekHaSSkUIJkwzclWZe64O1X4UlUjqqqLaPbUpMOQk6FBu/HtlGXNblIs0huw==", + "cpu": [ + "wasm32" + ], + "dev": true, + "license": "Apache-2.0 AND LGPL-3.0-or-later AND MIT", + "optional": true, + "dependencies": { + "@emnapi/runtime": "^1.7.0" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-win32-arm64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-win32-arm64/-/sharp-win32-arm64-0.34.5.tgz", + "integrity": "sha512-WQ3AgWCWYSb2yt+IG8mnC6Jdk9Whs7O0gxphblsLvdhSpSTtmu69ZG1Gkb6NuvxsNACwiPV6cNSZNzt0KPsw7g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 AND LGPL-3.0-or-later", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-win32-ia32": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-win32-ia32/-/sharp-win32-ia32-0.34.5.tgz", + "integrity": "sha512-FV9m/7NmeCmSHDD5j4+4pNI8Cp3aW+JvLoXcTUo0IqyjSfAZJ8dIUmijx1qaJsIiU+Hosw6xM5KijAWRJCSgNg==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "Apache-2.0 AND LGPL-3.0-or-later", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@img/sharp-win32-x64": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/@img/sharp-win32-x64/-/sharp-win32-x64-0.34.5.tgz", + "integrity": "sha512-+29YMsqY2/9eFEiW93eqWnuLcWcufowXewwSNIT6UwZdUUCrM3oFjMWH/Z6/TMmb4hlFenmfAVbpWeup2jryCw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 AND LGPL-3.0-or-later", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + } + }, + "node_modules/@inquirer/ansi": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@inquirer/ansi/-/ansi-2.0.5.tgz", + "integrity": "sha512-doc2sWgJpbFQ64UflSVd17ibMGDuxO1yKgOgLMwavzESnXjFWJqUeG8saYosqKpHp4kWiM5x1nXvEjbpx90gzw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + } + }, + "node_modules/@inquirer/checkbox": { + "version": "5.1.5", + "resolved": "https://registry.npmjs.org/@inquirer/checkbox/-/checkbox-5.1.5.tgz", + "integrity": "sha512-Jmf9tgBHIEK5SAOB7swYfStqmtkZb00xOTpSQmkoGEpdxOTpJi9RS0A8bkfDPHTTItZRJrRdZrEMu25wyj0VfQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@inquirer/ansi": "^2.0.5", + "@inquirer/core": "^11.1.10", + "@inquirer/figures": "^2.0.5", + "@inquirer/type": "^4.0.5" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/confirm": { + "version": "6.0.13", + "resolved": "https://registry.npmjs.org/@inquirer/confirm/-/confirm-6.0.13.tgz", + "integrity": "sha512-wkGPC7yJ5WJk1DJ5SX7fzk+gfj4BM8cf5dDDi71B/551xHrdsZVRJOC0WyikXd0pEsb/9cLniuE4atbsMqmFkw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@inquirer/core": "^11.1.10", + "@inquirer/type": "^4.0.5" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/core": { + "version": "11.1.10", + "resolved": "https://registry.npmjs.org/@inquirer/core/-/core-11.1.10.tgz", + "integrity": "sha512-a4Q5BXHQAHa9eO202sTaFCHFYVB3x5fauDuThEAdZ9gfn76pSxiKU7wWcEH0N1O0XmQvNfQNU6QXpiRxmYQx+A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@inquirer/ansi": "^2.0.5", + "@inquirer/figures": "^2.0.5", + "@inquirer/type": "^4.0.5", + "cli-width": "^4.1.0", + "fast-wrap-ansi": "^0.2.0", + "mute-stream": "^3.0.0", + "signal-exit": "^4.1.0" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/editor": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/@inquirer/editor/-/editor-5.1.2.tgz", + "integrity": "sha512-Y3Nor7S/DhIPo+8Ym/dSY4efwKI4BsflKDwXh0jNeXJsSF3dteS/3Yf+z4wkibVZDvYMyCgknSTQlNahfunGHg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@inquirer/core": "^11.1.10", + "@inquirer/external-editor": "^3.0.0", + "@inquirer/type": "^4.0.5" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/external-editor": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@inquirer/external-editor/-/external-editor-3.0.0.tgz", + "integrity": "sha512-lDSwMgg+M5rq6JKBYaJwSX6T9e/HK2qqZ1oxmOwn4AQoJE5D+7TumsxLGC02PWS//rkIVqbZv3XA3ejsc9FYvg==", + "dev": true, + "license": "MIT", + "dependencies": { + "chardet": "^2.1.1", + "iconv-lite": "^0.7.2" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/figures": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@inquirer/figures/-/figures-2.0.5.tgz", + "integrity": "sha512-NsSs4kzfm12lNetHwAn3GEuH317IzpwrMCbOuMIVytpjnJ90YYHNwdRgYGuKmVxwuIqSgqk3M5qqQt1cDk0tGQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + } + }, + "node_modules/@inquirer/input": { + "version": "5.0.13", + "resolved": "https://registry.npmjs.org/@inquirer/input/-/input-5.0.13.tgz", + "integrity": "sha512-0l0jCHlJnXIV8CTxwQC0C+5Ziq8WP22edWgmciW2xYvoeoSck4v5FvCS1ctKdqLLR0dUo93uAHgWHywgBSoRyw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@inquirer/core": "^11.1.10", + "@inquirer/type": "^4.0.5" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/select": { + "version": "5.1.5", + "resolved": "https://registry.npmjs.org/@inquirer/select/-/select-5.1.5.tgz", + "integrity": "sha512-6SRg6kHfK/sjLXOsuqNebuir+sjwrf/iWuRUnXgB2slzEewppI1WfzeS16XxDcOQmXBruMmmB9Cgrz7wsAxqMg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@inquirer/ansi": "^2.0.5", + "@inquirer/core": "^11.1.10", + "@inquirer/figures": "^2.0.5", + "@inquirer/type": "^4.0.5" + }, + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@inquirer/type": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/@inquirer/type/-/type-4.0.5.tgz", + "integrity": "sha512-aetVUNeKNc/VriqXlw1NRSW0zhMBB0W4bNbWRJgzRl/3d0QNDQFfk0GO5SDdtjMZVg6o8ZKEiadd7SCCzoOn5Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0" + }, + "peerDependencies": { + "@types/node": ">=18" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/@keyv/serialize": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@keyv/serialize/-/serialize-1.1.1.tgz", + "integrity": "sha512-dXn3FZhPv0US+7dtJsIi2R+c7qWYiReoEh5zUntWCf4oSpMNib8FDhSoed6m3QyZdx5hK7iLFkYk3rNxwt8vTA==", + "dev": true, + "license": "MIT" + }, + "node_modules/@kwsites/file-exists": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@kwsites/file-exists/-/file-exists-1.1.1.tgz", + "integrity": "sha512-m9/5YGR18lIwxSFDwfE3oA7bWuq9kdau6ugN4H2rJeyhFQZcG9AgSHkQtSD15a8WvTgfz9aikZMrKPHvbpqFiw==", + "dev": true, + "license": "MIT", + "dependencies": { + "debug": "^4.1.1" + } + }, + "node_modules/@kwsites/file-exists/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/@kwsites/file-exists/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/@kwsites/promise-deferred": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@kwsites/promise-deferred/-/promise-deferred-1.1.1.tgz", + "integrity": "sha512-GaHYm+c0O9MjZRu0ongGBRbinu8gVAMd2UZjji6jVmqKtZluZnptXGWhz1E8j8D2HJ3f/yMxKAUC0b+57wncIw==", + "dev": true, + "license": "MIT" + }, + "node_modules/@modelcontextprotocol/sdk": { + "version": "1.29.0", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.29.0.tgz", + "integrity": "sha512-zo37mZA9hJWpULgkRpowewez1y6ML5GsXJPY8FI0tBBCd77HEvza4jDqRKOXgHNn867PVGCyTdzqpz0izu5ZjQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@hono/node-server": "^1.19.9", + "ajv": "^8.17.1", + "ajv-formats": "^3.0.1", + "content-type": "^1.0.5", + "cors": "^2.8.5", + "cross-spawn": "^7.0.5", + "eventsource": "^3.0.2", + "eventsource-parser": "^3.0.0", + "express": "^5.2.1", + "express-rate-limit": "^8.2.1", + "hono": "^4.11.4", + "jose": "^6.1.3", + "json-schema-typed": "^8.0.2", + "pkce-challenge": "^5.0.0", + "raw-body": "^3.0.0", + "zod": "^3.25 || ^4.0", + "zod-to-json-schema": "^3.25.1" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "@cfworker/json-schema": "^4.1.1", + "zod": "^3.25 || ^4.0" + }, + "peerDependenciesMeta": { + "@cfworker/json-schema": { + "optional": true + }, + "zod": { + "optional": false + } + } + }, + "node_modules/@modelcontextprotocol/sdk/node_modules/eventsource-parser": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.8.tgz", + "integrity": "sha512-70QWGkr4snxr0OXLRWsFLeRBIRPuQOvt4s8QYjmUlmlkyTZkRqS7EDVRZtzU3TiyDbXSzaOeF0XUKy8PchzukQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@mongodb-js/saslprep": { + "version": "1.4.11", + "resolved": "https://registry.npmjs.org/@mongodb-js/saslprep/-/saslprep-1.4.11.tgz", + "integrity": "sha512-o9rAHc0IpIjuPSxRutWpE1F62x7n+4mVS4rCNHkzhIUMQcc18bb6xEq5wd2NdN0WjepIyXIppRshYI2kQDOZVA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "sparse-bitfield": "^3.0.3" + } + }, + "node_modules/@msgpack/msgpack": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/@msgpack/msgpack/-/msgpack-3.1.3.tgz", + "integrity": "sha512-47XIizs9XZXvuJgoaJUIE2lFoID8ugvc0jzSHP+Ptfk8nTbnR8g788wv48N03Kx0UkAv559HWRQ3yzOgzlRNUA==", + "dev": true, + "license": "ISC", + "optional": true, + "engines": { + "node": ">= 18" + } + }, + "node_modules/@napi-rs/canvas": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas/-/canvas-0.1.80.tgz", + "integrity": "sha512-DxuT1ClnIPts1kQx8FBmkk4BQDTfI5kIzywAaMjQSXfNnra5UFU9PwurXrl+Je3bJ6BGsp/zmshVVFbCmyI+ww==", + "dev": true, + "license": "MIT", + "optional": true, + "workspaces": [ + "e2e/*" + ], + "engines": { + "node": ">= 10" + }, + "optionalDependencies": { + "@napi-rs/canvas-android-arm64": "0.1.80", + "@napi-rs/canvas-darwin-arm64": "0.1.80", + "@napi-rs/canvas-darwin-x64": "0.1.80", + "@napi-rs/canvas-linux-arm-gnueabihf": "0.1.80", + "@napi-rs/canvas-linux-arm64-gnu": "0.1.80", + "@napi-rs/canvas-linux-arm64-musl": "0.1.80", + "@napi-rs/canvas-linux-riscv64-gnu": "0.1.80", + "@napi-rs/canvas-linux-x64-gnu": "0.1.80", + "@napi-rs/canvas-linux-x64-musl": "0.1.80", + "@napi-rs/canvas-win32-x64-msvc": "0.1.80" + } + }, + "node_modules/@napi-rs/canvas-android-arm64": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-android-arm64/-/canvas-android-arm64-0.1.80.tgz", + "integrity": "sha512-sk7xhN/MoXeuExlggf91pNziBxLPVUqF2CAVnB57KLG/pz7+U5TKG8eXdc3pm0d7Od0WreB6ZKLj37sX9muGOQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-darwin-arm64": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-darwin-arm64/-/canvas-darwin-arm64-0.1.80.tgz", + "integrity": "sha512-O64APRTXRUiAz0P8gErkfEr3lipLJgM6pjATwavZ22ebhjYl/SUbpgM0xcWPQBNMP1n29afAC/Us5PX1vg+JNQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-darwin-x64": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-darwin-x64/-/canvas-darwin-x64-0.1.80.tgz", + "integrity": "sha512-FqqSU7qFce0Cp3pwnTjVkKjjOtxMqRe6lmINxpIZYaZNnVI0H5FtsaraZJ36SiTHNjZlUB69/HhxNDT1Aaa9vA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-linux-arm-gnueabihf": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-linux-arm-gnueabihf/-/canvas-linux-arm-gnueabihf-0.1.80.tgz", + "integrity": "sha512-eyWz0ddBDQc7/JbAtY4OtZ5SpK8tR4JsCYEZjCE3dI8pqoWUC8oMwYSBGCYfsx2w47cQgQCgMVRVTFiiO38hHQ==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-linux-arm64-gnu": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-linux-arm64-gnu/-/canvas-linux-arm64-gnu-0.1.80.tgz", + "integrity": "sha512-qwA63t8A86bnxhuA/GwOkK3jvb+XTQaTiVML0vAWoHyoZYTjNs7BzoOONDgTnNtr8/yHrq64XXzUoLqDzU+Uuw==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-linux-arm64-musl": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-linux-arm64-musl/-/canvas-linux-arm64-musl-0.1.80.tgz", + "integrity": "sha512-1XbCOz/ymhj24lFaIXtWnwv/6eFHXDrjP0jYkc6iHQ9q8oXKzUX1Lc6bu+wuGiLhGh2GS/2JlfORC5ZcXimRcg==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-linux-riscv64-gnu": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-linux-riscv64-gnu/-/canvas-linux-riscv64-gnu-0.1.80.tgz", + "integrity": "sha512-XTzR125w5ZMs0lJcxRlS1K3P5RaZ9RmUsPtd1uGt+EfDyYMu4c6SEROYsxyatbbu/2+lPe7MPHOO/0a0x7L/gw==", + "cpu": [ + "riscv64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-linux-x64-gnu": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-linux-x64-gnu/-/canvas-linux-x64-gnu-0.1.80.tgz", + "integrity": "sha512-BeXAmhKg1kX3UCrJsYbdQd3hIMDH/K6HnP/pG2LuITaXhXBiNdh//TVVVVCBbJzVQaV5gK/4ZOCMrQW9mvuTqA==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-linux-x64-musl": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-linux-x64-musl/-/canvas-linux-x64-musl-0.1.80.tgz", + "integrity": "sha512-x0XvZWdHbkgdgucJsRxprX/4o4sEed7qo9rCQA9ugiS9qE2QvP0RIiEugtZhfLH3cyI+jIRFJHV4Fuz+1BHHMg==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@napi-rs/canvas-win32-x64-msvc": { + "version": "0.1.80", + "resolved": "https://registry.npmjs.org/@napi-rs/canvas-win32-x64-msvc/-/canvas-win32-x64-msvc-0.1.80.tgz", + "integrity": "sha512-Z8jPsM6df5V8B1HrCHB05+bDiCxjE9QA//3YrkKIdVDEwn5RKaqOxCJDRJkl48cJbylcrJbW4HxZbTte8juuPg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@nodable/entities": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@nodable/entities/-/entities-2.1.0.tgz", + "integrity": "sha512-nyT7T3nbMyBI/lvr6L5TyWbFJAI9FTgVRakNoBqCD+PmID8DzFrrNdLLtHMwMszOtqZa8PAOV24ZqDnQrhQINA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/nodable" + } + ], + "license": "MIT" + }, + "node_modules/@openai/codex": { + "version": "0.128.0", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0.tgz", + "integrity": "sha512-+xp6ODmFfBNnexIWRHApEaPXot2j6gyM8A5we/5IS/uY4eYHj4arETct4hQ5M4eO+MK7JY3ZU4xhuobhlysr0A==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "bin": { + "codex": "bin/codex.js" + }, + "engines": { + "node": ">=16" + }, + "optionalDependencies": { + "@openai/codex-darwin-arm64": "npm:@openai/codex@0.128.0-darwin-arm64", + "@openai/codex-darwin-x64": "npm:@openai/codex@0.128.0-darwin-x64", + "@openai/codex-linux-arm64": "npm:@openai/codex@0.128.0-linux-arm64", + "@openai/codex-linux-x64": "npm:@openai/codex@0.128.0-linux-x64", + "@openai/codex-win32-arm64": "npm:@openai/codex@0.128.0-win32-arm64", + "@openai/codex-win32-x64": "npm:@openai/codex@0.128.0-win32-x64" + } + }, + "node_modules/@openai/codex-darwin-arm64": { + "name": "@openai/codex", + "version": "0.128.0-darwin-arm64", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0-darwin-arm64.tgz", + "integrity": "sha512-w+6zohfHx/kHBdles/CyFKaY57u9I3nK8QI9+NrdwMliKA0b7xn13yblRNkMpe09j6vL1oAWoxYsMOQ/vjBGug==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=16" + } + }, + "node_modules/@openai/codex-darwin-x64": { + "name": "@openai/codex", + "version": "0.128.0-darwin-x64", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0-darwin-x64.tgz", + "integrity": "sha512-SDbn6fO22Puy8xmMIbZi4f2znMrUEPwABApke4mo+4ihaauwuVjeqzXvW5SPJz5ty/bG11/mSupQgReT7T8BBw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=16" + } + }, + "node_modules/@openai/codex-linux-arm64": { + "name": "@openai/codex", + "version": "0.128.0-linux-arm64", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0-linux-arm64.tgz", + "integrity": "sha512-+SvH73H60qvCXFuQGP/EsmR//s1hHMBR22PvJkXvM/hdnTIGucx+JqRUjAWdmmQ1IU6j3kgwVvdLW/6ICB+M6w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=16" + } + }, + "node_modules/@openai/codex-linux-x64": { + "name": "@openai/codex", + "version": "0.128.0-linux-x64", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0-linux-x64.tgz", + "integrity": "sha512-2lnSPA05CRRuKAzFW8BCmmNCSieDcToLwfC2ALLbBYilGLgzhRibjlDglK9F1BkEzfohSSWJu4PBbRu/aG60lQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=16" + } + }, + "node_modules/@openai/codex-sdk": { + "version": "0.128.0", + "resolved": "https://registry.npmjs.org/@openai/codex-sdk/-/codex-sdk-0.128.0.tgz", + "integrity": "sha512-Eao0LLA5x90qwU6SXYd21h4KxdCef1WpCvHFgKdbqzWMJ79lUvguGDGvx1RheP+zTdKGxJfJ6dulI5wSXoUBhQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@openai/codex": "0.128.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@openai/codex-win32-arm64": { + "name": "@openai/codex", + "version": "0.128.0-win32-arm64", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0-win32-arm64.tgz", + "integrity": "sha512-ECJvsqmYFdA9pn42xxK3Odp/G16AjmBW0BglX8L0PwPjqbstbmlew9bfHf7xvL+SNfNl4NmyotW0+RNo1phgaA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=16" + } + }, + "node_modules/@openai/codex-win32-x64": { + "name": "@openai/codex", + "version": "0.128.0-win32-x64", + "resolved": "https://registry.npmjs.org/@openai/codex/-/codex-0.128.0-win32-x64.tgz", + "integrity": "sha512-k3jmUAFrzkUtvjGTXvSKjQqJLLlzjxp/VoHJDYedgmXUn6j70HxK38IwapzmnYfiBiTuzETvGwjXHzZgzKjhoQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=16" + } + }, + "node_modules/@opencode-ai/sdk": { + "version": "1.15.5", + "resolved": "https://registry.npmjs.org/@opencode-ai/sdk/-/sdk-1.15.5.tgz", + "integrity": "sha512-ozJuEmXzrOvia5n0L1KAuvpyf9ESGmTk1FiPhn0RK5X1whbzjlTXL0NAxqNCEkqETxL35jS1KHArEiTpvtJ6FQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "cross-spawn": "7.0.6" + } + }, + "node_modules/@opentelemetry/api": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.1.tgz", + "integrity": "sha512-gLyJlPHPZYdAk1JENA9LeHejZe1Ti77/pTeFm/nMXmQH/HFZlcS/O2XJB+L8fkbrNSqhdtlvjBVjxwUYanNH5Q==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/@opentelemetry/api-logs": { + "version": "0.216.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.216.0.tgz", + "integrity": "sha512-KmGTgvxTJ0J01d4mOeX1wMV5NUTNf9HebIuOOGDfIn0a/IrnXIQbOnlylDyl9tkDv4h0DUpdI/GqCdLzfTkUXg==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.3.0" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/@opentelemetry/context-async-hooks": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/context-async-hooks/-/context-async-hooks-2.7.1.tgz", + "integrity": "sha512-OPFBYuXEn1E4ja3Y6eeA7O+ZnLBNcXTV5Cgsn1VaqBZ6hC5FnpZPLBNme1LJY8ZtF4aOujPKFoeWN4ik487KuQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/core": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.7.1.tgz", + "integrity": "sha512-QAqIj32AtK6+pEVNG7EOVxHdE06RP+FM5qpiEJ4RtDcFIqKUZHYhl7/7UY5efhwmwNAg7j8QbJVBLxMerc0+gw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/exporter-trace-otlp-http": { + "version": "0.216.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-http/-/exporter-trace-otlp-http-0.216.0.tgz", + "integrity": "sha512-DhWjvj0PUPFwFnhOEivpum8sJzj6FTuyx88zff+oHVLUhfd6cLyw4AIai/F4j0PZqYZBFuMT/OTMUd9wdXnBEQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.7.1", + "@opentelemetry/otlp-exporter-base": "0.216.0", + "@opentelemetry/otlp-transformer": "0.216.0", + "@opentelemetry/resources": "2.7.1", + "@opentelemetry/sdk-trace-base": "2.7.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/otlp-exporter-base": { + "version": "0.216.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-exporter-base/-/otlp-exporter-base-0.216.0.tgz", + "integrity": "sha512-sSnvb5f+FYa4mfYxj03rmmUh+aDwo3jok62dgIWUDw8ZCUPzEbgtv/YhZyKUSlKNNey7Uc5xmJgmtTLLIV6UDQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.7.1", + "@opentelemetry/otlp-transformer": "0.216.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/otlp-transformer": { + "version": "0.216.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.216.0.tgz", + "integrity": "sha512-g4Rb6sAsxQAo11eDjixfKxelruBsQFdJ8Wo23FCj7D6OXbidgXMu2xaRSYs4RdlomzAXSJuc86RcS3xmE8A6uA==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.216.0", + "@opentelemetry/core": "2.7.1", + "@opentelemetry/resources": "2.7.1", + "@opentelemetry/sdk-logs": "0.216.0", + "@opentelemetry/sdk-metrics": "2.7.1", + "@opentelemetry/sdk-trace-base": "2.7.1", + "protobufjs": "8.0.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/otlp-transformer/node_modules/protobufjs": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-8.0.1.tgz", + "integrity": "sha512-NWWCCscLjs+cOKF/s/XVNFRW7Yih0fdH+9brffR5NZCy8k42yRdl5KlWKMVXuI1vfCoy4o1z80XR/W/QUb3V3w==", + "dev": true, + "hasInstallScript": true, + "license": "BSD-3-Clause", + "dependencies": { + "@protobufjs/aspromise": "^1.1.2", + "@protobufjs/base64": "^1.1.2", + "@protobufjs/codegen": "^2.0.4", + "@protobufjs/eventemitter": "^1.1.0", + "@protobufjs/fetch": "^1.1.0", + "@protobufjs/float": "^1.0.2", + "@protobufjs/inquire": "^1.1.0", + "@protobufjs/path": "^1.1.2", + "@protobufjs/pool": "^1.1.0", + "@protobufjs/utf8": "^1.1.0", + "@types/node": ">=13.7.0", + "long": "^5.0.0" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/@opentelemetry/resources": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.7.1.tgz", + "integrity": "sha512-DeT6KKolmC4e/dRQvMQ/RwlnzhaqeiFOXY5ngoOPJ07GgVVKxZOg9EcrNZb5aTzUn+iCrJldAgOfQm1O/QfPAQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.7.1", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/sdk-logs": { + "version": "0.216.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.216.0.tgz", + "integrity": "sha512-KB3rcwQuitq0JbbsCcNdqMhRJX3kArAYz/ovb0jGRaBQAIrt2roik3xQXuhYxS37zx0jSkUZcJu1z3Y2UCxbDA==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.216.0", + "@opentelemetry/core": "2.7.1", + "@opentelemetry/resources": "2.7.1", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.4.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/sdk-metrics": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.7.1.tgz", + "integrity": "sha512-MpDJdkiFDs3Pm1RHO3KByuZbuBdJEXEAkiC0+yJdsZGVCdf1RpHR6n+LHDcS7ffmfrt5kVCzJSCfm4z2C7v0uQ==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.7.1", + "@opentelemetry/resources": "2.7.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.9.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.7.1.tgz", + "integrity": "sha512-NAYIlsF8MPUsKqJMiDQJTMPOmlbawC1Iz/omMLygZ1C9am8fTKYjTaI+OZM+WTY3t3Glo0wnOg/6/pac6RGPPw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.7.1", + "@opentelemetry/resources": "2.7.1", + "@opentelemetry/semantic-conventions": "^1.29.0" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/sdk-trace-node": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-node/-/sdk-trace-node-2.7.1.tgz", + "integrity": "sha512-pCpQxU68lV+I9s9svqMyVu5iHdDDUnqUpSxqwyCU8A9ejEsSnMPCbearwsUO4yk08ZJzAIUCFuReMdVQvHrdvg==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/context-async-hooks": "2.7.1", + "@opentelemetry/core": "2.7.1", + "@opentelemetry/sdk-trace-base": "2.7.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.10.0" + } + }, + "node_modules/@opentelemetry/semantic-conventions": { + "version": "1.41.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.41.1.tgz", + "integrity": "sha512-/UhIkaZgPutTFmQ7RnIJGgDXZmtEJ7Dvi86xNTFWcnRxVRNk/aotsqDJYeEvDP+FSMB2SdW+pQzNMcWP0rwuNA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=14" + } + }, + "node_modules/@playwright/browser-chromium": { + "version": "1.60.0", + "resolved": "https://registry.npmjs.org/@playwright/browser-chromium/-/browser-chromium-1.60.0.tgz", + "integrity": "sha512-0ND2pbNWKJYwhlA1LNaDC3DP2x7eguQkQF7Ga7XAlJV0AFieqYNRw/E+gaY9BpSFr1TYwfwXQv1bHq5AK9nbvA==", + "dev": true, + "hasInstallScript": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "playwright-core": "1.60.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@posthog/core": { + "version": "1.23.1", + "resolved": "https://registry.npmjs.org/@posthog/core/-/core-1.23.1.tgz", + "integrity": "sha512-GViD5mOv/mcbZcyzz3z9CS0R79JzxVaqEz4sP5Dsea178M/j3ZWe6gaHDZB9yuyGfcmIMQ/8K14yv+7QrK4sQQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "cross-spawn": "^7.0.6" + } + }, + "node_modules/@protobufjs/aspromise": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/aspromise/-/aspromise-1.1.2.tgz", + "integrity": "sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/base64": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/base64/-/base64-1.1.2.tgz", + "integrity": "sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/codegen": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@protobufjs/codegen/-/codegen-2.0.5.tgz", + "integrity": "sha512-zgXFLzW3Ap33e6d0Wlj4MGIm6Ce8O89n/apUaGNB/jx+hw+ruWEp7EwGUshdLKVRCxZW12fp9r40E1mQrf/34g==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/eventemitter": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/eventemitter/-/eventemitter-1.1.0.tgz", + "integrity": "sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/fetch": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@protobufjs/fetch/-/fetch-1.1.1.tgz", + "integrity": "sha512-GpptLrs57adMSuHi3VNj0mAF8dwh36LMaYF6XyJ6JMWlVsc+t42tm1HSEDmOs3A8fC9yyeisgLhsTVQokOZ0zw==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "@protobufjs/aspromise": "^1.1.1" + } + }, + "node_modules/@protobufjs/float": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@protobufjs/float/-/float-1.0.2.tgz", + "integrity": "sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/inquire": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/inquire/-/inquire-1.1.2.tgz", + "integrity": "sha512-pa0vFRuws4wkvaXKK1uXZMAwAX4/t8ANaJo45iw/oQHNQ9q5xUzwgFmVJGXiga2BeN+zpX7Vf9vmsiIa2J+MUw==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/path": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/path/-/path-1.1.2.tgz", + "integrity": "sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/pool": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/pool/-/pool-1.1.0.tgz", + "integrity": "sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@protobufjs/utf8": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@protobufjs/utf8/-/utf8-1.1.1.tgz", + "integrity": "sha512-oOAWABowe8EAbMyWKM0tYDKi8Yaox52D+HWZhAIJqQXbqe0xI/GV7FhLWqlEKreMkfDjshR5FKgi3mnle0h6Eg==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/@redis/bloom": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/@redis/bloom/-/bloom-5.12.1.tgz", + "integrity": "sha512-PUUfv+ms7jgPSBVoo/DN4AkPHj4D5TZSd6SbJX7egzBplkYUcKmHRE8RKia7UtZ8bSQbLguLvxVO+asKtQfZWA==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 18.19.0" + }, + "peerDependencies": { + "@redis/client": "^5.12.1" + } + }, + "node_modules/@redis/client": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/@redis/client/-/client-5.12.1.tgz", + "integrity": "sha512-7aPGWeqA3uFm43o19umzdl16CEjK/JQGtSXVPevplTaOU3VJA/rseBC1QvYUz9lLDIMBimc4SW/zrW4S89BaCA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "cluster-key-slot": "1.1.2" + }, + "engines": { + "node": ">= 18.19.0" + }, + "peerDependencies": { + "@node-rs/xxhash": "^1.1.0", + "@opentelemetry/api": ">=1 <2" + }, + "peerDependenciesMeta": { + "@node-rs/xxhash": { + "optional": true + }, + "@opentelemetry/api": { + "optional": true + } + } + }, + "node_modules/@redis/json": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/@redis/json/-/json-5.12.1.tgz", + "integrity": "sha512-eOze75esLve4vfqDel7aMX08CNaiLLQS2fV8mpRN9NxPe1rVR4vQyYiW/OgtGUysF6QOr9ANhfxABKNOJfXdKg==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 18.19.0" + }, + "peerDependencies": { + "@redis/client": "^5.12.1" + } + }, + "node_modules/@redis/search": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/@redis/search/-/search-5.12.1.tgz", + "integrity": "sha512-ItlxbxC9cKI6IU1TLWoczwJCRb6TdmkEpWv05UrPawqaAnWGRu3rcIqsc5vN483T2fSociuyV1UkWIL5I4//2w==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 18.19.0" + }, + "peerDependencies": { + "@redis/client": "^5.12.1" + } + }, + "node_modules/@redis/time-series": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/@redis/time-series/-/time-series-5.12.1.tgz", + "integrity": "sha512-c6JL6E3EcZJuNqKFz+KM+l9l5mpcQiKvTwgA3blt5glWJ8hjDk0yeHN3beE/MpqYIQ8UEX44ItQzgkE/gCBELQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 18.19.0" + }, + "peerDependencies": { + "@redis/client": "^5.12.1" + } + }, + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.60.4.tgz", + "integrity": "sha512-Boiz5+MsaROEWDf+GGEwF8VMHGhlUoQMtIPjOgA5fv4osupqTVnJteQNKJwUcnUog2G55jYXH7KZFFiJe0TEzQ==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@sec-ant/readable-stream": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/@sec-ant/readable-stream/-/readable-stream-0.4.1.tgz", + "integrity": "sha512-831qok9r2t8AlxLko40y2ebgSDhenenCatLVeW/uBtnHPyhHOvG0C7TvfgecV+wHzIm5KUICgzmVpWS+IMEAeg==", + "dev": true, + "license": "MIT" + }, + "node_modules/@simple-git/args-pathspec": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@simple-git/args-pathspec/-/args-pathspec-1.0.3.tgz", + "integrity": "sha512-ngJMaHlsWDTfjyq9F3VIQ8b7NXbBLq5j9i5bJ6XLYtD6qlDXT7fdKY2KscWWUF8t18xx052Y/PUO1K1TRc9yKA==", + "dev": true, + "license": "MIT" + }, + "node_modules/@simple-git/argv-parser": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@simple-git/argv-parser/-/argv-parser-1.1.1.tgz", + "integrity": "sha512-Q9lBcfQ+VQCpQqGJFHe5yooOS5hGdLFFbJ5R+R5aDsnkPCahtn1hSkMcORX65J2Z5lxSkD0lQorMsncuBQxYUw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@simple-git/args-pathspec": "^1.0.3" + } + }, + "node_modules/@sindresorhus/merge-streams": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/merge-streams/-/merge-streams-4.0.0.tgz", + "integrity": "sha512-tlqY9xq5ukxTUZBmoOp+m61cqwQD5pHJtFY3Mn8CA8ps6yghLH/Hw8UPdqg4OLmFW3IFlcXnQNmo/dh8HzXYIQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@slack/logger": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/@slack/logger/-/logger-4.0.1.tgz", + "integrity": "sha512-6cmdPrV/RYfd2U0mDGiMK8S7OJqpCTm7enMLRR3edccsPX8j7zXTLnaEF4fhxxJJTAIOil6+qZrnUPTuaLvwrQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@types/node": ">=18" + }, + "engines": { + "node": ">= 18", + "npm": ">= 8.6.0" + } + }, + "node_modules/@slack/types": { + "version": "2.21.1", + "resolved": "https://registry.npmjs.org/@slack/types/-/types-2.21.1.tgz", + "integrity": "sha512-I8vmSjNYWsaxuWPx6dz4yeh0h7vRBWbgAMK14LEmblbZ404BtrPbXs6jDPx4cYgGf8msDGF4A9opLZBu21FViQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 12.13.0", + "npm": ">= 6.12.0" + } + }, + "node_modules/@slack/web-api": { + "version": "7.16.0", + "resolved": "https://registry.npmjs.org/@slack/web-api/-/web-api-7.16.0.tgz", + "integrity": "sha512-68SAV77uuGKuhyyaRytX8UijVnqSLsTSKslGXw17cjQYXn+jtNl7gbaEjHgC5x2rhCuFdahBrEC2VCLppbzReg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@slack/logger": "^4.0.1", + "@slack/types": "^2.21.0", + "@types/node": ">=18", + "@types/retry": "0.12.0", + "axios": "^1.16.0", + "eventemitter3": "^5.0.1", + "form-data": "^4.0.4", + "is-electron": "2.2.2", + "is-stream": "^2", + "p-queue": "^6", + "p-retry": "^4", + "retry": "^0.13.1" + }, + "engines": { + "node": ">= 18", + "npm": ">= 8.6.0" + } + }, + "node_modules/@smithy/core": { + "version": "3.24.3", + "resolved": "https://registry.npmjs.org/@smithy/core/-/core-3.24.3.tgz", + "integrity": "sha512-Ep/7tPamGY8mgESE3LyLKtxJyy6U52WWAqr/3wial47Sj4u3PiIF73AOGI27UyLy9duTkhZbgzodOfLV4TduZg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@aws-crypto/crc32": "5.2.0", + "@smithy/types": "^4.14.2", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@smithy/credential-provider-imds": { + "version": "4.3.3", + "resolved": "https://registry.npmjs.org/@smithy/credential-provider-imds/-/credential-provider-imds-4.3.3.tgz", + "integrity": "sha512-I2Bti0DKFo2IJyN28ijCsx51BAumEYR4/1yZ1FXyBygy9MqbnMqCev4JPth/MbpRfBSRAX35hITSnAdJRo1u5w==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/core": "^3.24.3", + "@smithy/types": "^4.14.2", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@smithy/fetch-http-handler": { + "version": "5.4.3", + "resolved": "https://registry.npmjs.org/@smithy/fetch-http-handler/-/fetch-http-handler-5.4.3.tgz", + "integrity": "sha512-F+DRf8IJazRJgYog2A/yJK7eYVc0rqTlRzO+5ZxjJd4WkZoKz0IJRncf7G6t1pdVT3kryJcwuTFhN1c5m6N47A==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/core": "^3.24.3", + "@smithy/types": "^4.14.2", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@smithy/is-array-buffer": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@smithy/is-array-buffer/-/is-array-buffer-2.2.0.tgz", + "integrity": "sha512-GGP3O9QFD24uGeAXYUjwSTXARoqpZykHadOmA8G5vfJPK0/DC67qa//0qvqrJzL1xc8WQWX7/yc7fwudjPHPhA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@smithy/node-http-handler": { + "version": "4.7.3", + "resolved": "https://registry.npmjs.org/@smithy/node-http-handler/-/node-http-handler-4.7.3.tgz", + "integrity": "sha512-/jPhevcTFPMVl6KNjbaI47iOg1zxC7IsnX4PQDGVZKMFceOXtB8IEYaB7a9VvkP/3oC60WzTeKocvSI7vLT0vA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/core": "^3.24.3", + "@smithy/types": "^4.14.2", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@smithy/signature-v4": { + "version": "5.4.3", + "resolved": "https://registry.npmjs.org/@smithy/signature-v4/-/signature-v4-5.4.3.tgz", + "integrity": "sha512-53+75QuPl6DL+ct6vVEB51FDO5oulXr20TPV46VvJZg76lIlXNWfxi8j+G2V/t0I2qxCBOa3vX/8bmjrpFVo9g==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/core": "^3.24.3", + "@smithy/types": "^4.14.2", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@smithy/types": { + "version": "4.14.2", + "resolved": "https://registry.npmjs.org/@smithy/types/-/types-4.14.2.tgz", + "integrity": "sha512-P+otAxbV4CqBybp7EkcJCrig63yE2E7PuNVOmilVMRcx/O+QDzGULTrKsq4DV13gSfak9ObPrWaHl/9bL5YcWw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/@smithy/util-buffer-from": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@smithy/util-buffer-from/-/util-buffer-from-2.2.0.tgz", + "integrity": "sha512-IJdWBbTcMQ6DA0gdNhh/BwrLkDR+ADW5Kr1aZmd4k3DIF6ezMV4R2NIAmT08wQJ3yUK82thHWmC/TnK/wpMMIA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/is-array-buffer": "^2.2.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@smithy/util-utf8": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/@smithy/util-utf8/-/util-utf8-2.3.0.tgz", + "integrity": "sha512-R8Rdn8Hy72KKcebgLiv8jQcQkXoLMOGGv5uI1/k0l+snqkOzQ1R0ChUBCxWMlBsFMekWjq0wRudIweFs7sKT5A==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@smithy/util-buffer-from": "^2.2.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@so-ric/colorspace": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/@so-ric/colorspace/-/colorspace-1.1.6.tgz", + "integrity": "sha512-/KiKkpHNOBgkFJwu9sh48LkHSMYGyuTcSFK/qMBdnOAlrRJzRSXAOFB5qwzaVQuDl8wAvHVMkaASQDReTahxuw==", + "dev": true, + "license": "MIT", + "dependencies": { + "color": "^5.0.2", + "text-hex": "1.0.x" + } + }, + "node_modules/@socket.io/component-emitter": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@socket.io/component-emitter/-/component-emitter-3.1.2.tgz", + "integrity": "sha512-9BCxFwvbGg/RsZK9tjXd8s4UcwR0MWeFQ1XEKIQVVvAGJyINdrqKMcTRyLoK8Rse1GjzLV9cwjWV1olXRWEXVA==", + "dev": true, + "license": "MIT" + }, + "node_modules/@standard-schema/spec": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@standard-schema/spec/-/spec-1.1.0.tgz", + "integrity": "sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==", + "dev": true, + "license": "MIT" + }, + "node_modules/@swc/core": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core/-/core-1.15.33.tgz", + "integrity": "sha512-jOlwnFV2xhuuZeAUILGFULeR6vDPfijEJ57evfocwznQldLU3w2cZ9bSDryY9ip+AsM3r1NJKzf47V2NXebkeQ==", + "dev": true, + "hasInstallScript": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@swc/counter": "^0.1.3", + "@swc/types": "^0.1.26" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/swc" + }, + "optionalDependencies": { + "@swc/core-darwin-arm64": "1.15.33", + "@swc/core-darwin-x64": "1.15.33", + "@swc/core-linux-arm-gnueabihf": "1.15.33", + "@swc/core-linux-arm64-gnu": "1.15.33", + "@swc/core-linux-arm64-musl": "1.15.33", + "@swc/core-linux-ppc64-gnu": "1.15.33", + "@swc/core-linux-s390x-gnu": "1.15.33", + "@swc/core-linux-x64-gnu": "1.15.33", + "@swc/core-linux-x64-musl": "1.15.33", + "@swc/core-win32-arm64-msvc": "1.15.33", + "@swc/core-win32-ia32-msvc": "1.15.33", + "@swc/core-win32-x64-msvc": "1.15.33" + }, + "peerDependencies": { + "@swc/helpers": ">=0.5.17" + }, + "peerDependenciesMeta": { + "@swc/helpers": { + "optional": true + } + } + }, + "node_modules/@swc/core-darwin-arm64": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-darwin-arm64/-/core-darwin-arm64-1.15.33.tgz", + "integrity": "sha512-N+L0uXhuO7FIfzqwgxmzv0zIpV0qEp8wPX3QQs2p4atjMoywup2JTeDlXPw+z9pWJGCae3JjM+tZ6myclI+2gA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-darwin-x64": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-darwin-x64/-/core-darwin-x64-1.15.33.tgz", + "integrity": "sha512-/Il4QHSOhV4FekbsDtkrNmKbsX26oSysvgrRswa/RYOHXAkwXDbB4jaeKq6PsJLSPkzJ2KzQ061gtBnk0vNHfA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-arm-gnueabihf": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-arm-gnueabihf/-/core-linux-arm-gnueabihf-1.15.33.tgz", + "integrity": "sha512-C64hBnBxq4viOPQ8hlx+2lJ23bzZBGnjw7ryALmS+0Q3zHmwO8lw1/DArLENw4Q18/0w5wdEO1k3m1wWNtKGqQ==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "Apache-2.0", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-arm64-gnu": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-arm64-gnu/-/core-linux-arm64-gnu-1.15.33.tgz", + "integrity": "sha512-TRJfnJbX3jqpxRDRoieMzRiCBS5jOmXNb3iQXmcgjFEHKLnAgK1RZRU8Cq1MsPqO4jAJp/ld1G4O3fXuxv85uw==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-arm64-musl": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-arm64-musl/-/core-linux-arm64-musl-1.15.33.tgz", + "integrity": "sha512-il7tYM+CpUNzieQbwAjFT1P8zqAhmGWNAGhQZBnxurXZ0aNn+5nqYFTEUKNZl7QibtT0uQXzTZrNGHCIj6Y1Og==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-ppc64-gnu": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-ppc64-gnu/-/core-linux-ppc64-gnu-1.15.33.tgz", + "integrity": "sha512-ZtNBwN0Z7CFj9Il0FcPaKdjgP7URyKu/3RfH46vq+0paOBqLj4NYldD6Qo//Duif/7IOtAraUfDOmp0PLAufog==", + "cpu": [ + "ppc64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-s390x-gnu": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-s390x-gnu/-/core-linux-s390x-gnu-1.15.33.tgz", + "integrity": "sha512-De1IyajoOmhOYYjw/lx66bKlyDpHZTueqwpDrWgf5O7T6d1ODeJJO9/OqMBmrBQc5C+dNnlmIufHsp4QVCWufA==", + "cpu": [ + "s390x" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-x64-gnu": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-x64-gnu/-/core-linux-x64-gnu-1.15.33.tgz", + "integrity": "sha512-mGTH0YxmUN+x6vRN/I6NOk5X0ogNktkwPnJ94IMvR7QjhRDwL0O8RXEDhyUM0YtwWrryBOqaJQBX4zruxEPRGw==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-linux-x64-musl": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-linux-x64-musl/-/core-linux-x64-musl-1.15.33.tgz", + "integrity": "sha512-hj628ZkSEJf6zMf5VMbYrG2O6QqyTIp2qwY6VlCjvIa9lAEZ5c2lfPblCLVGYubTeLJDxadLB/CxqQYOQABeEQ==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-win32-arm64-msvc": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-win32-arm64-msvc/-/core-win32-arm64-msvc-1.15.33.tgz", + "integrity": "sha512-GV2oohtN2/5+KSccl86VULu3aT+LrISC8uzgSq0FRnikpD+Zwc+sBlXmoKQ+Db6jI57ITUOIB8jRkdGMABC29g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-win32-ia32-msvc": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-win32-ia32-msvc/-/core-win32-ia32-msvc-1.15.33.tgz", + "integrity": "sha512-gtyvzSNR8DHKfFEA2uqb8Ld1myqi6uEg2jyeUq3ikn5ytYs7H8RpZYC8mdy4NXr8hfcdJfCLXPlYaqqfBXpoEQ==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/core-win32-x64-msvc": { + "version": "1.15.33", + "resolved": "https://registry.npmjs.org/@swc/core-win32-x64-msvc/-/core-win32-x64-msvc-1.15.33.tgz", + "integrity": "sha512-d6fRqQSkJI+kmMEBWaDQ7TMl8+YjLYbwRUPZQ9DY0ORBJeTzOrG0twvfvlZ2xgw6jA0ScQKgfBm4vHLSLl5Hqg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 AND MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=10" + } + }, + "node_modules/@swc/counter": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/@swc/counter/-/counter-0.1.3.tgz", + "integrity": "sha512-e2BR4lsJkkRlKZ/qCHPw9ZaSxc0MVUd7gtbtaB7aMvHeJVYe8sOB8DBZkP2DtISHGSku9sCK6T6cnY0CtXrOCQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true + }, + "node_modules/@swc/types": { + "version": "0.1.26", + "resolved": "https://registry.npmjs.org/@swc/types/-/types-0.1.26.tgz", + "integrity": "sha512-lyMwd7WGgG79RS7EERZV3T8wMdmPq3xwyg+1nmAM64kIhx5yl+juO2PYIHb7vTiPgPCj8LYjsNV2T5wiQHUEaw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@swc/counter": "^0.1.3" + } + }, + "node_modules/@tokenizer/inflate": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/@tokenizer/inflate/-/inflate-0.4.1.tgz", + "integrity": "sha512-2mAv+8pkG6GIZiF1kNg1jAjh27IDxEPKwdGul3snfztFerfPGI1LjDezZp3i7BElXompqEtPmoPx6c2wgtWsOA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "debug": "^4.4.3", + "token-types": "^6.1.1" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Borewit" + } + }, + "node_modules/@tokenizer/inflate/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/@tokenizer/inflate/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", + "optional": true + }, + "node_modules/@tokenizer/token": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/@tokenizer/token/-/token-0.3.0.tgz", + "integrity": "sha512-OvjF+z51L3ov0OyAU0duzsYuvO01PH7x4t6DJx+guahgTnBHkhJdG7soQeTSFLWN3efnHyibZ4Z8l2EuWwJN3A==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/@types/cors": { + "version": "2.8.19", + "resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.19.tgz", + "integrity": "sha512-mFNylyeyqN93lfe/9CSxOGREz8cpzAhH+E93xJ4xWQf62V8sQ/24reV2nyzUWM6H6Xji+GGHpkbLe7pVoUEskg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/debug": { + "version": "4.1.12", + "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz", + "integrity": "sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@types/ms": "*" + } + }, + "node_modules/@types/ms": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@types/ms/-/ms-2.1.0.tgz", + "integrity": "sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/@types/node": { + "version": "25.9.1", + "resolved": "https://registry.npmjs.org/@types/node/-/node-25.9.1.tgz", + "integrity": "sha512-xfrlY7UD5rMJk3ZVJP8BNzS28J36YJg+xp+LPXV1TdWxr8uMH5A860QNxYDGQe/ylDSgjxE52Q9VnO7p75tJxg==", + "dev": true, + "license": "MIT", + "dependencies": { + "undici-types": ">=7.24.0 <7.24.7" + } + }, + "node_modules/@types/pegjs": { + "version": "0.10.6", + "resolved": "https://registry.npmjs.org/@types/pegjs/-/pegjs-0.10.6.tgz", + "integrity": "sha512-eLYXDbZWXh2uxf+w8sXS8d6KSoXTswfps6fvCUuVAGN8eRpfe7h9eSRydxiSJvo9Bf+GzifsDOr9TMQlmJdmkw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/@types/retry": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz", + "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/@types/tough-cookie": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@types/tough-cookie/-/tough-cookie-4.0.0.tgz", + "integrity": "sha512-I99sngh224D0M7XgW1s120zxCt3VYQ3IQsuw3P3jbq5GG4yc79+ZjyKznyOGIQrflfylLgcfekeZW/vk0yng6A==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/@types/triple-beam": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/@types/triple-beam/-/triple-beam-1.3.5.tgz", + "integrity": "sha512-6WaYesThRMCl19iryMYP7/x2OVgCtbIVflDGFpWnb9irXI3UjYE4AzmYuiUKY1AJstGijoY+MgUszMgRxIYTYw==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/webidl-conversions": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.3.tgz", + "integrity": "sha512-CiJJvcRtIgzadHCYXw7dqEnMNRjhGZlYK05Mj9OyktqV8uVT8fD2BFOB7S1uwBE3Kj2Z+4UyPmFw/Ixgw/LAlA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/@types/whatwg-url": { + "version": "13.0.0", + "resolved": "https://registry.npmjs.org/@types/whatwg-url/-/whatwg-url-13.0.0.tgz", + "integrity": "sha512-N8WXpbE6Wgri7KUSvrmQcqrMllKZ9uxkYWMt+mCSGwNc0Hsw9VQTW7ApqI4XNrx6/SaM2QQJCzMPDEXE058s+Q==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@types/webidl-conversions": "*" + } + }, + "node_modules/@types/ws": { + "version": "8.18.1", + "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.18.1.tgz", + "integrity": "sha512-ThVF6DCVhA8kUGy+aazFQ4kXQ7E1Ty7A3ypFOe0IcJV8O/M511G99AW24irKrW56Wt44yG9+ij8FaqoBGkuBXg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@typespec/ts-http-runtime": { + "version": "0.3.5", + "resolved": "https://registry.npmjs.org/@typespec/ts-http-runtime/-/ts-http-runtime-0.3.5.tgz", + "integrity": "sha512-yURCknZhvywvQItHMMmFSo+fq5arCUIyz/CVk7jD89MSai7dkaX8ufjCWp3NttLojoTVbcE72ri+be/TnEbMHw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "http-proxy-agent": "^7.0.0", + "https-proxy-agent": "^7.0.0", + "tslib": "^2.6.2" + }, + "engines": { + "node": ">=20.0.0" + } + }, + "node_modules/@vercel/oidc": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/@vercel/oidc/-/oidc-3.2.0.tgz", + "integrity": "sha512-UycprH3T6n3jH0k44NHMa7pnFHGu/N05MjojYr+Mc6I7obkoLIJujSWwin1pCvdy/eOxrI/l3uDLQsmcrOb4ug==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">= 20" + } + }, + "node_modules/@xmldom/xmldom": { + "version": "0.9.10", + "resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.9.10.tgz", + "integrity": "sha512-A9gOqLdi6cV4ibazAjcQufGj0B1y/vDqYrcuP6d/6x8P27gRS8643Dj9o1dEKtB6O7fwxb2FgBmJS2mX7gpvdw==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=14.6" + } + }, + "node_modules/a-sync-waterfall": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/a-sync-waterfall/-/a-sync-waterfall-1.0.1.tgz", + "integrity": "sha512-RYTOHHdWipFUliRFMCS4X2Yn2X8M87V/OpSqWzKKOGhzqyUxzyVmhHDH9sAvG+ZuQf/TAOFsLCpMw09I1ufUnA==", + "dev": true, + "license": "MIT" + }, + "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==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-types": "^3.0.0", + "negotiator": "^1.0.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/accepts/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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/adm-zip": { + "version": "0.5.17", + "resolved": "https://registry.npmjs.org/adm-zip/-/adm-zip-0.5.17.tgz", + "integrity": "sha512-+Ut8d9LLqwEvHHJl1+PIHqoyDxFgVN847JTVM3Izi3xHDWPE4UtzzXysMZQs64DMcrJfBeS/uoEP4AD3HQHnQQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=12.0" + } + }, + "node_modules/afinn-165": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/afinn-165/-/afinn-165-2.0.2.tgz", + "integrity": "sha512-mJ/RLUfpXfQA6bzugv+bBsc/QYkVrKaLYeS8fWBpKbTCsonv4iuV9ET0fgReEunm9vKLkaNgnekuSNlTC3WQ1Q==", + "dev": true, + "license": "MIT", + "optional": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/afinn-165-financialmarketnews": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/afinn-165-financialmarketnews/-/afinn-165-financialmarketnews-3.0.0.tgz", + "integrity": "sha512-0g9A1S3ZomFIGDTzZ0t6xmv4AuokBvBmpes8htiyHpH7N4xDmvSQL6UxL/Zcs2ypRb3VwgCscaD8Q3zEawKYhw==", + "dev": true, + "license": "MIT", + "optional": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/agent-base": { + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.4.tgz", + "integrity": "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 14" + } + }, + "node_modules/ai": { + "version": "6.0.185", + "resolved": "https://registry.npmjs.org/ai/-/ai-6.0.185.tgz", + "integrity": "sha512-oGsqscREaTlo75KHZLtwZxRyI+ZBwHV2wRX9B8smHjgOs13WwoCvUyr5aPUWpIBRz406wmIKy1RzoUEq0/WKJw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@ai-sdk/gateway": "3.0.116", + "@ai-sdk/provider": "3.0.10", + "@ai-sdk/provider-utils": "4.0.27", + "@opentelemetry/api": "^1.9.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "zod": "^3.25.76 || ^4.1.8" + } + }, + "node_modules/ajv": { + "version": "8.20.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz", + "integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==", + "dev": true, + "license": "MIT", + "dependencies": { + "fast-deep-equal": "^3.1.3", + "fast-uri": "^3.0.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/ajv-formats": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-3.0.1.tgz", + "integrity": "sha512-8iUql50EUR+uUcdRQ3HDqa6EVyo3docL8g5WJ3FNcWmu62IbkGUue/pEyLBW8VGKKucTPgqeks4fIU1DA4yowQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "ajv": "^8.0.0" + }, + "peerDependencies": { + "ajv": "^8.0.0" + }, + "peerDependenciesMeta": { + "ajv": { + "optional": true + } + } + }, + "node_modules/ansi-regex": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", + "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, + "node_modules/apparatus": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/apparatus/-/apparatus-0.0.10.tgz", + "integrity": "sha512-KLy/ugo33KZA7nugtQ7O0E1c8kQ52N3IvD/XgIh4w/Nr28ypfkwDfA67F1ev4N1m5D+BOk1+b2dEJDfpj/VvZg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "sylvester": ">= 0.0.8" + }, + "engines": { + "node": ">=0.2.6" + } + }, + "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/asap": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", + "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", + "dev": true, + "license": "MIT" + }, + "node_modules/asn1": { + "version": "0.2.6", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.6.tgz", + "integrity": "sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "safer-buffer": "~2.1.0" + } + }, + "node_modules/ast-types": { + "version": "0.13.4", + "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.13.4.tgz", + "integrity": "sha512-x1FCFnFifvYDDzTaLII71vG5uvDwgtmDTEVWAxrgeiR8VjMONcCXJx7E+USjDtHlwFmt9MysbqgF9b9Vjr6w+w==", + "dev": true, + "license": "MIT", + "dependencies": { + "tslib": "^2.0.1" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/async": { + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/async/-/async-3.2.6.tgz", + "integrity": "sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA==", + "dev": true, + "license": "MIT" + }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/axios": { + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.16.1.tgz", + "integrity": "sha512-caYkukvroVPO8KrzuJEb50Hm07KwfBZPEC3VeFHTsqWHvKTsy54hjJz9BS/cdaypROE2rH6xvm9mHX4fgWkr3A==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "follow-redirects": "^1.16.0", + "form-data": "^4.0.5", + "https-proxy-agent": "^5.0.1", + "proxy-from-env": "^2.1.0" + } + }, + "node_modules/axios/node_modules/agent-base": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", + "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "debug": "4" + }, + "engines": { + "node": ">= 6.0.0" + } + }, + "node_modules/axios/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/axios/node_modules/https-proxy-agent": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz", + "integrity": "sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "agent-base": "6", + "debug": "4" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/axios/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", + "optional": true + }, + "node_modules/balanced-match": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-4.0.4.tgz", + "integrity": "sha512-BLrgEcRTwX2o6gGxGOCNyMvGSp35YofuYzw9h1IMTRmKqttAZZVU67bdb9Pr2vUHA8+j3i2tJfjO6C6+4myGTA==", + "dev": true, + "license": "MIT", + "engines": { + "node": "18 || 20 || >=22" + } + }, + "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==", + "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/base64id": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/base64id/-/base64id-2.0.0.tgz", + "integrity": "sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog==", + "dev": true, + "license": "MIT", + "engines": { + "node": "^4.5.0 || >= 5.9" + } + }, + "node_modules/basic-ftp": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/basic-ftp/-/basic-ftp-5.3.1.tgz", + "integrity": "sha512-bopVNp6ugyA150DDuZfPFdt1KZ5a94ZDiwX4hMgZDzF+GttD80lEy8kj98kbyhLXnPvhtIo93mdnLIjpCAeeOw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/better-sqlite3": { + "version": "12.10.0", + "resolved": "https://registry.npmjs.org/better-sqlite3/-/better-sqlite3-12.10.0.tgz", + "integrity": "sha512-CyzaZRQKyHkB2ZInfTTl2nvT33EbDpjkLEbE8/Zck3Ll6O0qqvuGdrJ45HgtH+HykRg88ITY3AdreBGN70aBSQ==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "dependencies": { + "bindings": "^1.5.0", + "prebuild-install": "^7.1.1" + }, + "engines": { + "node": "20.x || 22.x || 23.x || 24.x || 25.x || 26.x" + } + }, + "node_modules/big-integer": { + "version": "1.6.52", + "resolved": "https://registry.npmjs.org/big-integer/-/big-integer-1.6.52.tgz", + "integrity": "sha512-QxD8cf2eVqJOOz63z6JIN9BzvVs/dlySa5HGSBH5xtR8dPteIRQnBxxKqkNTiT6jbDTF6jAfrd4oMcND9RGbQg==", + "dev": true, + "license": "Unlicense", + "optional": true, + "engines": { + "node": ">=0.6" + } + }, + "node_modules/bignumber.js": { + "version": "9.3.1", + "resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.3.1.tgz", + "integrity": "sha512-Ko0uX15oIUS7wJ3Rb30Fs6SkVbLmPBAKdlm7q9+ak9bbIeFf0MwuBsQV6z7+X768/cHsfg+WlysDWJcmthjsjQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": "*" + } + }, + "node_modules/binary-extensions": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-3.1.0.tgz", + "integrity": "sha512-Jvvd9hy1w+xUad8+ckQsWA/V1AoyubOvqn0aygjMOVM4BfIaRav1NFS3LsTSDaV4n4FtcCtQXvzep1E6MboqwQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/binaryextensions": { + "version": "6.11.0", + "resolved": "https://registry.npmjs.org/binaryextensions/-/binaryextensions-6.11.0.tgz", + "integrity": "sha512-sXnYK/Ij80TO3lcqZVV2YgfKN5QjUWIRk/XSm2J/4bd/lPko3lvk0O4ZppH6m+6hB2/GTu+ptNwVFe1xh+QLQw==", + "dev": true, + "license": "Artistic-2.0", + "dependencies": { + "editions": "^6.21.0" + }, + "engines": { + "node": ">=4" + }, + "funding": { + "url": "https://bevry.me/fund" + } + }, + "node_modules/bindings": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.5.0.tgz", + "integrity": "sha512-p2q/t/mhvuOj/UeLlV6566GD/guowlr0hHxClI0W9m7MWYkL1F0hLo+0Aexs9HSPCtR1SXQ0TD3MMKrXZajbiQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "file-uri-to-path": "1.0.0" + } + }, + "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/bluebird": { + "version": "3.7.2", + "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.7.2.tgz", + "integrity": "sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/body-parser": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.2.2.tgz", + "integrity": "sha512-oP5VkATKlNwcgvxi0vM0p/D3n2C3EReYVX+DNYs5TjZFn/oQt2j+4sVJtSMr18pdRr8wjTcBl6LoV+FUwzPmNA==", + "dev": true, + "license": "MIT", + "dependencies": { + "bytes": "^3.1.2", + "content-type": "^1.0.5", + "debug": "^4.4.3", + "http-errors": "^2.0.0", + "iconv-lite": "^0.7.0", + "on-finished": "^2.4.1", + "qs": "^6.14.1", + "raw-body": "^3.0.1", + "type-is": "^2.0.1" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/body-parser/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/boolean": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/boolean/-/boolean-3.2.0.tgz", + "integrity": "sha512-d0II/GO9uf9lfUHH2BQsjxzRJZBdsjgsBiW4BvhWk/3qoKwQFjIDVN19PfX8F2D/r9PCMTtLWjYVCFrpeYUzsw==", + "deprecated": "Package no longer supported. Contact Support at https://www.npmjs.com/support for more info.", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/bowser": { + "version": "2.14.1", + "resolved": "https://registry.npmjs.org/bowser/-/bowser-2.14.1.tgz", + "integrity": "sha512-tzPjzCxygAKWFOJP011oxFHs57HzIhOEracIgAePE4pqB3LikALKnSzUyU4MGs9/iCEUuHlAJTjTc5M+u7YEGg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/brace-expansion": { + "version": "5.0.6", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-5.0.6.tgz", + "integrity": "sha512-kLpxurY4Z4r9sgMsyG0Z9uzsBlgiU/EFKhj/h91/8yHu0edo7XuixOIH3VcJ8kkxs6/jPzoI6U9Vj3WqbMQ94g==", + "dev": true, + "license": "MIT", + "dependencies": { + "balanced-match": "^4.0.2" + }, + "engines": { + "node": "18 || 20 || >=22" + } + }, + "node_modules/bson": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/bson/-/bson-7.2.0.tgz", + "integrity": "sha512-YCEo7KjMlbNlyHhz7zAZNDpIpQbd+wOEHJYezv0nMYTn4x31eIUM2yomNNubclAt63dObUzKHWsBLJ9QcZNSnQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "engines": { + "node": ">=20.19.0" + } + }, + "node_modules/buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "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/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==", + "dev": true, + "license": "BSD-3-Clause" + }, + "node_modules/bundle-name": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bundle-name/-/bundle-name-4.1.0.tgz", + "integrity": "sha512-tjwM5exMg6BGRI+kNmTntNsvdZS1X8BFYS6tnJ2hdH0kVxM6/eVZ2xy+FqStSWvYmtfFMDLIxurorHwDKfDz5Q==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "run-applescript": "^7.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/cache-manager": { + "version": "7.2.8", + "resolved": "https://registry.npmjs.org/cache-manager/-/cache-manager-7.2.8.tgz", + "integrity": "sha512-0HDaDLBBY/maa/LmUVAr70XUOwsiQD+jyzCBjmUErYZUKdMS9dT59PqW59PpVqfGM7ve6H0J6307JTpkCYefHQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@cacheable/utils": "^2.3.3", + "keyv": "^5.5.5" + } + }, + "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==", + "dev": true, + "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==", + "dev": true, + "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/camelcase": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", + "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/chalk": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.6.2.tgz", + "integrity": "sha512-7NzBL0rN6fMUW+f7A6Io4h40qQlG+xGmtMxfbnH/K7TAtt8JQWVQK+6g0UXKMeVJoyV5EkkNsErQ8pVD3bLHbA==", + "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/chardet": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/chardet/-/chardet-2.1.1.tgz", + "integrity": "sha512-PsezH1rqdV9VvyNhxxOW32/d75r01NY7TQCmOqomRo15ZSOKbpTFVsfjghxo6JloQUCGnH4k1LGu0R4yCLlWQQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/charenc": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", + "integrity": "sha512-yrLQ/yVUFXkzg7EDQsPieE/53+0RlaWTs+wBrvW36cyilJ2SaDWfl4Yj7MtLTXleV9uEKefbAGUPv2/iWSooRA==", + "dev": true, + "license": "BSD-3-Clause", + "engines": { + "node": "*" + } + }, + "node_modules/chownr": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", + "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", + "dev": true, + "license": "ISC" + }, + "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-progress": { + "version": "3.12.0", + "resolved": "https://registry.npmjs.org/cli-progress/-/cli-progress-3.12.0.tgz", + "integrity": "sha512-tRkV3HJ1ASwm19THiiLIXLO7Im7wlTuKnvkYaTkyoAPefqjNg7W7DHKUlGRxy9vxDvbyCYQkQozvptuMkGCg8A==", + "dev": true, + "license": "MIT", + "dependencies": { + "string-width": "^4.2.3" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/cli-spinners": { + "version": "3.4.0", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-3.4.0.tgz", + "integrity": "sha512-bXfOC4QcT1tKXGorxL3wbJm6XJPDqEnij2gQ2m7ESQuE+/z9YFIWnl/5RpTiKWbMq3EVKR4fRLJGn6DVfu0mpw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/cli-table3": { + "version": "0.6.5", + "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.6.5.tgz", + "integrity": "sha512-+W/5efTR7y5HRD7gACw9yQjqMVvEMLBHmboM/kPWam+H+Hmyrgjh6YncVKK122YZkXrLudzTuAukUw9FnMf7IQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "string-width": "^4.2.0" + }, + "engines": { + "node": "10.* || >= 12.*" + }, + "optionalDependencies": { + "@colors/colors": "1.5.0" + } + }, + "node_modules/cli-width": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-4.1.0.tgz", + "integrity": "sha512-ouuZd4/dm2Sw5Gmqy6bGyNNNe1qt9RpmxveLSO7KcgsTnU7RXfsw+/bukWGo1abgBiMAic068rclZsO4IWmmxQ==", + "dev": true, + "license": "ISC", + "engines": { + "node": ">= 12" + } + }, + "node_modules/cluster-key-slot": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.2.tgz", + "integrity": "sha512-RMr0FhtfXemyinomL4hrWcYJxmX6deFdCxpJzhDttxgO1+bcCnkk+9drydLVDmAMG7NE6aN/fl4F7ucU/90gAA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/color": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/color/-/color-5.0.3.tgz", + "integrity": "sha512-ezmVcLR3xAVp8kYOm4GS45ZLLgIE6SPAFoduLr6hTDajwb3KZ2F46gulK3XpcwRFb5KKGCSezCBAY4Dw4HsyXA==", + "dev": true, + "license": "MIT", + "dependencies": { + "color-convert": "^3.1.3", + "color-string": "^2.1.3" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/color-convert": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-3.1.3.tgz", + "integrity": "sha512-fasDH2ont2GqF5HpyO4w0+BcewlhHEZOFn9c1ckZdHpJ56Qb7MHhH/IcJZbBGgvdtwdwNbLvxiBEdg336iA9Sg==", + "dev": true, + "license": "MIT", + "dependencies": { + "color-name": "^2.0.0" + }, + "engines": { + "node": ">=14.6" + } + }, + "node_modules/color-name": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-2.1.0.tgz", + "integrity": "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12.20" + } + }, + "node_modules/color-string": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/color-string/-/color-string-2.1.4.tgz", + "integrity": "sha512-Bb6Cq8oq0IjDOe8wJmi4JeNn763Xs9cfrBcaylK1tPypWzyoy2G3l90v9k64kjphl/ZJjPIShFztenRomi8WTg==", + "dev": true, + "license": "MIT", + "dependencies": { + "color-name": "^2.0.0" + }, + "engines": { + "node": ">=18" + } + }, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/commander": { + "version": "14.0.3", + "resolved": "https://registry.npmjs.org/commander/-/commander-14.0.3.tgz", + "integrity": "sha512-H+y0Jo/T1RZ9qPP4Eh1pkcQcLRglraJaSLoyOtHxu6AapkjWVCy2Sit1QQ4x3Dng8qDlSsZEet7g5Pq06MvTgw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=20" + } + }, + "node_modules/complex.js": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/complex.js/-/complex.js-2.4.3.tgz", + "integrity": "sha512-UrQVSUur14tNX6tiP4y8T4w4FeJAX3bi2cIv0pu/DTLFNxoq7z2Yh83Vfzztj6Px3X/lubqQ9IrPp7Bpn6p4MQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": "*" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/rawify" + } + }, + "node_modules/compressible": { + "version": "2.0.18", + "resolved": "https://registry.npmjs.org/compressible/-/compressible-2.0.18.tgz", + "integrity": "sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-db": ">= 1.43.0 < 2" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/compression": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/compression/-/compression-1.8.1.tgz", + "integrity": "sha512-9mAqGPHLakhCLeNyxPkK4xVo746zQ/czLH1Ky+vkitMnWfWZps8r0qXuwhwizagCRttsL4lfG4pIOvaWLpAP0w==", + "dev": true, + "license": "MIT", + "dependencies": { + "bytes": "3.1.2", + "compressible": "~2.0.18", + "debug": "2.6.9", + "negotiator": "~0.6.4", + "on-headers": "~1.1.0", + "safe-buffer": "5.2.1", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/content-disposition": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.1.0.tgz", + "integrity": "sha512-5jRCH9Z/+DRP7rkvY83B+yGIGX96OYdJmzngqnw2SBSxqCFPd0w2km3s5iawpGX8krnwSGmF0FW5Nhr0Hfai3g==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie": { + "version": "0.7.2", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.2.tgz", + "integrity": "sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6.6.0" + } + }, + "node_modules/core-util-is": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/cors": { + "version": "2.8.6", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.6.tgz", + "integrity": "sha512-tJtZBBHA6vjIAaF6EnIaq6laBBP9aq/Y3ouVJjEfoHbRBcHBAHYcMh/w8LDrk2PvIMMq8gmopa5D4V8RmbrxGw==", + "dev": true, + "license": "MIT", + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "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", + "optional": true, + "dependencies": { + "node-fetch": "^2.7.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==", + "dev": true, + "license": "MIT", + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/crypt": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/crypt/-/crypt-0.0.2.tgz", + "integrity": "sha512-mCxBlsHFYh9C+HVpiEacem8FEBnMXgU9gy4zmNC+SXAZNB/1idgp/aulFJ4FgCi7GPEVbfyng092GqL2k2rmow==", + "dev": true, + "license": "BSD-3-Clause", + "engines": { + "node": "*" + } + }, + "node_modules/csv-parse": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/csv-parse/-/csv-parse-6.2.1.tgz", + "integrity": "sha512-LRLMV+UCyfMokp8Wb411duBf1gaBKJfOfBWU9eHMJ+b+cJYZsNu3AFmjJf3+yPGd59Exz1TsMjaSFyxnYB9+IQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/csv-stringify": { + "version": "6.7.0", + "resolved": "https://registry.npmjs.org/csv-stringify/-/csv-stringify-6.7.0.tgz", + "integrity": "sha512-UdtziYp5HuTz7e5j8Nvq+a/3HQo+2/aJZ9xntNTpmRRIg/3YYqDVgiS9fvAhtNbnyfbv2ZBe0bqCHqzhE7FqWQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/data-uri-to-buffer": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-8.0.0.tgz", + "integrity": "sha512-6UHfyCux51b8PTGDgveqtz1tvphBku5DrMKKJbFAZAJOI2zsjDpDoYE1+QGj7FOMS4BdTFNJsJiR3zEB0xH0yQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 20" + } + }, + "node_modules/debounce": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/debounce/-/debounce-3.0.0.tgz", + "integrity": "sha512-64byRbF0/AirwbuHqB3/ZpMG9/nckDa6ZA0yd6UnaQNwbbemCOwvz2sL5sjXLHhZHADyiwLm0M5qMhltUUx+TA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/decimal.js": { + "version": "10.6.0", + "resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-10.6.0.tgz", + "integrity": "sha512-YpgQiITW3JXGntzdUmyUR1V812Hn8T1YVXhCu+wO3OpS4eU9l4YdD3qjyiKdV6mvV29zapkMeD390UVEf2lkUg==", + "dev": true, + "license": "MIT" + }, + "node_modules/decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "mimic-response": "^3.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/dedent": { + "version": "1.7.2", + "resolved": "https://registry.npmjs.org/dedent/-/dedent-1.7.2.tgz", + "integrity": "sha512-WzMx3mW98SN+zn3hgemf4OzdmyNhhhKz5Ay0pUfQiMQ3e1g+xmTJWp/pKdwKVXhdSkAEGIIzqeuWrL3mV/AXbA==", + "dev": true, + "license": "MIT", + "peerDependencies": { + "babel-plugin-macros": "^3.1.0" + }, + "peerDependenciesMeta": { + "babel-plugin-macros": { + "optional": true + } + } + }, + "node_modules/deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/default-browser": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/default-browser/-/default-browser-5.5.0.tgz", + "integrity": "sha512-H9LMLr5zwIbSxrmvikGuI/5KGhZ8E2zH3stkMgM5LpOWDutGM2JZaj460Udnf1a+946zc7YBgrqEWwbk7zHvGw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "bundle-name": "^4.1.0", + "default-browser-id": "^5.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/default-browser-id": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/default-browser-id/-/default-browser-id-5.0.1.tgz", + "integrity": "sha512-x1VCxdX4t+8wVfd1so/9w+vQ4vx7lKd2Qp5tDRutErwmR85OgmfX7RlLRMWafRMY7hbEiXIbudNrjOAPa/hL8Q==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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", + "optional": true, + "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-lazy-prop": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-3.0.0.tgz", + "integrity": "sha512-N+MeXYoqr3pOgn8xfyRPREN7gHakLYjhsHhWGT3fWAiL4IkAt0iDw14QiiEm2bE30c5XX5q0FtAA3CK5f9/BUg==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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", + "optional": true, + "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/degenerator": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/degenerator/-/degenerator-7.0.1.tgz", + "integrity": "sha512-ABErK0IefDSyHjlPH7WUEenIAX2rPPnrDcDM+TS3z3+zu9TfyKKi07BQM+8rmxpdE2y1v5fjjdoAS/x4D2U60w==", + "dev": true, + "license": "MIT", + "dependencies": { + "ast-types": "^0.13.4", + "escodegen": "^2.1.0", + "esprima": "^4.0.1" + }, + "engines": { + "node": ">= 20" + }, + "peerDependencies": { + "quickjs-wasi": "^2.2.0" + } + }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "dev": true, + "license": "MIT", + "optional": true, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/detect-libc": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz", + "integrity": "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=8" + } + }, + "node_modules/detect-node": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/detect-node/-/detect-node-2.1.0.tgz", + "integrity": "sha512-T0NIuQpnTvFDATNuHN5roPwSBG83rFsuO+MXXH9/3N1eFbn4wcPjttvjMLEPWJ0RGUYgQE7cGgS3tNxbqCGM7g==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/dotenv": { + "version": "17.4.2", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-17.4.2.tgz", + "integrity": "sha512-nI4U3TottKAcAD9LLud4Cb7b2QztQMUEfHbvhTH09bqXTxnSie8WnjPALV/WMCrJZ6UV/qHJ6L03OqO3LcdYZw==", + "dev": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://dotenvx.com" + } + }, + "node_modules/drizzle-orm": { + "version": "0.45.2", + "resolved": "https://registry.npmjs.org/drizzle-orm/-/drizzle-orm-0.45.2.tgz", + "integrity": "sha512-kY0BSaTNYWnoDMVoyY8uxmyHjpJW1geOmBMdSSicKo9CIIWkSxMIj2rkeSR51b8KAPB7m+qysjuHme5nKP+E5Q==", + "dev": true, + "license": "Apache-2.0", + "peerDependencies": { + "@aws-sdk/client-rds-data": ">=3", + "@cloudflare/workers-types": ">=4", + "@electric-sql/pglite": ">=0.2.0", + "@libsql/client": ">=0.10.0", + "@libsql/client-wasm": ">=0.10.0", + "@neondatabase/serverless": ">=0.10.0", + "@op-engineering/op-sqlite": ">=2", + "@opentelemetry/api": "^1.4.1", + "@planetscale/database": ">=1.13", + "@prisma/client": "*", + "@tidbcloud/serverless": "*", + "@types/better-sqlite3": "*", + "@types/pg": "*", + "@types/sql.js": "*", + "@upstash/redis": ">=1.34.7", + "@vercel/postgres": ">=0.8.0", + "@xata.io/client": "*", + "better-sqlite3": ">=7", + "bun-types": "*", + "expo-sqlite": ">=14.0.0", + "gel": ">=2", + "knex": "*", + "kysely": "*", + "mysql2": ">=2", + "pg": ">=8", + "postgres": ">=3", + "sql.js": ">=1", + "sqlite3": ">=5" + }, + "peerDependenciesMeta": { + "@aws-sdk/client-rds-data": { + "optional": true + }, + "@cloudflare/workers-types": { + "optional": true + }, + "@electric-sql/pglite": { + "optional": true + }, + "@libsql/client": { + "optional": true + }, + "@libsql/client-wasm": { + "optional": true + }, + "@neondatabase/serverless": { + "optional": true + }, + "@op-engineering/op-sqlite": { + "optional": true + }, + "@opentelemetry/api": { + "optional": true + }, + "@planetscale/database": { + "optional": true + }, + "@prisma/client": { + "optional": true + }, + "@tidbcloud/serverless": { + "optional": true + }, + "@types/better-sqlite3": { + "optional": true + }, + "@types/pg": { + "optional": true + }, + "@types/sql.js": { + "optional": true + }, + "@upstash/redis": { + "optional": true + }, + "@vercel/postgres": { + "optional": true + }, + "@xata.io/client": { + "optional": true + }, + "better-sqlite3": { + "optional": true + }, + "bun-types": { + "optional": true + }, + "expo-sqlite": { + "optional": true + }, + "gel": { + "optional": true + }, + "knex": { + "optional": true + }, + "kysely": { + "optional": true + }, + "mysql2": { + "optional": true + }, + "pg": { + "optional": true + }, + "postgres": { + "optional": true + }, + "prisma": { + "optional": true + }, + "sql.js": { + "optional": true + }, + "sqlite3": { + "optional": true + } + } + }, + "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==", + "dev": true, + "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/duplexer2": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer2/-/duplexer2-0.1.4.tgz", + "integrity": "sha512-asLFVfWWtJ90ZyOUHMqk7/S2w2guQKxUI2itj3d92ADHhxUSbCMGi1f1cBcJ7xM1To+pE/Khbwo1yuNbMEPKeA==", + "dev": true, + "license": "BSD-3-Clause", + "optional": true, + "dependencies": { + "readable-stream": "^2.0.2" + } + }, + "node_modules/duplexer2/node_modules/readable-stream": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", + "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/duplexer2/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/duplexer2/node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "safe-buffer": "~5.1.0" + } + }, + "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==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "safe-buffer": "^5.0.1" + } + }, + "node_modules/editions": { + "version": "6.22.0", + "resolved": "https://registry.npmjs.org/editions/-/editions-6.22.0.tgz", + "integrity": "sha512-UgGlf8IW75je7HZjNDpJdCv4cGJWIi6yumFdZ0R7A8/CIhQiWUjyGLCxdHpd8bmyD1gnkfUNK0oeOXqUS2cpfQ==", + "dev": true, + "license": "Artistic-2.0", + "dependencies": { + "version-range": "^4.15.0" + }, + "engines": { + "ecmascript": ">= es5", + "node": ">=4" + }, + "funding": { + "url": "https://bevry.me/fund" + } + }, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/emoji-regex": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "dev": true, + "license": "MIT" + }, + "node_modules/enabled": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/enabled/-/enabled-2.0.0.tgz", + "integrity": "sha512-AKrN98kuwOzMIdAizXGI86UFBoo26CL21UM763y1h/GMSJ4/OHU9k2YlsmBpyScFo/wbLzWQJBMCW4+IO3/+OQ==", + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/end-of-stream": { + "version": "1.4.5", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.5.tgz", + "integrity": "sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==", + "dev": true, + "license": "MIT", + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/engine.io": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.6.7.tgz", + "integrity": "sha512-DgOngfDKM2EviOH3Mr9m7ks1q8roetLy/IMmYthAYzbpInMbYc/GS+fWFA3rl1gvwKVsQrVV61fo5emD1y3OJQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/cors": "^2.8.12", + "@types/node": ">=10.0.0", + "@types/ws": "^8.5.12", + "accepts": "~1.3.4", + "base64id": "2.0.0", + "cookie": "~0.7.2", + "cors": "~2.8.5", + "debug": "~4.4.1", + "engine.io-parser": "~5.2.1", + "ws": "~8.18.3" + }, + "engines": { + "node": ">=10.2.0" + } + }, + "node_modules/engine.io-client": { + "version": "6.6.4", + "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-6.6.4.tgz", + "integrity": "sha512-+kjUJnZGwzewFDw951CDWcwj35vMNf2fcj7xQWOctq1F2i1jkDdVvdFG9kM/BEChymCH36KgjnW0NsL58JYRxw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@socket.io/component-emitter": "~3.1.0", + "debug": "~4.4.1", + "engine.io-parser": "~5.2.1", + "ws": "~8.18.3", + "xmlhttprequest-ssl": "~2.1.1" + } + }, + "node_modules/engine.io-client/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/engine.io-client/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/engine.io-client/node_modules/ws": { + "version": "8.18.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.3.tgz", + "integrity": "sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg==", + "dev": true, + "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/engine.io-parser": { + "version": "5.2.3", + "resolved": "https://registry.npmjs.org/engine.io-parser/-/engine.io-parser-5.2.3.tgz", + "integrity": "sha512-HqD3yTBfnBxIrbnM1DoD6Pcq8NECnh8d4As1Qgh0z5Gg3jRRIqijury0CL3ghu/edArpUYiYqQiDUQBIs4np3Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/engine.io/node_modules/accepts": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", + "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-types": "~2.1.34", + "negotiator": "0.6.3" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/engine.io/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/engine.io/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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/engine.io/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==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/engine.io/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/engine.io/node_modules/negotiator": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", + "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/engine.io/node_modules/ws": { + "version": "8.18.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.3.tgz", + "integrity": "sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg==", + "dev": true, + "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/entities": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-8.0.0.tgz", + "integrity": "sha512-zwfzJecQ/Uej6tusMqwAqU/6KL2XaB2VZ2Jg54Je6ahNBGNH6Ek6g3jjNCF0fG9EWQKGZNddNjU5F1ZQn/sBnA==", + "dev": true, + "license": "BSD-2-Clause", + "engines": { + "node": ">=20.19.0" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "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==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "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==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "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/es6-error": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/es6-error/-/es6-error-4.1.1.tgz", + "integrity": "sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/es6-promisify": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-7.0.0.tgz", + "integrity": "sha512-ginqzK3J90Rd4/Yz7qRrqUeIpe3TwSXTPPZtPne7tGBPeAaQiU8qt4fpKApnxHcq1AwtUdHVg5P77x/yrggG8Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/esbuild": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.28.0.tgz", + "integrity": "sha512-sNR9MHpXSUV/XB4zmsFKN+QgVG82Cc7+/aaxJ8Adi8hyOac+EXptIp45QBPaVyX3N70664wRbTcLTOemCAnyqw==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "@esbuild/aix-ppc64": "0.28.0", + "@esbuild/android-arm": "0.28.0", + "@esbuild/android-arm64": "0.28.0", + "@esbuild/android-x64": "0.28.0", + "@esbuild/darwin-arm64": "0.28.0", + "@esbuild/darwin-x64": "0.28.0", + "@esbuild/freebsd-arm64": "0.28.0", + "@esbuild/freebsd-x64": "0.28.0", + "@esbuild/linux-arm": "0.28.0", + "@esbuild/linux-arm64": "0.28.0", + "@esbuild/linux-ia32": "0.28.0", + "@esbuild/linux-loong64": "0.28.0", + "@esbuild/linux-mips64el": "0.28.0", + "@esbuild/linux-ppc64": "0.28.0", + "@esbuild/linux-riscv64": "0.28.0", + "@esbuild/linux-s390x": "0.28.0", + "@esbuild/linux-x64": "0.28.0", + "@esbuild/netbsd-arm64": "0.28.0", + "@esbuild/netbsd-x64": "0.28.0", + "@esbuild/openbsd-arm64": "0.28.0", + "@esbuild/openbsd-x64": "0.28.0", + "@esbuild/openharmony-arm64": "0.28.0", + "@esbuild/sunos-x64": "0.28.0", + "@esbuild/win32-arm64": "0.28.0", + "@esbuild/win32-ia32": "0.28.0", + "@esbuild/win32-x64": "0.28.0" + } + }, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/escape-latex": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/escape-latex/-/escape-latex-1.2.0.tgz", + "integrity": "sha512-nV5aVWW1K0wEiUIEdZ4erkGGH8mDxGyxSeqPzRNtWP7ataw+/olFObw7hujFWlVjNsaDFw5VZ5NzVSIqRgfTiw==", + "dev": true, + "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", + "optional": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/escodegen": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-2.1.0.tgz", + "integrity": "sha512-2NlIDTwUWJN0mRPQOdtQBzbUHvdGY2P1VXSyU83Q3xKxM7WHX2Ql8dKq782Q9TgQUNOLEzEYu9bzLNj1q88I5w==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "esprima": "^4.0.1", + "estraverse": "^5.2.0", + "esutils": "^2.0.2" + }, + "bin": { + "escodegen": "bin/escodegen.js", + "esgenerate": "bin/esgenerate.js" + }, + "engines": { + "node": ">=6.0" + }, + "optionalDependencies": { + "source-map": "~0.6.1" + } + }, + "node_modules/esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "dev": true, + "license": "BSD-2-Clause", + "bin": { + "esparse": "bin/esparse.js", + "esvalidate": "bin/esvalidate.js" + }, + "engines": { + "node": ">=4" + } + }, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/eventemitter3": { + "version": "5.0.4", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.4.tgz", + "integrity": "sha512-mlsTRyGaPBjPedk6Bvw+aqbsXDtoAyAzm5MO7JgU+yVRyMQ5O8bD4Kcci7BS85f93veegeCPkL8R4GLClnjLFw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/events": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", + "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.8.x" + } + }, + "node_modules/eventsource": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/eventsource/-/eventsource-3.0.7.tgz", + "integrity": "sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==", + "dev": true, + "license": "MIT", + "dependencies": { + "eventsource-parser": "^3.0.1" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/eventsource-parser": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-1.1.2.tgz", + "integrity": "sha512-v0eOBUbiaFojBu2s2NPBfYUoRR9GjcDNvCXVaqEf5vVfpIAh9f8RCo4vXTP8c63QRKCFwoLpMpTdPwwhEKVgzA==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=14.18" + } + }, + "node_modules/eventsource/node_modules/eventsource-parser": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.8.tgz", + "integrity": "sha512-70QWGkr4snxr0OXLRWsFLeRBIRPuQOvt4s8QYjmUlmlkyTZkRqS7EDVRZtzU3TiyDbXSzaOeF0XUKy8PchzukQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/execa": { + "version": "9.6.1", + "resolved": "https://registry.npmjs.org/execa/-/execa-9.6.1.tgz", + "integrity": "sha512-9Be3ZoN4LmYR90tUoVu2te2BsbzHfhJyfEiAVfz7N5/zv+jduIfLrV2xdQXOHbaD6KgpGdO9PRPM1Y4Q9QkPkA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@sindresorhus/merge-streams": "^4.0.0", + "cross-spawn": "^7.0.6", + "figures": "^6.1.0", + "get-stream": "^9.0.0", + "human-signals": "^8.0.1", + "is-plain-obj": "^4.1.0", + "is-stream": "^4.0.1", + "npm-run-path": "^6.0.0", + "pretty-ms": "^9.2.0", + "signal-exit": "^4.1.0", + "strip-final-newline": "^4.0.0", + "yoctocolors": "^2.1.1" + }, + "engines": { + "node": "^18.19.0 || >=20.5.0" + }, + "funding": { + "url": "https://github.com/sindresorhus/execa?sponsor=1" + } + }, + "node_modules/execa/node_modules/is-stream": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-4.0.1.tgz", + "integrity": "sha512-Dnz92NInDqYckGEUJv689RbRiTSEHCQ7wOVeALbkOz999YpqT46yMRIGtSNl2iCL1waAZSx40+h59NV/EwzV/A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/expand-template": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-2.0.3.tgz", + "integrity": "sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==", + "dev": true, + "license": "(MIT OR WTFPL)", + "engines": { + "node": ">=6" + } + }, + "node_modules/express": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/express/-/express-5.2.1.tgz", + "integrity": "sha512-hIS4idWWai69NezIdRt2xFVofaF4j+6INOpJlVOLDO8zXGpUVEVzIYk12UUi2JzjEzWL3IOAxcTubgz9Po0yXw==", + "dev": true, + "license": "MIT", + "dependencies": { + "accepts": "^2.0.0", + "body-parser": "^2.2.1", + "content-disposition": "^1.0.0", + "content-type": "^1.0.5", + "cookie": "^0.7.1", + "cookie-signature": "^1.2.1", + "debug": "^4.4.0", + "depd": "^2.0.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": "8.5.2", + "resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-8.5.2.tgz", + "integrity": "sha512-5Kb34ipNX694DH48vN9irak1Qx30nb0PLYHXfJgw4YEjiC3ZEmZJhwOp+VfiCYwFzvFTdB9QkArYS5kXa2cx2A==", + "dev": true, + "license": "MIT", + "dependencies": { + "ip-address": "^10.2.0" + }, + "engines": { + "node": ">= 16" + }, + "funding": { + "url": "https://github.com/sponsors/express-rate-limit" + }, + "peerDependencies": { + "express": ">= 4.11" + } + }, + "node_modules/express/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/express/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/exsolve": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/exsolve/-/exsolve-1.0.8.tgz", + "integrity": "sha512-LmDxfWXwcTArk8fUEnOfSZpHOJ6zOMUJKOtFLFqJLoKJetuQG874Uc7/Kki7zFLzYybmZhp1M7+98pfMqeX8yA==", + "dev": true, + "license": "MIT" + }, + "node_modules/extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "dev": true, + "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==", + "dev": true, + "license": "MIT" + }, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/fast-string-truncated-width": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/fast-string-truncated-width/-/fast-string-truncated-width-3.0.3.tgz", + "integrity": "sha512-0jjjIEL6+0jag3l2XWWizO64/aZVtpiGE3t0Zgqxv0DPuxiMjvB3M24fCyhZUO4KomJQPj3LTSUnDP3GpdwC0g==", + "dev": true, + "license": "MIT" + }, + "node_modules/fast-string-width": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/fast-string-width/-/fast-string-width-3.0.2.tgz", + "integrity": "sha512-gX8LrtNEI5hq8DVUfRQMbr5lpaS4nMIWV+7XEbXk2b8kiQIizgnlr12B4dA3ZEx3308ze0O4Q1R+cHts8kyUJg==", + "dev": true, + "license": "MIT", + "dependencies": { + "fast-string-truncated-width": "^3.0.2" + } + }, + "node_modules/fast-uri": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.1.2.tgz", + "integrity": "sha512-rVjf7ArG3LTk+FS6Yw81V1DLuZl1bRbNrev6Tmd/9RaroeeRRJhAt7jg/6YFxbvAQXUCavSoZhPPj6oOx+5KjQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/fastify" + }, + { + "type": "opencollective", + "url": "https://opencollective.com/fastify" + } + ], + "license": "BSD-3-Clause" + }, + "node_modules/fast-wrap-ansi": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/fast-wrap-ansi/-/fast-wrap-ansi-0.2.2.tgz", + "integrity": "sha512-7F2Fl+TjRSenLqlU3UjSH0iyqopqoZIu7eZVpEirP2g1GtWa2G/ecEmBdgz31+Mxr+ELclgg6sokpSFIQiZ02Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "fast-string-width": "^3.0.2" + } + }, + "node_modules/fast-xml-builder": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-xml-builder/-/fast-xml-builder-1.2.0.tgz", + "integrity": "sha512-00aAWieqff+ZJhsXA4g1g7M8k+7AYoMUUHF+/zFb5U6Uv/P0Vl4QZo84/IcufzYalLuEj9928bXN9PbbFzMF0Q==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/NaturalIntelligence" + } + ], + "license": "MIT", + "dependencies": { + "path-expression-matcher": "^1.5.0", + "xml-naming": "^0.1.0" + } + }, + "node_modules/fast-xml-parser": { + "version": "5.8.0", + "resolved": "https://registry.npmjs.org/fast-xml-parser/-/fast-xml-parser-5.8.0.tgz", + "integrity": "sha512-6bIM7fsJxeo3uXv7OncQYsBAMPJ7V16Slahl/6M98C/i2q+vB1+4a0MtrvYwDFEUrwDSbAmeLDRXsOBwrL7yAg==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/NaturalIntelligence" + } + ], + "license": "MIT", + "dependencies": { + "@nodable/entities": "^2.1.0", + "fast-xml-builder": "^1.2.0", + "path-expression-matcher": "^1.5.0", + "strnum": "^2.3.0", + "xml-naming": "^0.1.0" + }, + "bin": { + "fxparser": "src/cli/cli.js" + } + }, + "node_modules/fastest-levenshtein": { + "version": "1.0.16", + "resolved": "https://registry.npmjs.org/fastest-levenshtein/-/fastest-levenshtein-1.0.16.tgz", + "integrity": "sha512-eRnCtTTtGZFpQCwhJiUOuxPQWRXVKYDn0b2PeHfXL6/Zi53SLAzAHfVhVWK2AryC/WH05kGfxhFIPvTF0SXQzg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 4.9.1" + } + }, + "node_modules/fecha": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/fecha/-/fecha-4.2.3.tgz", + "integrity": "sha512-OP2IUU6HeYKJi3i0z4A19kHMQoLVs4Hc+DPqqxI2h/DPZHTm/vjsfC6P0b4jCMy14XizLBqvndQ+UilD7707Jw==", + "dev": true, + "license": "MIT" + }, + "node_modules/fetch-blob": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.2.0.tgz", + "integrity": "sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/jimmywarting" + }, + { + "type": "paypal", + "url": "https://paypal.me/jimmywarting" + } + ], + "license": "MIT", + "dependencies": { + "node-domexception": "^1.0.0", + "web-streams-polyfill": "^3.0.3" + }, + "engines": { + "node": "^12.20 || >= 14.13" + } + }, + "node_modules/fetch-retry": { + "version": "5.0.6", + "resolved": "https://registry.npmjs.org/fetch-retry/-/fetch-retry-5.0.6.tgz", + "integrity": "sha512-3yurQZ2hD9VISAhJJP9bpYFNQrHHBXE2JxxjY5aLEcDi46RmAzJE2OC9FAde0yis5ElW0jTTzs0zfg/Cca4XqQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/fflate": { + "version": "0.8.3", + "resolved": "https://registry.npmjs.org/fflate/-/fflate-0.8.3.tgz", + "integrity": "sha512-tbZNuJrLwGUp3zshBtdy4W+ORxZuIh8a5ilyIEQDC5rY1f3U20JMry0Ll3WBzU58EZKsEuJFXhb5gwv8CsPvgA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/figures": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-6.1.0.tgz", + "integrity": "sha512-d+l3qxjSesT4V7v2fh+QnmFnUWv9lSpjarhShNTgBOfA0ttejbQUAlHLitbjkoRiDulW0OPoQPYIGhIC8ohejg==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-unicode-supported": "^2.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/file-type": { + "version": "21.3.2", + "resolved": "https://registry.npmjs.org/file-type/-/file-type-21.3.2.tgz", + "integrity": "sha512-DLkUvGwep3poOV2wpzbHCOnSKGk1LzyXTv+aHFgN2VFl96wnp8YA9YjO2qPzg5PuL8q/SW9Pdi6WTkYOIh995w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@tokenizer/inflate": "^0.4.1", + "strtok3": "^10.3.4", + "token-types": "^6.1.1", + "uint8array-extras": "^1.4.0" + }, + "engines": { + "node": ">=20" + }, + "funding": { + "url": "https://github.com/sindresorhus/file-type?sponsor=1" + } + }, + "node_modules/file-uri-to-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", + "integrity": "sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==", + "dev": true, + "license": "MIT" + }, + "node_modules/finalhandler": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-2.1.1.tgz", + "integrity": "sha512-S8KoZgRZN+a5rNwqTxlZZePjT/4cnm0ROV70LedRHZ0p8u9fRID0hJUZQpkKLzro8LfmC8sx23bY6tVNxv8pQA==", + "dev": true, + "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": ">= 18.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/finalhandler/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/flatbuffers": { + "version": "25.9.23", + "resolved": "https://registry.npmjs.org/flatbuffers/-/flatbuffers-25.9.23.tgz", + "integrity": "sha512-MI1qs7Lo4Syw0EOzUl0xjs2lsoeqFku44KpngfIduHBYvzm8h2+7K8YMQh1JtVVVrUvhLpNwqVi4DERegUJhPQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true + }, + "node_modules/fn.name": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fn.name/-/fn.name-1.1.0.tgz", + "integrity": "sha512-GRnmB5gPyJpAhTQdSZTSp9uaPSvl09KoYcMQtsB9rQoOmzs9dH6ffeccH+Z+cv6P68Hu5bC6JjRh4Ah/mHSNRw==", + "dev": true, + "license": "MIT" + }, + "node_modules/follow-redirects": { + "version": "1.16.0", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.16.0.tgz", + "integrity": "sha512-y5rN/uOsadFT/JfYwhxRS5R7Qce+g3zG97+JrtFZlC9klX/W5hD7iiLzScI4nZqUS7DNUdhPgw4xI8W2LuXlUw==", + "dev": true, + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "license": "MIT", + "optional": true, + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/form-data": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz", + "integrity": "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "es-set-tostringtag": "^2.1.0", + "hasown": "^2.0.2", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/formdata-polyfill": { + "version": "4.0.10", + "resolved": "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz", + "integrity": "sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==", + "dev": true, + "license": "MIT", + "dependencies": { + "fetch-blob": "^3.1.2" + }, + "engines": { + "node": ">=12.20.0" + } + }, + "node_modules/forwarded": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fraction.js": { + "version": "5.3.4", + "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-5.3.4.tgz", + "integrity": "sha512-1X1NTtiJphryn/uLQz3whtY6jK3fTqoE3ohKs0tT+Ujr1W59oopxmoEh7Lu5p6vBaPbgoM0bzveAW4Qi5RyWDQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": "*" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/rawify" + } + }, + "node_modules/fresh": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-2.0.0.tgz", + "integrity": "sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "dev": true, + "license": "MIT" + }, + "node_modules/fs-extra": { + "version": "11.3.5", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.3.5.tgz", + "integrity": "sha512-eKpRKAovdpZtR1WopLHxlBWvAgPny3c4gX1G5Jhwmmw4XJj0ifSD5qB5TOo8hmA0wlRKDAOAhEE1yVPgs6Fgcg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + }, + "engines": { + "node": ">=14.14" + } + }, + "node_modules/fs-extra/node_modules/universalify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", + "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 10.0.0" + } + }, + "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/function-bind": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", + "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/gaxios": { + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/gaxios/-/gaxios-7.1.4.tgz", + "integrity": "sha512-bTIgTsM2bWn3XklZISBTQX7ZSddGW+IO3bMdGaemHZ3tbqExMENHLx6kKZ/KlejgrMtj8q7wBItt51yegqalrA==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "extend": "^3.0.2", + "https-proxy-agent": "^7.0.1", + "node-fetch": "^3.3.2" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/gaxios/node_modules/data-uri-to-buffer": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.1.tgz", + "integrity": "sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 12" + } + }, + "node_modules/gaxios/node_modules/node-fetch": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-3.3.2.tgz", + "integrity": "sha512-dRB78srN/l6gqWulah9SrxeYnxeddIG30+GOqK/9OlLVyLg3HPnr6SqOWTWOXKRwC2eGYCkZ59NNuSgvSrpgOA==", + "dev": true, + "license": "MIT", + "dependencies": { + "data-uri-to-buffer": "^4.0.0", + "fetch-blob": "^3.1.4", + "formdata-polyfill": "^4.0.10" + }, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/node-fetch" + } + }, + "node_modules/gcp-metadata": { + "version": "8.1.2", + "resolved": "https://registry.npmjs.org/gcp-metadata/-/gcp-metadata-8.1.2.tgz", + "integrity": "sha512-zV/5HKTfCeKWnxG0Dmrw51hEWFGfcF2xiXqcA3+J90WDuP0SvoiSO5ORvcBsifmx/FoIjgQN3oNOGaQ5PhLFkg==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "gaxios": "^7.0.0", + "google-logging-utils": "^1.0.0", + "json-bigint": "^1.0.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/get-east-asian-width": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/get-east-asian-width/-/get-east-asian-width-1.6.0.tgz", + "integrity": "sha512-QRbvDIbx6YklUe6RxeTeleMR0yv3cYH6PsPZHcnVn7xv7zO1BHN8r0XETu8n6Ye3Q+ahtSarc3WgtNWmehIBfA==", + "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==", + "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" + }, + "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==", + "dev": true, + "license": "MIT", + "dependencies": { + "dunder-proto": "^1.0.1", + "es-object-atoms": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/get-stream": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-9.0.1.tgz", + "integrity": "sha512-kVCxPF3vQM/N0B1PmoqVUqgHP+EeVjmZSQn+1oCRPxd2P21P2F19lIgbR3HBosbB1PUhOAoctJnfEn2GbN2eZA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@sec-ant/readable-stream": "^0.4.1", + "is-stream": "^4.0.1" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/get-stream/node_modules/is-stream": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-4.0.1.tgz", + "integrity": "sha512-Dnz92NInDqYckGEUJv689RbRiTSEHCQ7wOVeALbkOz999YpqT46yMRIGtSNl2iCL1waAZSx40+h59NV/EwzV/A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/get-uri": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/get-uri/-/get-uri-8.0.0.tgz", + "integrity": "sha512-CqtZlMKvfJeY0Zxv8wazDwXmSKmnMnsmNy8j8+wudi8EyG/pMUB1NqHc+Tv1QaNtpYsK9nOYjb7r7Ufu32RPSw==", + "dev": true, + "license": "MIT", + "dependencies": { + "basic-ftp": "^5.2.0", + "data-uri-to-buffer": "8.0.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/get-uri/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/get-uri/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/github-from-package": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", + "integrity": "sha512-SyHy3T1v2NUXn29OsWdxmK6RwHD+vkj3v8en8AOBZ1wBQ/hCAQ5bAQTD02kW4W9tUp/3Qh6J8r9EvntiyCmOOw==", + "dev": true, + "license": "MIT" + }, + "node_modules/glob": { + "version": "13.0.6", + "resolved": "https://registry.npmjs.org/glob/-/glob-13.0.6.tgz", + "integrity": "sha512-Wjlyrolmm8uDpm/ogGyXZXb1Z+Ca2B8NbJwqBVg0axK9GbBeoS7yGV6vjXnYdGm6X53iehEuxxbyiKp8QmN4Vw==", + "dev": true, + "license": "BlueOak-1.0.0", + "dependencies": { + "minimatch": "^10.2.2", + "minipass": "^7.1.3", + "path-scurry": "^2.0.2" + }, + "engines": { + "node": "18 || 20 || >=22" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/global-agent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/global-agent/-/global-agent-3.0.0.tgz", + "integrity": "sha512-PT6XReJ+D07JvGoxQMkT6qji/jVNfX/h364XHZOWeRzy64sSFr+xJ5OX7LI3b4MPQzdL4H8Y8M0xzPpsVMwA8Q==", + "dev": true, + "license": "BSD-3-Clause", + "optional": true, + "dependencies": { + "boolean": "^3.0.1", + "es6-error": "^4.1.1", + "matcher": "^3.0.0", + "roarr": "^2.15.3", + "semver": "^7.3.2", + "serialize-error": "^7.0.1" + }, + "engines": { + "node": ">=10.0" + } + }, + "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", + "optional": true, + "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": "10.6.2", + "resolved": "https://registry.npmjs.org/google-auth-library/-/google-auth-library-10.6.2.tgz", + "integrity": "sha512-e27Z6EThmVNNvtYASwQxose/G57rkRuaRbQyxM2bvYLLX/GqWZ5chWq2EBoUchJbCc57eC9ArzO5wMsEmWftCw==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "base64-js": "^1.3.0", + "ecdsa-sig-formatter": "^1.0.11", + "gaxios": "^7.1.4", + "gcp-metadata": "8.1.2", + "google-logging-utils": "1.1.3", + "jws": "^4.0.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/google-logging-utils": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-1.1.3.tgz", + "integrity": "sha512-eAmLkjDjAFCVXg7A1unxHsLf961m6y17QFqXqAXGj/gVkKFrEICfStRfwUlGNfeCEjNRa32JEWOUTlYXPyyKvA==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=14" + } + }, + "node_modules/googleapis-common": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/googleapis-common/-/googleapis-common-8.0.1.tgz", + "integrity": "sha512-eCzNACUXPb1PW5l0ULTzMHaL/ltPRADoPgjBlT8jWsTbxkCp6siv+qKJ/1ldaybCthGwsYFYallF7u9AkU4L+A==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "extend": "^3.0.2", + "gaxios": "^7.0.0-rc.4", + "google-auth-library": "^10.1.0", + "qs": "^6.7.0", + "url-template": "^2.0.8" + }, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/gopd": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", + "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/graceful-fs": { + "version": "4.2.11", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz", + "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==", + "dev": true, + "license": "ISC", + "optional": true + }, + "node_modules/guid-typescript": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/guid-typescript/-/guid-typescript-1.0.9.tgz", + "integrity": "sha512-Y8T4vYhEfwJOTbouREvG+3XDsjr8E3kIr7uf+JZ0BYloFsttiHU0WfvANVsR7TxNUJa/WpCnw/Ino/p+DeBhBQ==", + "dev": true, + "license": "ISC", + "optional": true + }, + "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", + "optional": true, + "dependencies": { + "es-define-property": "^1.0.0" + }, + "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==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "has-symbols": "^1.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/hashery": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/hashery/-/hashery-1.5.1.tgz", + "integrity": "sha512-iZyKG96/JwPz1N55vj2Ie2vXbhu440zfUfJvSwEqEbeLluk7NnapfGqa7LH0mOsnDxTF85Mx8/dyR6HfqcbmbQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "hookified": "^1.15.0" + }, + "engines": { + "node": ">=20" + } + }, + "node_modules/hasown": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.3.tgz", + "integrity": "sha512-ej4AhfhfL2Q2zpMmLo7U1Uv9+PyhIZpgQLGT1F9miIGmiCJIoCgSmczFdrc97mWT4kVY72KA+WnnhJ5pghSvSg==", + "dev": true, + "license": "MIT", + "dependencies": { + "function-bind": "^1.1.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/hono": { + "version": "4.12.21", + "resolved": "https://registry.npmjs.org/hono/-/hono-4.12.21.tgz", + "integrity": "sha512-uV63apnb0kyPtAUwoWgaGh9HyIFcv8lgmzPZSiTBQAFOFGIzka5EZ1dZocmGnn0XdX0+XTqJ6Tqv7selMuGLRQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=16.9.0" + } + }, + "node_modules/hookified": { + "version": "1.15.1", + "resolved": "https://registry.npmjs.org/hookified/-/hookified-1.15.1.tgz", + "integrity": "sha512-MvG/clsADq1GPM2KGo2nyfaWVyn9naPiXrqIe4jYjXNZQt238kWyOGrsyc/DmRAQ+Re6yeo6yX/yoNCG5KAEVg==", + "dev": true, + "license": "MIT" + }, + "node_modules/http-errors": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.1.tgz", + "integrity": "sha512-4FbRdAX+bSdmo4AUFuS0WNiPz8NgFt+r8ThgNWmlrjQjt1Q7ZR9+zTlce2859x4KSXrwIsaeTqDoKQmtP8pLmQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "depd": "~2.0.0", + "inherits": "~2.0.4", + "setprototypeof": "~1.2.0", + "statuses": "~2.0.2", + "toidentifier": "~1.0.1" + }, + "engines": { + "node": ">= 0.8" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/http-proxy-agent": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-7.0.2.tgz", + "integrity": "sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "agent-base": "^7.1.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/http-proxy-agent/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/http-proxy-agent/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", + "optional": true + }, + "node_modules/http-status-codes": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/http-status-codes/-/http-status-codes-2.3.0.tgz", + "integrity": "sha512-RJ8XvFvpPM/Dmc5SV+dC4y5PCeOhT3x1Hq0NU3rjGeg5a/CqlhZ7uudknPwZFz4aeAXDcbAyaeP7GAo9lvngtA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/http-z": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/http-z/-/http-z-8.1.1.tgz", + "integrity": "sha512-4rEIu4SljSAs+lgCzzskyNdYllteGIHdnMBsu9MqafivyPAofSmCsrRjHQgxLs0BoPkUJBa7Ld6rXP32SPI8Fg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + } + }, + "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==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "^7.1.2", + "debug": "4" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/https-proxy-agent/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/https-proxy-agent/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/human-signals": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-8.0.1.tgz", + "integrity": "sha512-eKCa6bwnJhvxj14kZk5NCPc6Hb6BdsU9DZcOnmQKSnO1VKrfV0zCvtttPZUsBvjmNDn8rpcJfpwSYnHBjc95MQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">=18.18.0" + } + }, + "node_modules/ibm-cloud-sdk-core": { + "version": "5.4.19", + "resolved": "https://registry.npmjs.org/ibm-cloud-sdk-core/-/ibm-cloud-sdk-core-5.4.19.tgz", + "integrity": "sha512-BPeSnFP1qRxLinqnfl2BnKGp5z2+OvZXxuwMdSAdS9eAT0kTdk33A2n5TBnLTzE42pVLc7YC4CSG5XF6x9vpDg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@types/debug": "4.1.12", + "@types/node": "18.19.80", + "@types/tough-cookie": "4.0.0", + "axios": "1.15.2", + "camelcase": "6.3.0", + "debug": "4.3.4", + "dotenv": "16.4.5", + "extend": "3.0.2", + "file-type": "21.3.2", + "form-data": "4.0.4", + "isstream": "0.1.2", + "jsonwebtoken": "9.0.3", + "load-esm": "1.0.3", + "mime-types": "2.1.35", + "retry-axios": "2.6.0", + "tough-cookie": "4.1.3" + }, + "engines": { + "node": ">=20" + } + }, + "node_modules/ibm-cloud-sdk-core/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==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "undici-types": "~5.26.4" + } + }, + "node_modules/ibm-cloud-sdk-core/node_modules/axios": { + "version": "1.15.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.15.2.tgz", + "integrity": "sha512-wLrXxPtcrPTsNlJmKjkPnNPK2Ihe0hn0wGSaTEiHRPxwjvJwT3hKmXF4dpqxmPO9SoNb2FsYXj/xEo0gHN+D5A==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "follow-redirects": "^1.15.11", + "form-data": "^4.0.5", + "proxy-from-env": "^2.1.0" + } + }, + "node_modules/ibm-cloud-sdk-core/node_modules/axios/node_modules/form-data": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz", + "integrity": "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "es-set-tostringtag": "^2.1.0", + "hasown": "^2.0.2", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/ibm-cloud-sdk-core/node_modules/debug": { + "version": "4.3.4", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", + "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "ms": "2.1.2" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/ibm-cloud-sdk-core/node_modules/dotenv": { + "version": "16.4.5", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.4.5.tgz", + "integrity": "sha512-ZmdL2rui+eB2YwhsWzjInR8LldtZHGDoQ1ugH85ppHKwpUHL7j7rN0Ti9NCnGiQbhaZ11FpR+7ao1dNsmduNUg==", + "dev": true, + "license": "BSD-2-Clause", + "optional": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://dotenvx.com" + } + }, + "node_modules/ibm-cloud-sdk-core/node_modules/form-data": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.4.tgz", + "integrity": "sha512-KrGhL9Q4zjj0kiUt5OO4Mr/A/jlI2jDYs5eHBpYHPcBEVSiipAvn2Ko2HnPe20rmcuuvMHNdZFp+4IlGTMF0Ow==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "es-set-tostringtag": "^2.1.0", + "hasown": "^2.0.2", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/ibm-cloud-sdk-core/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==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/ibm-cloud-sdk-core/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==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/ibm-cloud-sdk-core/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==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/ibm-cloud-sdk-core/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==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/iconv-lite": { + "version": "0.7.2", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.7.2.tgz", + "integrity": "sha512-im9DjEDQ55s9fL4EYzOAv0yMqmMBSZp6G0VvFyTMPKWxiSBHUj9NW/qqLmXUwXrrM7AvqSlTCfvqRb0cM8yYqw==", + "dev": true, + "license": "MIT", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + }, + "engines": { + "node": ">=0.10.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "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/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true, + "license": "ISC" + }, + "node_modules/ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "dev": true, + "license": "ISC" + }, + "node_modules/ip-address": { + "version": "10.2.0", + "resolved": "https://registry.npmjs.org/ip-address/-/ip-address-10.2.0.tgz", + "integrity": "sha512-/+S6j4E9AHvW9SWMSEY9Xfy66O5PWvVEJ08O0y5JGyEKQpojb0K0GKpz/v5HJ/G0vi3D2sjGK78119oXZeE0qA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 12" + } + }, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true, + "license": "MIT" + }, + "node_modules/is-docker": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-3.0.0.tgz", + "integrity": "sha512-eljcgEDlEns/7AXFosB5K/2nCM4P7FQPkGc/DWLy5rmFEWvZayGrik1d9/QIY5nJ4f9YsVvBkA6kJpHn9rISdQ==", + "dev": true, + "license": "MIT", + "optional": true, + "bin": { + "is-docker": "cli.js" + }, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-electron": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/is-electron/-/is-electron-2.2.2.tgz", + "integrity": "sha512-FO/Rhvz5tuw4MCWkpMzHFKWD2LsfHzIb7i6MdPYZ/KW7AlxawyLkqdy+jPZP1WubqEADE3O4FUENlJHDfQASRg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/is-fullwidth-code-point": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", + "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, + "node_modules/is-inside-container": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-inside-container/-/is-inside-container-1.0.0.tgz", + "integrity": "sha512-KIYLCCJghfHZxqjYBE7rEy0OBuTd5xCHS7tHVgvCLkx7StIoaxwNW3hCALgEUjFfeRk+MG/Qxmp/vtETEF3tRA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "is-docker": "^3.0.0" + }, + "bin": { + "is-inside-container": "cli.js" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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-plain-obj": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", + "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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/is-wsl": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-3.1.1.tgz", + "integrity": "sha512-e6rvdUCiQCAuumZslxRJWR/Doq4VpPR82kqclvcS0efgt430SlGIk05vdCN58+VrzgtIcfNODjozVielycD4Sw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "is-inside-container": "^1.0.0" + }, + "engines": { + "node": ">=16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", + "dev": true, + "license": "ISC" + }, + "node_modules/isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha512-Yljz7ffyPbrLpLngrMtZ7NduUgVvi6wG9RJ9IUcyCd59YQ911PBJphODUcbOVbqYfxe1wuYf/LJ8PauMRwsM/g==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/istextorbinary": { + "version": "9.5.0", + "resolved": "https://registry.npmjs.org/istextorbinary/-/istextorbinary-9.5.0.tgz", + "integrity": "sha512-5mbUj3SiZXCuRf9fT3ibzbSSEWiy63gFfksmGfdOzujPjW3k+z8WvIBxcJHBoQNlaZaiyB25deviif2+osLmLw==", + "dev": true, + "license": "Artistic-2.0", + "dependencies": { + "binaryextensions": "^6.11.0", + "editions": "^6.21.0", + "textextensions": "^6.11.0" + }, + "engines": { + "node": ">=4" + }, + "funding": { + "url": "https://bevry.me/fund" + } + }, + "node_modules/javascript-natural-sort": { + "version": "0.7.1", + "resolved": "https://registry.npmjs.org/javascript-natural-sort/-/javascript-natural-sort-0.7.1.tgz", + "integrity": "sha512-nO6jcEfZWQXDhOiBtG2KvKyEptz7RVbpGP4vTD2hLBdmNQSsCiicO2Ioinv6UI4y9ukqnBpy+XZ9H6uLNgJTlw==", + "dev": true, + "license": "MIT" + }, + "node_modules/jks-js": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/jks-js/-/jks-js-1.1.7.tgz", + "integrity": "sha512-BeiDRKsAi1NwEwgx2JB/9/0tar5BNGIv+foGm1G5GgiyR35s/iUnfd/BWqYd16mLDD8qTaAVBrIcOOuVqXJZNQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "node-forge": "^1.4.0", + "node-int64": "^0.4.0", + "node-rsa": "^1.1.1" + } + }, + "node_modules/jose": { + "version": "6.2.3", + "resolved": "https://registry.npmjs.org/jose/-/jose-6.2.3.tgz", + "integrity": "sha512-YYVDInQKFJfR/xa3ojUTl8c2KoTwiL1R5Wg9YCydwH0x0B9grbzlg5HC7mMjCtUJjbQ/YnGEZIhI5tCgfTb4Hw==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/panva" + } + }, + "node_modules/js-rouge": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/js-rouge/-/js-rouge-3.2.0.tgz", + "integrity": "sha512-2dvY28iFq5NcwxPNzc2zMgLVJED843m6CnKrCy0jYnOKd+QQhdkxI1wmdQspbcOAggo3K3gUZfhTSwmM+lWoBA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/js-yaml": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.1.tgz", + "integrity": "sha512-qQKT4zQxXl8lLwBtHMWwaTcGfFOZviOJet3Oy/xmGk2gZH677CJM9EvtfdSkgWcATZhj/55JZ0rmy3myCT5lsA==", + "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==", + "dev": true, + "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==", + "dev": true, + "license": "(AFL-2.1 OR BSD-3-Clause)" + }, + "node_modules/json-schema-to-ts": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/json-schema-to-ts/-/json-schema-to-ts-3.1.1.tgz", + "integrity": "sha512-+DWg8jCJG2TEnpy7kOm/7/AxaYoaRbjVB4LFZLySZlWn8exGs3A4OLJR966cVvU26N7X9TWxl+Jsw7dzAqKT6g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.18.3", + "ts-algebra": "^2.0.0" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", + "dev": true, + "license": "MIT" + }, + "node_modules/json-schema-typed": { + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/json-schema-typed/-/json-schema-typed-8.0.2.tgz", + "integrity": "sha512-fQhoXdcvc3V28x7C7BMs4P5+kNlgUURe2jmUT1T//oBRMDrqy1QPelJimwZGo7Hg9VPV3EQV5Bnq4hbFy2vetA==", + "dev": true, + "license": "BSD-2-Clause" + }, + "node_modules/json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA==", + "dev": true, + "license": "ISC", + "optional": true + }, + "node_modules/json5": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "dev": true, + "license": "MIT", + "bin": { + "json5": "lib/cli.js" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/jsonfile": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.2.1.tgz", + "integrity": "sha512-zwOTdL3rFQ/lRdBnntKVOX6k5cKJwEc1HdilT71BWEu7J41gXIB2MRp+vxduPSwZJPWBxEzv4yH1wYLJGUHX4Q==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "universalify": "^2.0.0" + }, + "optionalDependencies": { + "graceful-fs": "^4.1.6" + } + }, + "node_modules/jsonfile/node_modules/universalify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz", + "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 10.0.0" + } + }, + "node_modules/jsonwebtoken": { + "version": "9.0.3", + "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.3.tgz", + "integrity": "sha512-MT/xP0CrubFRNLNKvxJ2BYfy53Zkm++5bX9dtuPbqAeQpTVe0MQTFhao8+Cp//EmJp244xt6Drw/GVEGCUj40g==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "jws": "^4.0.1", + "lodash.includes": "^4.3.0", + "lodash.isboolean": "^3.0.3", + "lodash.isinteger": "^4.0.4", + "lodash.isnumber": "^3.0.3", + "lodash.isplainobject": "^4.0.6", + "lodash.isstring": "^4.0.1", + "lodash.once": "^4.0.0", + "ms": "^2.1.1", + "semver": "^7.5.4" + }, + "engines": { + "node": ">=12", + "npm": ">=6" + } + }, + "node_modules/jsonwebtoken/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", + "optional": true + }, + "node_modules/jwa": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.1.tgz", + "integrity": "sha512-hRF04fqJIP8Abbkq5NKGN0Bbr3JxlQ+qhZufXVr0DvujKy93ZCbXZMHDL4EOtodSbCWxOqR8MS1tXA5hwqCXDg==", + "dev": true, + "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.1", + "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.1.tgz", + "integrity": "sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA==", + "dev": true, + "license": "MIT", + "dependencies": { + "jwa": "^2.0.1", + "safe-buffer": "^5.0.1" + } + }, + "node_modules/kareem": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/kareem/-/kareem-3.3.0.tgz", + "integrity": "sha512-kpSuLD3/7RenBnjnJdOHXCKC8dTd1JzeOiJhN0necWWci6cC+qX+VuwPnMVgb+a4+KNJSfgqahpnfWaeDXCimw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "engines": { + "node": ">=18.0.0" + } + }, + "node_modules/keyv": { + "version": "5.6.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-5.6.0.tgz", + "integrity": "sha512-CYDD3SOtsHtyXeEORYRx2qBtpDJFjRTGXUtmNEMGyzYOKj1TE3tycdlho7kA1Ufx9OYWZzg52QFBGALTirzDSw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@keyv/serialize": "^1.1.1" + } + }, + "node_modules/keyv-file": { + "version": "5.3.3", + "resolved": "https://registry.npmjs.org/keyv-file/-/keyv-file-5.3.3.tgz", + "integrity": "sha512-uCFUhiVYf+BcA6DP4smhnRLOR4yzUUA15yJSk4/rP5oAPnF3MpfajejwvSV8l+okm+EGiW4IHP3gn+xahpvZcQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@keyv/serialize": "^1.1.1", + "tslib": "^1.14.1" + } + }, + "node_modules/keyv-file/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true, + "license": "0BSD" + }, + "node_modules/kuler": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/kuler/-/kuler-2.0.0.tgz", + "integrity": "sha512-Xq9nH7KlWZmXAtodXDDRE7vs6DU1gTU8zYDHDiWLSip45Egwq3plLHzPn27NgvzL2r1LMPC1vdqh98sQxtqj4A==", + "dev": true, + "license": "MIT" + }, + "node_modules/langfuse": { + "version": "3.38.20", + "resolved": "https://registry.npmjs.org/langfuse/-/langfuse-3.38.20.tgz", + "integrity": "sha512-MAmBAASSzJtmK1O9HQegA1mFsQhT8Yf+OJRGvE7FXkyv3g/eiBE0glLD0Ohg3pkxhoPdggM5SejK7ue9ctlaMA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "langfuse-core": "^3.38.20" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/langfuse-core": { + "version": "3.38.20", + "resolved": "https://registry.npmjs.org/langfuse-core/-/langfuse-core-3.38.20.tgz", + "integrity": "sha512-zBKVmQN/1oT5VWZUBYlWzvokIlkC/6mnpgr/2atMyTeAm+jR3ia7w2iJMjlrF5/oG8ukO1s8+LDRCzJpF1QeEA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "mustache": "^4.2.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/load-esm": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/load-esm/-/load-esm-1.0.3.tgz", + "integrity": "sha512-v5xlu8eHD1+6r8EHTg6hfmO97LN8ugKtiXcy5e6oN72iD2r6u0RPfLl6fxM+7Wnh2ZRq15o0russMst44WauPA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/Borewit" + }, + { + "type": "buymeacoffee", + "url": "https://buymeacoffee.com/borewit" + } + ], + "license": "MIT", + "optional": true, + "engines": { + "node": ">=13.2.0" + } + }, + "node_modules/lodash.includes": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", + "integrity": "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/lodash.isboolean": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", + "integrity": "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/lodash.isinteger": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", + "integrity": "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/lodash.isnumber": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", + "integrity": "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/lodash.isplainobject": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", + "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/lodash.isstring": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", + "integrity": "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/lodash.once": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", + "integrity": "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/log-symbols": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-7.0.1.tgz", + "integrity": "sha512-ja1E3yCr9i/0hmBVaM0bfwDjnGy8I/s6PP4DFp+yP+a+mrHO4Rm7DtmnqROTUkHIkqffC84YY7AeqX6oFk0WFg==", + "dev": true, + "license": "MIT", + "dependencies": { + "is-unicode-supported": "^2.0.0", + "yoctocolors": "^2.1.1" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/logform": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/logform/-/logform-2.7.0.tgz", + "integrity": "sha512-TFYA4jnP7PVbmlBIfhlSe+WKxs9dklXMTEGcBCIvLhE/Tn3H6Gk1norupVW7m5Cnd4bLcr08AytbyV/xj7f/kQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@colors/colors": "1.6.0", + "@types/triple-beam": "^1.3.2", + "fecha": "^4.2.0", + "ms": "^2.1.1", + "safe-stable-stringify": "^2.3.1", + "triple-beam": "^1.3.0" + }, + "engines": { + "node": ">= 12.0.0" + } + }, + "node_modules/logform/node_modules/@colors/colors": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.6.0.tgz", + "integrity": "sha512-Ir+AOibqzrIsL6ajt3Rz3LskB7OiMVHqltZmspbW/TJuTVuyOMirVqAkjfY6JISiLHgyNqicAC8AyHHGzNd/dA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/logform/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/long": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/long/-/long-5.3.2.tgz", + "integrity": "sha512-mNAgZ1GmyNhD7AuqnTG3/VQ26o760+ZYBPKjPvugO8+nLbYfX6TVpJPseBvopbdY+qpZ/lKUnmEc1LeZYS3QAA==", + "dev": true, + "license": "Apache-2.0" + }, + "node_modules/lru-cache": { + "version": "11.4.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.4.0.tgz", + "integrity": "sha512-W+R+kFL4HgVxONq2bhXPi3bGpzGe/yEhVOp233qw9wCRtgncJ15P3bC+e4zZMu4Cq7d+WAJjXGW0uUkifhcatA==", + "dev": true, + "license": "BlueOak-1.0.0", + "engines": { + "node": "20 || >=22" + } + }, + "node_modules/matcher": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/matcher/-/matcher-3.0.0.tgz", + "integrity": "sha512-OkeDaAZ/bQCxeFAozM55PKcKU0yJMPGifLwV4Qgjitu+5MoAfSQN4lsLJeXZ1b8w0x+/Emda6MZgXS1jvsapng==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "escape-string-regexp": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/mathjs": { + "version": "15.2.0", + "resolved": "https://registry.npmjs.org/mathjs/-/mathjs-15.2.0.tgz", + "integrity": "sha512-UAQzSVob9rNLdGpqcFMYmSu9dkuLYy7Lr2hBEQS5SHQdknA9VppJz3cy2KkpMzTODunad6V6cNv+5kOLsePLow==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "@babel/runtime": "^7.26.10", + "complex.js": "^2.2.5", + "decimal.js": "^10.4.3", + "escape-latex": "^1.2.0", + "fraction.js": "^5.2.1", + "javascript-natural-sort": "^0.7.1", + "seedrandom": "^3.0.5", + "tiny-emitter": "^2.1.0", + "typed-function": "^4.2.1" + }, + "bin": { + "mathjs": "bin/cli.js" + }, + "engines": { + "node": ">= 18" + } + }, + "node_modules/md5": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/md5/-/md5-2.3.0.tgz", + "integrity": "sha512-T1GITYmFaKuO91vxyoQMFETst+O71VUPEU3ze5GNzDm0OWdP8v1ziTaAEPUr/3kLsY3Sftgz242A1SetQiDL7g==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "charenc": "0.0.2", + "crypt": "0.0.2", + "is-buffer": "~1.1.6" + } + }, + "node_modules/media-typer": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-1.1.0.tgz", + "integrity": "sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/memjs": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/memjs/-/memjs-1.3.2.tgz", + "integrity": "sha512-qUEg2g8vxPe+zPn09KidjIStHPtoBO8Cttm8bgJFWWabbsjQ9Av9Ky+6UcvKx6ue0LLb/LEhtcyQpRyKfzeXcg==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/memory-pager": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/memory-pager/-/memory-pager-1.5.0.tgz", + "integrity": "sha512-ZS4Bp4r/Zoeq6+NLJpP+0Zzm0pR8whtGPf1XExKLJBAczGMnSi3It14OiNCStjQjM6NU1okjQGSxgEZN8eBYKg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/mime-db": { + "version": "1.54.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.54.0.tgz", + "integrity": "sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-3.0.2.tgz", + "integrity": "sha512-Lbgzdk0h4juoQ9fCKXW4by0UJqj+nOOrI9MJ1sSj4nI8aI2eo1qmvQEie4VD1glsS250n15LsWsYtCugiStS5A==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-db": "^1.54.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "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/mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/minimatch": { + "version": "10.2.5", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.2.5.tgz", + "integrity": "sha512-MULkVLfKGYDFYejP07QOurDLLQpcjk7Fw+7jXS2R2czRQzR56yHRveU5NDJEOviH+hETZKSkIk5c+T23GjFUMg==", + "dev": true, + "license": "BlueOak-1.0.0", + "dependencies": { + "brace-expansion": "^5.0.5" + }, + "engines": { + "node": "18 || 20 || >=22" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/minimist": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", + "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/minipass": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-7.1.3.tgz", + "integrity": "sha512-tEBHqDnIoM/1rXME1zgka9g6Q2lcoCkxHLuc7ODJ5BxbP5d4c2Z5cGgtXAku59200Cx7diuHTOYfSBD8n6mm8A==", + "dev": true, + "license": "BlueOak-1.0.0", + "engines": { + "node": ">=16 || 14 >=14.17" + } + }, + "node_modules/mkdirp-classic": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz", + "integrity": "sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==", + "dev": true, + "license": "MIT" + }, + "node_modules/mongodb-connection-string-url": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/mongodb-connection-string-url/-/mongodb-connection-string-url-7.0.1.tgz", + "integrity": "sha512-h0AZ9A7IDVwwHyMxmdMXKy+9oNlF0zFoahHiX3vQ8e3KFcSP3VmsmfvtRSuLPxmyv2vjIDxqty8smTgie/SNRQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@types/whatwg-url": "^13.0.0", + "whatwg-url": "^14.1.0" + }, + "engines": { + "node": ">=20.19.0" + } + }, + "node_modules/mongodb-connection-string-url/node_modules/tr46": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-5.1.1.tgz", + "integrity": "sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "punycode": "^2.3.1" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/mongodb-connection-string-url/node_modules/webidl-conversions": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz", + "integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==", + "dev": true, + "license": "BSD-2-Clause", + "optional": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/mongodb-connection-string-url/node_modules/whatwg-url": { + "version": "14.2.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.2.0.tgz", + "integrity": "sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tr46": "^5.1.0", + "webidl-conversions": "^7.0.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/mongoose": { + "version": "9.6.2", + "resolved": "https://registry.npmjs.org/mongoose/-/mongoose-9.6.2.tgz", + "integrity": "sha512-7m8HntjkoRnwEmuPC0kdlwcZXJOQf4twumFj+PNzg/anqqZE2Er7hQslqyzy07mP3JcFjoTSgH5765PyqOXsxw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "kareem": "3.3.0", + "mongodb": "~7.2", + "mpath": "0.9.0", + "mquery": "6.0.0", + "ms": "2.1.3", + "sift": "17.1.3" + }, + "engines": { + "node": ">=20.19.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mongoose" + } + }, + "node_modules/mongoose/node_modules/mongodb": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-7.2.0.tgz", + "integrity": "sha512-F/2+BMZtLVhY30ioZp0dAmZ+IRZMBqI+nrv6t5+9/1AIwCa8sMRC3jBf81lpxMhnZgqq8CoUD503Z1oZWq1/sw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@mongodb-js/saslprep": "^1.3.0", + "bson": "^7.2.0", + "mongodb-connection-string-url": "^7.0.0" + }, + "engines": { + "node": ">=20.19.0" + }, + "peerDependencies": { + "@aws-sdk/credential-providers": "^3.806.0", + "@mongodb-js/zstd": "^7.0.0", + "gcp-metadata": "^7.0.1", + "kerberos": "^7.0.0", + "mongodb-client-encryption": ">=7.0.0 <7.1.0", + "snappy": "^7.3.2", + "socks": "^2.8.6" + }, + "peerDependenciesMeta": { + "@aws-sdk/credential-providers": { + "optional": true + }, + "@mongodb-js/zstd": { + "optional": true + }, + "gcp-metadata": { + "optional": true + }, + "kerberos": { + "optional": true + }, + "mongodb-client-encryption": { + "optional": true + }, + "snappy": { + "optional": true + }, + "socks": { + "optional": true + } + } + }, + "node_modules/mongoose/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", + "optional": true + }, + "node_modules/mpath": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/mpath/-/mpath-0.9.0.tgz", + "integrity": "sha512-ikJRQTk8hw5DEoFVxHG1Gn9T/xcjtdnOKIU1JTmGjZZlg9LST2mBLmcX3/ICIbgJydT2GOc15RnNy5mHmzfSew==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/mquery": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/mquery/-/mquery-6.0.0.tgz", + "integrity": "sha512-b2KQNsmgtkscfeDgkYMcWGn9vZI9YoXh802VDEwE6qc50zxBFQ0Oo8ROkawbPAsXCY1/Z1yp0MagqsZStPWJjw==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=20.19.0" + } + }, + "node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true, + "license": "MIT" + }, + "node_modules/mustache": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/mustache/-/mustache-4.2.0.tgz", + "integrity": "sha512-71ippSywq5Yb7/tVYyGbkBggbU8H3u5Rz56fH60jGFgr8uHwxs+aSKeqmluIVzM0m0kB7xQjKS6qPfd0b2ZoqQ==", + "dev": true, + "license": "MIT", + "optional": true, + "bin": { + "mustache": "bin/mustache" + } + }, + "node_modules/mute-stream": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-3.0.0.tgz", + "integrity": "sha512-dkEJPVvun4FryqBmZ5KhDo0K9iDXAwn08tMLDinNdRBNPcYEDiWYysLcc6k3mjTMlbP9KyylvRpd4wFtwrT9rw==", + "dev": true, + "license": "ISC", + "engines": { + "node": "^20.17.0 || >=22.9.0" + } + }, + "node_modules/napi-build-utils": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-2.0.0.tgz", + "integrity": "sha512-GEbrYkbfF7MoNaoh2iGG84Mnf/WZfB0GdGEsM8wz7Expx/LlWf5U8t9nvJKXSp3qr5IsEbK04cBGhol/KwOsWA==", + "dev": true, + "license": "MIT" + }, + "node_modules/natural": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/natural/-/natural-8.1.1.tgz", + "integrity": "sha512-Ucb+lsUcGxUqu3rn8cwHjT6gJQosO63nIX/aBQXB3+IDkNbFV7PuviysO+Rzz3aKn7PZhPj3bNF4PS9gDVjYCQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "afinn-165": "^2.0.2", + "afinn-165-financialmarketnews": "^3.0.0", + "apparatus": "^0.0.10", + "dotenv": "^17.3.1", + "memjs": "^1.3.2", + "mongoose": "^9.2.1", + "pg": "^8.18.0", + "redis": "^5.11.0", + "safe-stable-stringify": "^2.5.0", + "stopwords-iso": "^1.1.0", + "sylvester": "^0.0.21", + "underscore": "^1.13.0", + "uuid": "^13.0.0", + "wordnet-db": "^3.1.14" + }, + "engines": { + "node": ">=0.4.10" + } + }, + "node_modules/negotiator": { + "version": "0.6.4", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.4.tgz", + "integrity": "sha512-myRT3DiWPHqho5PrJaIRyaMv2kgYf0mUVgBNOYMuCH5Ki1yEiQaf/ZJuQ62nvpc44wL5WDbTX7yGJi1Neevw8w==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/netmask": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/netmask/-/netmask-2.1.1.tgz", + "integrity": "sha512-eonl3sLUha+S1GzTPxychyhnUzKyeQkZ7jLjKrBagJgPla13F+uQ71HgpFefyHgqrjEbCPkDArxYsjY8/+gLKA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/node-abi": { + "version": "3.92.0", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.92.0.tgz", + "integrity": "sha512-KdHvFWZjEKDf0cakgFjebl371GPsISX2oZHcuyKqM7DtogIsHrqKeLTo8wBHxaXRAQlY2PsPlZmfo+9ZCxEREQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "semver": "^7.3.5" + }, + "engines": { + "node": ">=10" + } + }, + "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==", + "deprecated": "Use your platform's native DOMException instead", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "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-forge": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-1.4.0.tgz", + "integrity": "sha512-LarFH0+6VfriEhqMMcLX2F7SwSXeWwnEAJEsYm5QKWchiVYVvJyV9v7UDvUv+w5HO23ZpQTXDv/GxdDdMyOuoQ==", + "dev": true, + "license": "(BSD-3-Clause OR GPL-2.0)", + "engines": { + "node": ">= 6.13.0" + } + }, + "node_modules/node-int64": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/node-int64/-/node-int64-0.4.0.tgz", + "integrity": "sha512-O5lz91xSOeoXP6DulyHfllpq+Eg00MWitZIbtPfoSEvqIHdl5gfcY6hYzDWnj0qD5tz52PI08u9qUvSVeUBeHw==", + "dev": true, + "license": "MIT" + }, + "node_modules/node-rsa": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/node-rsa/-/node-rsa-1.1.1.tgz", + "integrity": "sha512-Jd4cvbJMryN21r5HgxQOpMEqv+ooke/korixNNK3mGqfGJmy0M77WDDzo/05969+OkMy3XW1UuZsSmW9KQm7Fw==", + "dev": true, + "license": "MIT", + "dependencies": { + "asn1": "^0.2.4" + } + }, + "node_modules/node-sql-parser": { + "version": "5.4.0", + "resolved": "https://registry.npmjs.org/node-sql-parser/-/node-sql-parser-5.4.0.tgz", + "integrity": "sha512-jVe6Z61gPcPjCElPZ6j8llB3wnqGcuQzefim1ERsqIakxnEy5JlzV7XKdO1KmacRG5TKwPc4vJTgSRQ0LfkbFw==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@types/pegjs": "^0.10.0", + "big-integer": "^1.6.48" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/npm-run-path": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-6.0.0.tgz", + "integrity": "sha512-9qny7Z9DsQU8Ou39ERsPU4OZQlSTP47ShQzuKZ6PRXpYLtIFgl/DEBYEXKlvcEa+9tHVcK8CF81Y2V72qaZhWA==", + "dev": true, + "license": "MIT", + "dependencies": { + "path-key": "^4.0.0", + "unicorn-magic": "^0.3.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/npm-run-path/node_modules/path-key": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-4.0.0.tgz", + "integrity": "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/nunjucks": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/nunjucks/-/nunjucks-3.2.4.tgz", + "integrity": "sha512-26XRV6BhkgK0VOxfbU5cQI+ICFUtMLixv1noZn1tGU38kQH5A5nmmbk/O45xdyBhD1esk47nKrY0mvQpZIhRjQ==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "a-sync-waterfall": "^1.0.0", + "asap": "^2.0.3", + "commander": "^5.1.0" + }, + "bin": { + "nunjucks-precompile": "bin/precompile" + }, + "engines": { + "node": ">= 6.9.0" + }, + "peerDependencies": { + "chokidar": "^3.3.0" + }, + "peerDependenciesMeta": { + "chokidar": { + "optional": true + } + } + }, + "node_modules/nunjucks/node_modules/commander": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-5.1.0.tgz", + "integrity": "sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 6" + } + }, + "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==", + "dev": true, + "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==", + "dev": true, + "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", + "optional": true, + "engines": { + "node": ">= 0.4" + } + }, + "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==", + "dev": true, + "license": "MIT", + "dependencies": { + "ee-first": "1.1.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/on-headers": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/on-headers/-/on-headers-1.1.0.tgz", + "integrity": "sha512-737ZY3yNnXy37FHkQxPzt4UZ2UWPWiCZWLvFZ4fu5cueciegX0zGPnrlY6bwRg4FdQOe9YU8MkmJwGhoMybl8A==", + "dev": true, + "license": "MIT", + "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==", + "dev": true, + "license": "ISC", + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/one-time": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/one-time/-/one-time-1.0.0.tgz", + "integrity": "sha512-5DXOiRKwuSEcQ/l0kGCF6Q3jcADFv5tSmRaJck/OqkVFcOzutB134KRSfF0xDrL39MNnqxbHBbUUcjZIhTgb2g==", + "dev": true, + "license": "MIT", + "dependencies": { + "fn.name": "1.x.x" + } + }, + "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/onnxruntime-common": { + "version": "1.24.3", + "resolved": "https://registry.npmjs.org/onnxruntime-common/-/onnxruntime-common-1.24.3.tgz", + "integrity": "sha512-GeuPZO6U/LBJXvwdaqHbuUmoXiEdeCjWi/EG7Y1HNnDwJYuk6WUbNXpF6luSUY8yASul3cmUlLGrCCL1ZgVXqA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/onnxruntime-node": { + "version": "1.24.3", + "resolved": "https://registry.npmjs.org/onnxruntime-node/-/onnxruntime-node-1.24.3.tgz", + "integrity": "sha512-JH7+czbc8ALA819vlTgcV+Q214/+VjGeBHDjX81+ZCD0PCVCIFGFNtT0V4sXG/1JXypKPgScQcB3ij/hk3YnTg==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "optional": true, + "os": [ + "win32", + "darwin", + "linux" + ], + "dependencies": { + "adm-zip": "^0.5.16", + "global-agent": "^3.0.0", + "onnxruntime-common": "1.24.3" + } + }, + "node_modules/onnxruntime-web": { + "version": "1.26.0-dev.20260416-b7804b056c", + "resolved": "https://registry.npmjs.org/onnxruntime-web/-/onnxruntime-web-1.26.0-dev.20260416-b7804b056c.tgz", + "integrity": "sha512-MD6Ss4GSpQBo6zqoJzyT9LRbKYs7x/JVN23FT24EcEvlqF4VuzPOeH6X38orZPKHQDbprn7K+SBpu0/mj2CQiw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "flatbuffers": "^25.1.24", + "guid-typescript": "^1.0.9", + "long": "^5.2.3", + "onnxruntime-common": "1.24.0-dev.20251116-b39e144322", + "platform": "^1.3.6", + "protobufjs": "^7.2.4" + } + }, + "node_modules/onnxruntime-web/node_modules/onnxruntime-common": { + "version": "1.24.0-dev.20251116-b39e144322", + "resolved": "https://registry.npmjs.org/onnxruntime-common/-/onnxruntime-common-1.24.0-dev.20251116-b39e144322.tgz", + "integrity": "sha512-BOoomdHYmNRL5r4iQ4bMvsl2t0/hzVQ3OM3PHD0gxeXu1PmggqBv3puZicEUVOA3AtHHYmqZtjMj9FOfGrATTw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/onnxruntime-web/node_modules/protobufjs": { + "version": "7.6.0", + "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-7.6.0.tgz", + "integrity": "sha512-LtESOsMPTZgyYtwxhvdgdjGL0HmXEaRA/hVD6sol4zA60hVXXXP/SGmxnqDbgGE8gy7pYex7cym+5vYPcmaXBQ==", + "dev": true, + "hasInstallScript": true, + "license": "BSD-3-Clause", + "optional": true, + "dependencies": { + "@protobufjs/aspromise": "^1.1.2", + "@protobufjs/base64": "^1.1.2", + "@protobufjs/codegen": "^2.0.5", + "@protobufjs/eventemitter": "^1.1.0", + "@protobufjs/fetch": "^1.1.1", + "@protobufjs/float": "^1.0.2", + "@protobufjs/inquire": "^1.1.2", + "@protobufjs/path": "^1.1.2", + "@protobufjs/pool": "^1.1.0", + "@protobufjs/utf8": "^1.1.1", + "@types/node": ">=13.7.0", + "long": "^5.3.2" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/open": { + "version": "10.2.0", + "resolved": "https://registry.npmjs.org/open/-/open-10.2.0.tgz", + "integrity": "sha512-YgBpdJHPyQ2UE5x+hlSXcnejzAvD0b22U2OuAP+8OnlJT+PjWPxtgmGqKKc+RgTM63U9gN0YzrYc71R2WT/hTA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "default-browser": "^5.2.1", + "define-lazy-prop": "^3.0.0", + "is-inside-container": "^1.0.0", + "wsl-utils": "^0.1.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/openai": { + "version": "6.38.0", + "resolved": "https://registry.npmjs.org/openai/-/openai-6.38.0.tgz", + "integrity": "sha512-AoMplt2UalrpgUDMh3L09QWjNRlgJPipclQvA6sYAaeF6nHNBMgmikAZGmcYLn8on4d9sQY9Q8bOLfrBS7Lc8g==", + "dev": true, + "license": "Apache-2.0", + "bin": { + "openai": "bin/cli" + }, + "peerDependencies": { + "ws": "^8.18.0", + "zod": "^3.25 || ^4.0" + }, + "peerDependenciesMeta": { + "ws": { + "optional": true + }, + "zod": { + "optional": true + } + } + }, + "node_modules/openapi-fetch": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/openapi-fetch/-/openapi-fetch-0.8.2.tgz", + "integrity": "sha512-4g+NLK8FmQ51RW6zLcCBOVy/lwYmFJiiT+ckYZxJWxUxH4XFhsNcX2eeqVMfVOi+mDNFja6qDXIZAz2c5J/RVw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "openapi-typescript-helpers": "^0.0.5" + } + }, + "node_modules/openapi-typescript-helpers": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/openapi-typescript-helpers/-/openapi-typescript-helpers-0.0.5.tgz", + "integrity": "sha512-MRffg93t0hgGZbYTxg60hkRIK2sRuEOHEtCUgMuLgbCC33TMQ68AmxskzUlauzZYD47+ENeGV/ElI7qnWqrAxA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/opener": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/opener/-/opener-1.5.2.tgz", + "integrity": "sha512-ur5UIdyw5Y7yEj9wLzhqXiy6GZ3Mwx0yGI+5sMn2r0N0v3cKJvUmFH5yPP+WXh9e0xfyzyJX95D8l088DNFj7A==", + "dev": true, + "license": "(WTFPL OR MIT)", + "bin": { + "opener": "bin/opener-bin.js" + } + }, + "node_modules/ora": { + "version": "9.4.0", + "resolved": "https://registry.npmjs.org/ora/-/ora-9.4.0.tgz", + "integrity": "sha512-84cglkRILFxdtA8hAvLNdMrtBpPNBTrQ9/ulg0FA7xLMnD6mifv+enAIeRmvtv+WgdCE+LPGOfQmtJRrVaIVhQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "chalk": "^5.6.2", + "cli-cursor": "^5.0.0", + "cli-spinners": "^3.2.0", + "is-interactive": "^2.0.0", + "is-unicode-supported": "^2.1.0", + "log-symbols": "^7.0.1", + "stdin-discarder": "^0.3.2", + "string-width": "^8.1.0" + }, + "engines": { + "node": ">=20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/ora/node_modules/ansi-regex": { + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.2.2.tgz", + "integrity": "sha512-Bq3SmSpyFHaWjPk8If9yc6svM8c56dB5BAtW4Qbw5jHTwwXXcTLoRMkpDJp6VL0XzlWaCHTXrkFURMYmD0sLqg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-regex?sponsor=1" + } + }, + "node_modules/ora/node_modules/string-width": { + "version": "8.2.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-8.2.1.tgz", + "integrity": "sha512-IIaP0g3iy9Cyy18w3M9YcaDudujEAVHKt3a3QJg1+sr/oX96TbaGUubG0hJyCjCBThFH+tFpcIyoUHUn1ogaLA==", + "dev": true, + "license": "MIT", + "dependencies": { + "get-east-asian-width": "^1.5.0", + "strip-ansi": "^7.1.2" + }, + "engines": { + "node": ">=20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/ora/node_modules/strip-ansi": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.2.0.tgz", + "integrity": "sha512-yDPMNjp4WyfYBkHnjIRLfca1i6KMyGCtsVgoKe/z1+6vukgaENdgGBZt+ZmKPc4gavvEZ5OgHfHdrazhgNyG7w==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-regex": "^6.2.2" + }, + "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/p-finally": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha512-LICb2p9CB7FS+0eR1oqWnHhp0FljGLZCWBE9aix0Uye9W8LTQPwMTYVGWQWIw9RdQiDg4+epXQODwIYJtSJaow==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/p-queue": { + "version": "6.6.2", + "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-6.6.2.tgz", + "integrity": "sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "eventemitter3": "^4.0.4", + "p-timeout": "^3.2.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-queue-compat": { + "version": "1.0.225", + "resolved": "https://registry.npmjs.org/p-queue-compat/-/p-queue-compat-1.0.225.tgz", + "integrity": "sha512-SdfGSQSJJpD7ZR+dJEjjn9GuuBizHPLW/yarJpXnmrHRruzrq7YM8OqsikSrKeoPv+Pi1YXw9IIBSIg5WveQHA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "eventemitter3": "5.x", + "p-timeout-compat": "^1.0.3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/p-queue/node_modules/eventemitter3": { + "version": "4.0.7", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", + "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/p-retry": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/p-retry/-/p-retry-4.6.2.tgz", + "integrity": "sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@types/retry": "0.12.0", + "retry": "^0.13.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/p-timeout": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-3.2.0.tgz", + "integrity": "sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "p-finally": "^1.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/p-timeout-compat": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/p-timeout-compat/-/p-timeout-compat-1.0.8.tgz", + "integrity": "sha512-+7LpKr1ilnWU0LbV2r+Wz4srwMcFTUysmgL824ZxJcZP3u4Hyi/D/39pbyEs4j0XXCHvbv069+LDPxlCijfVRQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/pac-proxy-agent": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/pac-proxy-agent/-/pac-proxy-agent-9.0.1.tgz", + "integrity": "sha512-3ZOSpLboOlpW4yp8Cuv21KlTULRqyJ5Uuad3wXpSKFrxdNgcHEyoa22GRaZ2UlgCVuR6z+5BiavtYVvbajL/Yw==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4", + "get-uri": "8.0.0", + "http-proxy-agent": "9.0.0", + "https-proxy-agent": "9.0.0", + "pac-resolver": "9.0.1", + "quickjs-wasi": "^2.2.0", + "socks-proxy-agent": "10.0.0" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/pac-proxy-agent/node_modules/agent-base": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-9.0.0.tgz", + "integrity": "sha512-TQf59BsZnytt8GdJKLPfUZ54g/iaUL2OWDSFCCvMOhsHduDQxO8xC4PNeyIkVcA5KwL2phPSv0douC0fgWzmnA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 20" + } + }, + "node_modules/pac-proxy-agent/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/pac-proxy-agent/node_modules/http-proxy-agent": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-9.0.0.tgz", + "integrity": "sha512-FcF8VhXYLQcxWCnt/cCpT2apKsRDUGeVEeMqGu4HSTu29U8Yw0TLOjdYIlDsYk3IkUh+taX4IDWpPcCqKDhCjA==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/pac-proxy-agent/node_modules/https-proxy-agent": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-9.0.0.tgz", + "integrity": "sha512-/MVmHp58WkOypgFhCLk4fzpPcFQvTJ/e6LBI7irpIO2HfxUbpmYoHF+KzipzJpxxzJu7aJNWQ0xojJ/dzV2G5g==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/pac-proxy-agent/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/pac-resolver": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/pac-resolver/-/pac-resolver-9.0.1.tgz", + "integrity": "sha512-lJbS008tmkj08VhoM8Hzuv/VE5tK9MS0OIQ/7+s0lIF+BYhiQWFYzkSpML7lXs9iBu2jfmzBTLzhe9n6BX+dYw==", + "dev": true, + "license": "MIT", + "dependencies": { + "degenerator": "7.0.1", + "netmask": "^2.0.2" + }, + "engines": { + "node": ">= 20" + }, + "peerDependencies": { + "quickjs-wasi": "^2.2.0" + } + }, + "node_modules/parse-ms": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-ms/-/parse-ms-4.0.0.tgz", + "integrity": "sha512-TXfryirbmq34y8QBwgqCVLi+8oA3oWx2eAnSn62ITyEhEYaWRlVZ2DvMM9eZbMs/RfxPu/PK/aBLyGj4IrqMHw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/parse5": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-8.0.1.tgz", + "integrity": "sha512-z1e/HMG90obSGeidlli3hj7cbocou0/wa5HacvI3ASx34PecNjNQeaHNo5WIZpWofN9kgkqV1q5YvXe3F0FoPw==", + "dev": true, + "license": "MIT", + "dependencies": { + "entities": "^8.0.0" + }, + "funding": { + "url": "https://github.com/inikulin/parse5?sponsor=1" + } + }, + "node_modules/parseurl": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/path-expression-matcher": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/path-expression-matcher/-/path-expression-matcher-1.5.0.tgz", + "integrity": "sha512-cbrerZV+6rvdQrrD+iGMcZFEiiSrbv9Tfdkvnusy6y0x0GKBXREFg/Y65GhIfm0tnLntThhzCnfKwp1WRjeCyQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/NaturalIntelligence" + } + ], + "license": "MIT", + "engines": { + "node": ">=14.0.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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, + "node_modules/path-scurry": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/path-scurry/-/path-scurry-2.0.2.tgz", + "integrity": "sha512-3O/iVVsJAPsOnpwWIeD+d6z/7PmqApyQePUtCndjatj/9I5LylHvt5qluFaBT3I5h3r1ejfR056c+FCv+NnNXg==", + "dev": true, + "license": "BlueOak-1.0.0", + "dependencies": { + "lru-cache": "^11.0.0", + "minipass": "^7.1.2" + }, + "engines": { + "node": "18 || 20 || >=22" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/path-to-regexp": { + "version": "8.4.2", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-8.4.2.tgz", + "integrity": "sha512-qRcuIdP69NPm4qbACK+aDogI5CBDMi1jKe0ry5rSQJz8JVLsC7jV8XpiJjGRLLol3N+R5ihGYcrPLTno6pAdBA==", + "dev": true, + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/pdf-parse": { + "version": "2.4.5", + "resolved": "https://registry.npmjs.org/pdf-parse/-/pdf-parse-2.4.5.tgz", + "integrity": "sha512-mHU89HGh7v+4u2ubfnevJ03lmPgQ5WU4CxAVmTSh/sxVTEDYd1er/dKS/A6vg77NX47KTEoihq8jZBLr8Cxuwg==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@napi-rs/canvas": "0.1.80", + "pdfjs-dist": "5.4.296" + }, + "bin": { + "pdf-parse": "bin/cli.mjs" + }, + "engines": { + "node": ">=20.16.0 <21 || >=22.3.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/mehmet-kozan" + } + }, + "node_modules/pdfjs-dist": { + "version": "5.4.296", + "resolved": "https://registry.npmjs.org/pdfjs-dist/-/pdfjs-dist-5.4.296.tgz", + "integrity": "sha512-DlOzet0HO7OEnmUmB6wWGJrrdvbyJKftI1bhMitK7O2N8W2gc757yyYBbINy9IDafXAV9wmKr9t7xsTaNKRG5Q==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "engines": { + "node": ">=20.16.0 || >=22.3.0" + }, + "optionalDependencies": { + "@napi-rs/canvas": "^0.1.80" + } + }, + "node_modules/pem": { + "version": "1.14.8", + "resolved": "https://registry.npmjs.org/pem/-/pem-1.14.8.tgz", + "integrity": "sha512-ZpbOf4dj9/fQg5tQzTqv4jSKJQsK7tPl0pm4/pvPcZVjZcJg7TMfr3PBk6gJH97lnpJDu4e4v8UUqEz5daipCg==", + "dev": true, + "license": "MIT", + "dependencies": { + "es6-promisify": "^7.0.0", + "md5": "^2.3.0", + "os-tmpdir": "^1.0.2", + "which": "^2.0.2" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/pg": { + "version": "8.21.0", + "resolved": "https://registry.npmjs.org/pg/-/pg-8.21.0.tgz", + "integrity": "sha512-AUP1EYJuHraQGsVoCQVIcM7TEJVGtDzxWtGFZd8rds9d+CCXlU5Js1rYgfLNvxy9iJrpHjGrRjoi/3BT9fRyiA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "pg-connection-string": "^2.13.0", + "pg-pool": "^3.14.0", + "pg-protocol": "^1.14.0", + "pg-types": "2.2.0", + "pgpass": "1.0.5" + }, + "engines": { + "node": ">= 16.0.0" + }, + "optionalDependencies": { + "pg-cloudflare": "^1.4.0" + }, + "peerDependencies": { + "pg-native": ">=3.0.1" + }, + "peerDependenciesMeta": { + "pg-native": { + "optional": true + } + } + }, + "node_modules/pg-cloudflare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/pg-cloudflare/-/pg-cloudflare-1.4.0.tgz", + "integrity": "sha512-Vo7z/6rrQYxpNRylp4Tlob2elzbh+N/MOQbxFVWCxS7oEx6jF53GTJFxK2WWpKuBRkmiin4Mt+xofFDjx09R0A==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/pg-connection-string": { + "version": "2.13.0", + "resolved": "https://registry.npmjs.org/pg-connection-string/-/pg-connection-string-2.13.0.tgz", + "integrity": "sha512-EMnU9E2fSULdsbErBbMaXJvFeD9B4+nPcM3f+4lsiCR0BHLPrLVjv3DbyM2hgQQviKJaTWIRRTjKjWlHg3p2ig==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/pg-int8": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/pg-int8/-/pg-int8-1.0.1.tgz", + "integrity": "sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw==", + "dev": true, + "license": "ISC", + "optional": true, + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/pg-pool": { + "version": "3.14.0", + "resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.14.0.tgz", + "integrity": "sha512-gKtPkFdQPU3DksooVLi9LsjZxrsBUZIpa+7aVx+LV5pNh0KzP4Zleud2po+ConrxbuXGBJ6Hfer6hdgpIBpBaw==", + "dev": true, + "license": "MIT", + "optional": true, + "peerDependencies": { + "pg": ">=8.0" + } + }, + "node_modules/pg-protocol": { + "version": "1.14.0", + "resolved": "https://registry.npmjs.org/pg-protocol/-/pg-protocol-1.14.0.tgz", + "integrity": "sha512-n5taZ1kO3s9ngDTVxsEznOqCyToTgz0FLuPq0B33COy5pPpuWJpY3/2oRBVETuOgzdqRXfWpM9HIhp2LBBT1BA==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/pg-types": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/pg-types/-/pg-types-2.2.0.tgz", + "integrity": "sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "pg-int8": "1.0.1", + "postgres-array": "~2.0.0", + "postgres-bytea": "~1.0.0", + "postgres-date": "~1.0.4", + "postgres-interval": "^1.1.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/pgpass": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/pgpass/-/pgpass-1.0.5.tgz", + "integrity": "sha512-FdW9r/jQZhSeohs1Z3sI1yxFQNFvMcnmfuj4WBMUTxOrAyLMaTcE1aAMBiTlbMNaXvBCQuVi0R7hd8udDSP7ug==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "split2": "^4.1.0" + } + }, + "node_modules/pkce-challenge": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/pkce-challenge/-/pkce-challenge-5.0.1.tgz", + "integrity": "sha512-wQ0b/W4Fr01qtpHlqSqspcj3EhBvimsdh0KlHhH8HRZnMsEa0ea2fTULOXOS9ccQr3om+GcGRk4e+isrZWV8qQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=16.20.0" + } + }, + "node_modules/platform": { + "version": "1.3.6", + "resolved": "https://registry.npmjs.org/platform/-/platform-1.3.6.tgz", + "integrity": "sha512-fnWVljUchTro6RiCFvCXBbNhJc2NijN7oIQxbwsyL0buWJPG85v81ehlHI9fXrJsMNgTofEoWIQeClKpgxFLrg==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/playwright": { + "version": "1.60.0", + "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.60.0.tgz", + "integrity": "sha512-hheHdokM8cdqCb0lcE3s+zT4t4W+vvjpGxsZlDnikarzx8tSzMebh3UiFtgqwFwnTnjYQcsyMF8ei2mCO/tpeA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "playwright-core": "1.60.0" + }, + "bin": { + "playwright": "cli.js" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "fsevents": "2.3.2" + } + }, + "node_modules/playwright-core": { + "version": "1.60.0", + "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.60.0.tgz", + "integrity": "sha512-9bW6zvX/m0lEbgTKJ6YppOKx8H3VOPBMOCFh2irXFOT4BbHgrx5hPjwJYLT40Lu+4qtD36qKc/Hn56StUW57IA==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "bin": { + "playwright-core": "cli.js" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/playwright-extra": { + "version": "4.3.6", + "resolved": "https://registry.npmjs.org/playwright-extra/-/playwright-extra-4.3.6.tgz", + "integrity": "sha512-q2rVtcE8V8K3vPVF1zny4pvwZveHLH8KBuVU2MoE3Jw4OKVoBWsHI9CH9zPydovHHOCDxjGN2Vg+2m644q3ijA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "debug": "^4.3.4" + }, + "engines": { + "node": ">=12" + }, + "peerDependencies": { + "playwright": "*", + "playwright-core": "*" + }, + "peerDependenciesMeta": { + "playwright": { + "optional": true + }, + "playwright-core": { + "optional": true + } + } + }, + "node_modules/playwright-extra/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/playwright-extra/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", + "optional": true + }, + "node_modules/playwright/node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/postgres-array": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/postgres-array/-/postgres-array-2.0.0.tgz", + "integrity": "sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/postgres-bytea": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/postgres-bytea/-/postgres-bytea-1.0.1.tgz", + "integrity": "sha512-5+5HqXnsZPE65IJZSMkZtURARZelel2oXUEO8rH83VS/hxH5vv1uHquPg5wZs8yMAfdv971IU+kcPUczi7NVBQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/postgres-date": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/postgres-date/-/postgres-date-1.0.7.tgz", + "integrity": "sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/postgres-interval": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/postgres-interval/-/postgres-interval-1.2.0.tgz", + "integrity": "sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "xtend": "^4.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/posthog-node": { + "version": "5.24.17", + "resolved": "https://registry.npmjs.org/posthog-node/-/posthog-node-5.24.17.tgz", + "integrity": "sha512-mdb8TKt+YCRbGQdYar3AKNUPCyEiqcprScF4unYpGALF6HlBaEuO6wPuIqXXpCWkw4VclJYCKbb6lq6pH6bJeA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@posthog/core": "1.23.1" + }, + "engines": { + "node": "^20.20.0 || >=22.22.0" + } + }, + "node_modules/prebuild-install": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/prebuild-install/-/prebuild-install-7.1.3.tgz", + "integrity": "sha512-8Mf2cbV7x1cXPUILADGI3wuhfqWvtiLA1iclTDbFRZkgRQS0NqsPZphna9V+HyTEadheuPmjaJMsbzKQFOzLug==", + "deprecated": "No longer maintained. Please contact the author of the relevant native addon; alternatives are available.", + "dev": true, + "license": "MIT", + "dependencies": { + "detect-libc": "^2.0.0", + "expand-template": "^2.0.3", + "github-from-package": "0.0.0", + "minimist": "^1.2.3", + "mkdirp-classic": "^0.5.3", + "napi-build-utils": "^2.0.0", + "node-abi": "^3.3.0", + "pump": "^3.0.0", + "rc": "^1.2.7", + "simple-get": "^4.0.0", + "tar-fs": "^2.0.0", + "tunnel-agent": "^0.6.0" + }, + "bin": { + "prebuild-install": "bin.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/pretty-ms": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/pretty-ms/-/pretty-ms-9.3.0.tgz", + "integrity": "sha512-gjVS5hOP+M3wMm5nmNOucbIrqudzs9v/57bWRHQWLYklXqoXKrVfYW2W9+glfGsqtPgpiz5WwyEEB+ksXIx3gQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "parse-ms": "^4.0.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/promptfoo": { + "version": "0.121.11", + "resolved": "https://registry.npmjs.org/promptfoo/-/promptfoo-0.121.11.tgz", + "integrity": "sha512-URdQxCgfKbXfA5jFYBkYdGNcz6z2mo/umnGUJ1irVYNNDV9X8qUNAt0sC5OixTUCEGgx1+H9frcbboTtZuJybQ==", + "dev": true, + "license": "MIT", + "workspaces": [ + "src/app", + "site" + ], + "dependencies": { + "@anthropic-ai/sdk": "^0.92.0", + "@apidevtools/json-schema-ref-parser": "^15.3.1", + "@googleapis/sheets": "^13.0.1", + "@inquirer/checkbox": "^5.1.0", + "@inquirer/confirm": "^6.0.8", + "@inquirer/core": "^11.1.5", + "@inquirer/editor": "^5.0.8", + "@inquirer/input": "^5.0.8", + "@inquirer/select": "^5.1.0", + "@modelcontextprotocol/sdk": "^1.29.0", + "@openai/agents": "^0.8.5", + "@opencode-ai/sdk": "^1.14.33", + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.6.0", + "@opentelemetry/exporter-trace-otlp-http": "^0.216.0", + "@opentelemetry/resources": "^2.6.0", + "@opentelemetry/sdk-trace-base": "^2.6.0", + "@opentelemetry/sdk-trace-node": "^2.6.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@types/ws": "^8.18.1", + "ai": "^6.0.168", + "ajv": "^8.18.0", + "ajv-formats": "^3.0.1", + "async": "^3.2.6", + "better-sqlite3": "^12.8.0", + "binary-extensions": "^3.1.0", + "cache-manager": "^7.2.8", + "chalk": "^5.6.2", + "chokidar": "5.0.0", + "cli-progress": "^3.12.0", + "cli-table3": "^0.6.5", + "commander": "^14.0.3", + "compression": "^1.8.1", + "cors": "^2.8.6", + "csv-parse": "^6.2.0", + "csv-stringify": "^6.7.0", + "debounce": "^3.0.0", + "dedent": "^1.7.2", + "dotenv": "^17.3.1", + "drizzle-orm": "^0.45.1", + "execa": "^9.6.1", + "express": "^5.2.1", + "exsolve": "^1.0.8", + "fast-deep-equal": "^3.1.3", + "fast-safe-stringify": "^2.1.1", + "fast-xml-parser": "^5.7.1", + "fastest-levenshtein": "^1.0.16", + "gcp-metadata": "^8.1.2", + "glob": "^13.0.6", + "http-z": "^8.1.1", + "istextorbinary": "^9.5.0", + "jks-js": "^1.1.5", + "js-rouge": "^3.2.0", + "js-yaml": "^4.1.1", + "json5": "^2.2.3", + "keyv": "^5.6.0", + "keyv-file": "^5.3.3", + "lru-cache": "^11.3.0", + "mathjs": "^15.1.1", + "minimatch": "^10.2.4", + "nunjucks": "^3.2.4", + "openai": "^6.35.0", + "opener": "^1.5.2", + "ora": "^9.3.0", + "parse5": "^8.0.0", + "pem": "~1.14.8", + "posthog-node": "~5.24.10", + "protobufjs": "^8.0.0", + "proxy-agent": "^8.0.0", + "proxy-from-env": "^2.1.0", + "python-shell": "^5.0.0", + "rfdc": "^1.4.1", + "rxjs": "^7.8.2", + "semver": "^7.7.4", + "simple-git": "^3.33.0", + "socket.io": "^4.8.3", + "socket.io-client": "^4.8.3", + "text-extensions": "^3.1.0", + "tsx": "^4.21.0", + "undici": "^7.25.0", + "winston": "^3.19.0", + "ws": "^8.19.0", + "zod": "^4.3.6" + }, + "bin": { + "pf": "dist/src/entrypoint.js", + "promptfoo": "dist/src/entrypoint.js" + }, + "engines": { + "node": "^20.20.0 || >=22.22.0" + }, + "optionalDependencies": { + "@anthropic-ai/claude-agent-sdk": "^0.2.126", + "@aws-sdk/client-bedrock-agent-runtime": "^3.1040.0", + "@aws-sdk/client-bedrock-runtime": "^3.1040.0", + "@aws-sdk/client-s3": "^3.1003.0", + "@aws-sdk/client-sagemaker-runtime": "^3.1040.0", + "@aws-sdk/credential-provider-sso": "^3.972.16", + "@azure/ai-projects": "^2.1.0", + "@azure/identity": "^4.13.0", + "@azure/msal-node": "^5.1.0", + "@azure/openai-assistants": "^1.0.0-beta.6", + "@fal-ai/client": "~1.10.0", + "@huggingface/transformers": "^4.0.0", + "@ibm-cloud/watsonx-ai": "^1.7.11", + "@ibm-generative-ai/node-sdk": "^3.2.4", + "@openai/codex-sdk": "^0.128.0", + "@playwright/browser-chromium": "^1.59.1", + "@rollup/rollup-linux-x64-gnu": "^4.59.0", + "@slack/web-api": "^7.15.0", + "@smithy/node-http-handler": "^4.4.14", + "@swc/core": "^1.15.18", + "@swc/core-darwin-arm64": "^1.15.18", + "@swc/core-darwin-x64": "^1.15.18", + "@swc/core-linux-x64-gnu": "^1.15.18", + "@swc/core-linux-x64-musl": "^1.15.18", + "@swc/core-win32-x64-msvc": "^1.15.18", + "google-auth-library": "^10.6.2", + "hono": "^4.12.5", + "ibm-cloud-sdk-core": "^5.4.11", + "langfuse": "^3.38.20", + "natural": "^8.1.1", + "node-sql-parser": "^5.4.0", + "pdf-parse": "^2.4.5", + "playwright": "^1.59.1", + "playwright-extra": "^4.3.6", + "read-excel-file": "^9.0.0", + "sharp": "^0.34.5" + } + }, + "node_modules/promptfoo/node_modules/@anthropic-ai/claude-agent-sdk": { + "version": "0.2.141", + "resolved": "https://registry.npmjs.org/@anthropic-ai/claude-agent-sdk/-/claude-agent-sdk-0.2.141.tgz", + "integrity": "sha512-AIBacMWGcZIUcXlUoObqjwJ6pmJI3BayAqPAFXuvSq3DHJXdiuZVs7l/zTB5l3nRhRv5cqSrI2XbiDeHgZWizw==", + "dev": true, + "license": "SEE LICENSE IN README.md", + "optional": true, + "dependencies": { + "@anthropic-ai/sdk": "^0.93.0", + "@modelcontextprotocol/sdk": "^1.29.0" + }, + "engines": { + "node": ">=18.0.0" + }, + "optionalDependencies": { + "@anthropic-ai/claude-agent-sdk-darwin-arm64": "0.2.141", + "@anthropic-ai/claude-agent-sdk-darwin-x64": "0.2.141", + "@anthropic-ai/claude-agent-sdk-linux-arm64": "0.2.141", + "@anthropic-ai/claude-agent-sdk-linux-arm64-musl": "0.2.141", + "@anthropic-ai/claude-agent-sdk-linux-x64": "0.2.141", + "@anthropic-ai/claude-agent-sdk-linux-x64-musl": "0.2.141", + "@anthropic-ai/claude-agent-sdk-win32-arm64": "0.2.141", + "@anthropic-ai/claude-agent-sdk-win32-x64": "0.2.141" + }, + "peerDependencies": { + "zod": "^4.0.0" + } + }, + "node_modules/promptfoo/node_modules/@anthropic-ai/claude-agent-sdk/node_modules/@anthropic-ai/sdk": { + "version": "0.93.0", + "resolved": "https://registry.npmjs.org/@anthropic-ai/sdk/-/sdk-0.93.0.tgz", + "integrity": "sha512-q9vaSZQVFx6B/gPxetGYfLXSJD5v0sOmh0OpZDq7yCrTSA+Rscvrtyol7JJTW40wEpQB4U1B4JXzxQitbQ3CAA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "json-schema-to-ts": "^3.1.1" + }, + "bin": { + "anthropic-ai-sdk": "bin/cli" + }, + "peerDependencies": { + "zod": "^3.25.0 || ^4.0.0" + }, + "peerDependenciesMeta": { + "zod": { + "optional": true + } + } + }, + "node_modules/promptfoo/node_modules/@openai/agents": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/@openai/agents/-/agents-0.8.5.tgz", + "integrity": "sha512-OFA7XVV1qXE8lzatvQj080KdSArt8utBExFXRfD5B/R7KT0D+AVaKwg6nLoW3Gxb30vRkIUQf+MaW/Wz+gO3Yg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@openai/agents-core": "0.8.5", + "@openai/agents-openai": "0.8.5", + "@openai/agents-realtime": "0.8.5", + "debug": "^4.4.0", + "openai": "^6.26.0" + }, + "peerDependencies": { + "zod": "^4.0.0" + } + }, + "node_modules/promptfoo/node_modules/@openai/agents-core": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/@openai/agents-core/-/agents-core-0.8.5.tgz", + "integrity": "sha512-qs9mmN+D+UmqEZo3qrvhhIIXIOgSvJPic0v4a+ruq+eYgcQMk3PY8lLcsdQwJit6zf2Wyfv1q2cX5m3jzWZpKw==", + "dev": true, + "license": "MIT", + "dependencies": { + "debug": "^4.4.0", + "openai": "^6.26.0" + }, + "optionalDependencies": { + "@modelcontextprotocol/sdk": "^1.26.0" + }, + "peerDependencies": { + "zod": "^4.0.0" + }, + "peerDependenciesMeta": { + "zod": { + "optional": true + } + } + }, + "node_modules/promptfoo/node_modules/@openai/agents-openai": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/@openai/agents-openai/-/agents-openai-0.8.5.tgz", + "integrity": "sha512-cGYmyiVy8ecgf2Vch0L/ekeNo3xuZsuWnRsxyv+w9ai9dgxUifdEQ6G3dtsjMLtmXVHRVGoO7mVBr+tKcilntw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@openai/agents-core": "0.8.5", + "debug": "^4.4.0", + "openai": "^6.26.0" + }, + "peerDependencies": { + "zod": "^4.0.0" + } + }, + "node_modules/promptfoo/node_modules/@openai/agents-realtime": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/@openai/agents-realtime/-/agents-realtime-0.8.5.tgz", + "integrity": "sha512-JqKVsR33OvKtTxRp5Ylhw8WfNvJ49ZIhlhMZlSVKqwR2Ks6JuxqFJ0zM9p7JIbTQDSlAZnmnZJv1qlItaildiQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@openai/agents-core": "0.8.5", + "@types/ws": "^8.18.1", + "debug": "^4.4.0", + "ws": "^8.18.1" + }, + "peerDependencies": { + "zod": "^4.0.0" + } + }, + "node_modules/promptfoo/node_modules/chokidar": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-5.0.0.tgz", + "integrity": "sha512-TQMmc3w+5AxjpL8iIiwebF73dRDF4fBIieAqGn9RGCWaEVwQ6Fb2cGe31Yns0RRIzii5goJ1Y7xbMwo1TxMplw==", + "dev": true, + "license": "MIT", + "dependencies": { + "readdirp": "^5.0.0" + }, + "engines": { + "node": ">= 20.19.0" + }, + "funding": { + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/promptfoo/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/promptfoo/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/promptfoo/node_modules/readdirp": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-5.0.0.tgz", + "integrity": "sha512-9u/XQ1pvrQtYyMpZe7DXKv2p5CNvyVwzUB6uhLAnQwHMSgKMBR62lc7AHljaeteeHXn11XTAaLLUVZYVZyuRBQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 20.19.0" + }, + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/promptfoo/node_modules/zod": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/zod/-/zod-4.4.3.tgz", + "integrity": "sha512-ytENFjIJFl2UwYglde2jchW2Hwm4GJFLDiSXWdTrJQBIN9Fcyp7n4DhxJEiWNAJMV1/BqWfW/kkg71UDcHJyTQ==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/colinhacks" + } + }, + "node_modules/protobufjs": { + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-8.4.0.tgz", + "integrity": "sha512-iriNhQ57SYA5Jbdi+41AyPdx6jPPkFO7DODzkOBmqFhgYn/JzX2HxgxYPY18eQAs3CP/AWqtPvkWn8rclRAxdQ==", + "dev": true, + "hasInstallScript": true, + "license": "BSD-3-Clause", + "dependencies": { + "long": "^5.3.2" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "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==", + "dev": true, + "license": "MIT", + "dependencies": { + "forwarded": "0.2.0", + "ipaddr.js": "1.9.1" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/proxy-agent": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/proxy-agent/-/proxy-agent-8.0.1.tgz", + "integrity": "sha512-kccqGBqHZXR8onQhY/ganJjoO8QIKKRiFBhPOzbTZK16attzSZ/0XSmp9H7jrRxPKHjhGyx1q32lMPrJ3uLFgA==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4", + "http-proxy-agent": "9.0.0", + "https-proxy-agent": "9.0.0", + "lru-cache": "^7.14.1", + "pac-proxy-agent": "9.0.1", + "proxy-from-env": "^2.0.0", + "socks-proxy-agent": "10.0.0" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/proxy-agent/node_modules/agent-base": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-9.0.0.tgz", + "integrity": "sha512-TQf59BsZnytt8GdJKLPfUZ54g/iaUL2OWDSFCCvMOhsHduDQxO8xC4PNeyIkVcA5KwL2phPSv0douC0fgWzmnA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 20" + } + }, + "node_modules/proxy-agent/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/proxy-agent/node_modules/http-proxy-agent": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-9.0.0.tgz", + "integrity": "sha512-FcF8VhXYLQcxWCnt/cCpT2apKsRDUGeVEeMqGu4HSTu29U8Yw0TLOjdYIlDsYk3IkUh+taX4IDWpPcCqKDhCjA==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/proxy-agent/node_modules/https-proxy-agent": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-9.0.0.tgz", + "integrity": "sha512-/MVmHp58WkOypgFhCLk4fzpPcFQvTJ/e6LBI7irpIO2HfxUbpmYoHF+KzipzJpxxzJu7aJNWQ0xojJ/dzV2G5g==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/proxy-agent/node_modules/lru-cache": { + "version": "7.18.3", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.18.3.tgz", + "integrity": "sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA==", + "dev": true, + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/proxy-agent/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/proxy-from-env": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-2.1.0.tgz", + "integrity": "sha512-cJ+oHTW1VAEa8cJslgmUZrc+sjRKgAKl3Zyse6+PV38hZe/V6Z14TbCuXcan9F9ghlz4QrFr2c92TNF82UkYHA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + } + }, + "node_modules/psl": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.15.0.tgz", + "integrity": "sha512-JZd3gMVBAVQkSs6HdNZo9Sdo0LNcQeMNP3CozBJb3JYC/QUYZTnKxP+f8oWRX4rHP5EurWxqAHTSwUCjlNKa1w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "punycode": "^2.3.1" + }, + "funding": { + "url": "https://github.com/sponsors/lupomontero" + } + }, + "node_modules/pump": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.4.tgz", + "integrity": "sha512-VS7sjc6KR7e1ukRFhQSY5LM2uBWAUPiOPa/A3mkKmiMwSmRFUITt0xuj+/lesgnCv+dPIEYlkzrcyXgquIHMcA==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/python-shell": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/python-shell/-/python-shell-5.0.0.tgz", + "integrity": "sha512-RUOOOjHLhgR1MIQrCtnEqz/HJ1RMZBIN+REnpSUrfft2bXqXy69fwJASVziWExfFXsR1bCY0TznnHooNsCo0/w==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10" + } + }, + "node_modules/qs": { + "version": "6.15.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.15.2.tgz", + "integrity": "sha512-Rzq0KEyX/w/tEybncDgdkZrJgVUsUMk3xjh3t5bv3S1HTAtg+uOYt72+ZfwiQwKdysThkTBdL/rTi6HDmX9Ddw==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "side-channel": "^1.1.0" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/querystringify": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/querystringify/-/querystringify-2.2.0.tgz", + "integrity": "sha512-FIqgj2EUvTa7R50u0rGsyTftzjYmv/a3hO345bZNrqabNqjtgiDMgmo4mkUjd+nzU5oF3dClKqFIPUKybUyqoQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/quickjs-wasi": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/quickjs-wasi/-/quickjs-wasi-2.2.0.tgz", + "integrity": "sha512-zQxXmQMrEoD3S+jQdYsloq4qAuaxKFHZj6hHqOYGwB2iQZH+q9e/lf5zQPXCKOk0WJuAjzRFbO4KwHIp2D05Iw==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/raw-body": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-3.0.2.tgz", + "integrity": "sha512-K5zQjDllxWkf7Z5xJdV0/B0WTNqx6vxG70zJE4N0kBs4LovmEYWJzQGxC9bS9RAKu3bgM40lrd5zoLJ12MQ5BA==", + "dev": true, + "license": "MIT", + "dependencies": { + "bytes": "~3.1.2", + "http-errors": "~2.0.1", + "iconv-lite": "~0.7.0", + "unpipe": "~1.0.0" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, + "license": "(BSD-2-Clause OR MIT OR Apache-2.0)", + "dependencies": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "bin": { + "rc": "cli.js" + } + }, + "node_modules/read-excel-file": { + "version": "9.0.9", + "resolved": "https://registry.npmjs.org/read-excel-file/-/read-excel-file-9.0.9.tgz", + "integrity": "sha512-FWwC3IypIQDVPTtO4pz0Sq6An7lQI17pXqCusaTX8yi3p9CCRtXx/SI3BtcPSTaLhwcwr9mI+KXSa/dWMmnvjQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@xmldom/xmldom": "^0.9.9", + "fflate": "^0.8.2", + "unzipper": "^0.12.3" + }, + "engines": { + "node": ">=18" + } + }, + "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/redis": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/redis/-/redis-5.12.1.tgz", + "integrity": "sha512-LDsoVvb/CpoV9EN3FXvgvSHNJWuCIzl9MiO3ppOevuGLpSGJhwfQjpEwfFJcQvNSddHADDdZaWx0HnmMxRXG7g==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@redis/bloom": "5.12.1", + "@redis/client": "5.12.1", + "@redis/json": "5.12.1", + "@redis/search": "5.12.1", + "@redis/time-series": "5.12.1" + }, + "engines": { + "node": ">= 18.19.0" + } + }, + "node_modules/require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/requires-port": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", + "integrity": "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "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/retry": { + "version": "0.13.1", + "resolved": "https://registry.npmjs.org/retry/-/retry-0.13.1.tgz", + "integrity": "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/retry-axios": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/retry-axios/-/retry-axios-2.6.0.tgz", + "integrity": "sha512-pOLi+Gdll3JekwuFjXO3fTq+L9lzMQGcSq7M5gIjExcl3Gu1hd4XXuf5o3+LuSBsaULQH7DiNbsqPd1chVpQGQ==", + "dev": true, + "license": "Apache-2.0", + "optional": true, + "engines": { + "node": ">=10.7.0" + }, + "peerDependencies": { + "axios": "*" + } + }, + "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/roarr": { + "version": "2.15.4", + "resolved": "https://registry.npmjs.org/roarr/-/roarr-2.15.4.tgz", + "integrity": "sha512-CHhPh+UNHD2GTXNYhPWLnU8ONHdI+5DI+4EYIAOaiD63rHeYlZvyh8P+in5999TTSFgUYuKUAjzRI4mdh/p+2A==", + "dev": true, + "license": "BSD-3-Clause", + "optional": true, + "dependencies": { + "boolean": "^3.0.1", + "detect-node": "^2.0.4", + "globalthis": "^1.0.1", + "json-stringify-safe": "^5.0.1", + "semver-compare": "^1.0.0", + "sprintf-js": "^1.1.2" + }, + "engines": { + "node": ">=8.0" + } + }, + "node_modules/robot3": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/robot3/-/robot3-0.4.1.tgz", + "integrity": "sha512-hzjy826lrxzx8eRgv80idkf8ua1JAepRc9Efdtj03N3KNJuznQCPlyCJ7gnUmDFwZCLQjxy567mQVKmdv2BsXQ==", + "dev": true, + "license": "BSD-2-Clause", + "optional": true + }, + "node_modules/router": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/router/-/router-2.2.0.tgz", + "integrity": "sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==", + "dev": true, + "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/router/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/router/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/run-applescript": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/run-applescript/-/run-applescript-7.1.0.tgz", + "integrity": "sha512-DPe5pVFaAsinSaV6QjQ6gdiedWDcRCbUuiQfQa2wmWV7+xC9bGulGI8+TdRmoFkAPaBXk8CrAbnlY2ISniJ47Q==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "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/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==", + "dev": true, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/seedrandom": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/seedrandom/-/seedrandom-3.0.5.tgz", + "integrity": "sha512-8OwmbklUNzwezjGInmZ+2clQmExQPvomqjL7LFqOYqtmuxRgQYqOD3mHaU+MvZn5FLUeVxVfQjwLZW/n/JFuqg==", + "dev": true, + "license": "MIT" + }, + "node_modules/semver": { + "version": "7.8.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.8.0.tgz", + "integrity": "sha512-AcM7dV/5ul4EekoQ29Agm5vri8JNqRyj39o0qpX6vDF2GZrtutZl5RwgD1XnZjiTAfncsJhMI48QQH3sN87YNA==", + "dev": true, + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/semver-compare": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/semver-compare/-/semver-compare-1.0.0.tgz", + "integrity": "sha512-YM3/ITh2MJ5MtzaM429anh+x2jiLVjqILF4m4oyQB18W7Ggea7BfqdH/wGMK7dDiMghv/6WG7znWMwUDzJiXow==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/send": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/send/-/send-1.2.1.tgz", + "integrity": "sha512-1gnZf7DFcoIcajTjTwjwuDjzuz4PPcY2StKPlsGAQ1+YH20IRVrBaXSWmdjowTJ6u8Rc01PoYOGHXfP1mYcZNQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "debug": "^4.4.3", + "encodeurl": "^2.0.0", + "escape-html": "^1.0.3", + "etag": "^1.8.1", + "fresh": "^2.0.0", + "http-errors": "^2.0.1", + "mime-types": "^3.0.2", + "ms": "^2.1.3", + "on-finished": "^2.4.1", + "range-parser": "^1.2.1", + "statuses": "^2.0.2" + }, + "engines": { + "node": ">= 18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/send/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "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==", + "dev": true, + "license": "MIT" + }, + "node_modules/serialize-error": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/serialize-error/-/serialize-error-7.0.1.tgz", + "integrity": "sha512-8I8TjW5KMOKsZQTvoxjuSIa7foAwPWGOts+6o7sgjz41/qMD9VQHEDxi6PBvK2l0MXUmqZyNpUK+T2tQaaElvw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "type-fest": "^0.13.1" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/serve-static": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-2.2.1.tgz", + "integrity": "sha512-xRXBn0pPqQTVQiC8wyQrKs2MOlX24zQ0POGaj0kultvoOCstBQM5yvOhAVSUwOMjQtTvsPWoNCHfPGwaaQJhTw==", + "dev": true, + "license": "MIT", + "dependencies": { + "encodeurl": "^2.0.0", + "escape-html": "^1.0.3", + "parseurl": "^1.3.3", + "send": "^1.2.0" + }, + "engines": { + "node": ">= 18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/setprototypeof": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", + "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", + "dev": true, + "license": "ISC" + }, + "node_modules/sharp": { + "version": "0.34.5", + "resolved": "https://registry.npmjs.org/sharp/-/sharp-0.34.5.tgz", + "integrity": "sha512-Ou9I5Ft9WNcCbXrU9cMgPBcCK8LiwLqcbywW3t4oDV37n1pzpuNLsYiAV8eODnjbtQlSDwZ2cUEeQz4E54Hltg==", + "dev": true, + "hasInstallScript": true, + "license": "Apache-2.0", + "optional": true, + "dependencies": { + "@img/colour": "^1.0.0", + "detect-libc": "^2.1.2", + "semver": "^7.7.3" + }, + "engines": { + "node": "^18.17.0 || ^20.3.0 || >=21.0.0" + }, + "funding": { + "url": "https://opencollective.com/libvips" + }, + "optionalDependencies": { + "@img/sharp-darwin-arm64": "0.34.5", + "@img/sharp-darwin-x64": "0.34.5", + "@img/sharp-libvips-darwin-arm64": "1.2.4", + "@img/sharp-libvips-darwin-x64": "1.2.4", + "@img/sharp-libvips-linux-arm": "1.2.4", + "@img/sharp-libvips-linux-arm64": "1.2.4", + "@img/sharp-libvips-linux-ppc64": "1.2.4", + "@img/sharp-libvips-linux-riscv64": "1.2.4", + "@img/sharp-libvips-linux-s390x": "1.2.4", + "@img/sharp-libvips-linux-x64": "1.2.4", + "@img/sharp-libvips-linuxmusl-arm64": "1.2.4", + "@img/sharp-libvips-linuxmusl-x64": "1.2.4", + "@img/sharp-linux-arm": "0.34.5", + "@img/sharp-linux-arm64": "0.34.5", + "@img/sharp-linux-ppc64": "0.34.5", + "@img/sharp-linux-riscv64": "0.34.5", + "@img/sharp-linux-s390x": "0.34.5", + "@img/sharp-linux-x64": "0.34.5", + "@img/sharp-linuxmusl-arm64": "0.34.5", + "@img/sharp-linuxmusl-x64": "0.34.5", + "@img/sharp-wasm32": "0.34.5", + "@img/sharp-win32-arm64": "0.34.5", + "@img/sharp-win32-ia32": "0.34.5", + "@img/sharp-win32-x64": "0.34.5" + } + }, + "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==", + "dev": true, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=8" + } + }, + "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==", + "dev": true, + "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.1", + "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.1.tgz", + "integrity": "sha512-mjn/0bi/oUURjc5Xl7IaWi/OJJJumuoJFQJfDDyO46+hBWsfaVM65TBHq2eoZBhzl9EchxOijpkbRC8SVBQU0w==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "object-inspect": "^1.13.4" + }, + "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==", + "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" + }, + "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==", + "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" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/sift": { + "version": "17.1.3", + "resolved": "https://registry.npmjs.org/sift/-/sift-17.1.3.tgz", + "integrity": "sha512-Rtlj66/b0ICeFzYTuNvX/EF1igRbbnGSvEyT79McoZa/DeGhMyC5pWKOEsZKnpkqtSeovd5FL/bjHWC3CIIvCQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "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/simple-concat": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.1.tgz", + "integrity": "sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==", + "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/simple-get": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-4.0.1.tgz", + "integrity": "sha512-brv7p5WgH0jmQJr1ZDDfKDOSeWWg+OVypG99A/5vYGPqJ6pxiaHLy8nxtFjBA7oMa01ebA9gfh1uMCFqOuXxvA==", + "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": { + "decompress-response": "^6.0.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" + } + }, + "node_modules/simple-git": { + "version": "3.36.0", + "resolved": "https://registry.npmjs.org/simple-git/-/simple-git-3.36.0.tgz", + "integrity": "sha512-cGQjLjK8bxJw4QuYT7gxHw3/IouVESbhahSsHrX97MzCL1gu2u7oy38W6L2ZIGECEfIBG4BabsWDPjBxJENv9Q==", + "dev": true, + "license": "MIT", + "dependencies": { + "@kwsites/file-exists": "^1.1.1", + "@kwsites/promise-deferred": "^1.1.1", + "@simple-git/args-pathspec": "^1.0.3", + "@simple-git/argv-parser": "^1.1.0", + "debug": "^4.4.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/steveukx/git-js?sponsor=1" + } + }, + "node_modules/simple-git/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/simple-git/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/smart-buffer": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz", + "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 6.0.0", + "npm": ">= 3.0.0" + } + }, + "node_modules/socket.io": { + "version": "4.8.3", + "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.8.3.tgz", + "integrity": "sha512-2Dd78bqzzjE6KPkD5fHZmDAKRNe3J15q+YHDrIsy9WEkqttc7GY+kT9OBLSMaPbQaEd0x1BjcmtMtXkfpc+T5A==", + "dev": true, + "license": "MIT", + "dependencies": { + "accepts": "~1.3.4", + "base64id": "~2.0.0", + "cors": "~2.8.5", + "debug": "~4.4.1", + "engine.io": "~6.6.0", + "socket.io-adapter": "~2.5.2", + "socket.io-parser": "~4.2.4" + }, + "engines": { + "node": ">=10.2.0" + } + }, + "node_modules/socket.io-adapter": { + "version": "2.5.6", + "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-2.5.6.tgz", + "integrity": "sha512-DkkO/dz7MGln0dHn5bmN3pPy+JmywNICWrJqVWiVOyvXjWQFIv9c2h24JrQLLFJ2aQVQf/Cvl1vblnd4r2apLQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "debug": "~4.4.1", + "ws": "~8.18.3" + } + }, + "node_modules/socket.io-adapter/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/socket.io-adapter/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/socket.io-adapter/node_modules/ws": { + "version": "8.18.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.3.tgz", + "integrity": "sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg==", + "dev": true, + "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/socket.io-client": { + "version": "4.8.3", + "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-4.8.3.tgz", + "integrity": "sha512-uP0bpjWrjQmUt5DTHq9RuoCBdFJF10cdX9X+a368j/Ft0wmaVgxlrjvK3kjvgCODOMMOz9lcaRzxmso0bTWZ/g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@socket.io/component-emitter": "~3.1.0", + "debug": "~4.4.1", + "engine.io-client": "~6.6.1", + "socket.io-parser": "~4.2.4" + }, + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/socket.io-client/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/socket.io-client/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/socket.io-parser": { + "version": "4.2.6", + "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-4.2.6.tgz", + "integrity": "sha512-asJqbVBDsBCJx0pTqw3WfesSY0iRX+2xzWEWzrpcH7L6fLzrhyF8WPI8UaeM4YCuDfpwA/cgsdugMsmtz8EJeg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@socket.io/component-emitter": "~3.1.0", + "debug": "~4.4.1" + }, + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/socket.io-parser/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/socket.io-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==", + "dev": true, + "license": "MIT" + }, + "node_modules/socket.io/node_modules/accepts": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", + "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-types": "~2.1.34", + "negotiator": "0.6.3" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/socket.io/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/socket.io/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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/socket.io/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==", + "dev": true, + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/socket.io/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/socket.io/node_modules/negotiator": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", + "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/socks": { + "version": "2.8.9", + "resolved": "https://registry.npmjs.org/socks/-/socks-2.8.9.tgz", + "integrity": "sha512-LJhUYUvItdQ0LkJTmPeaEObWXAqFyfmP85x0tch/ez9cahmhlBBLbIqDFnvBnUJGagb0JbIQrkBs1wJ+yRYpEw==", + "dev": true, + "license": "MIT", + "dependencies": { + "ip-address": "^10.1.1", + "smart-buffer": "^4.2.0" + }, + "engines": { + "node": ">= 10.0.0", + "npm": ">= 3.0.0" + } + }, + "node_modules/socks-proxy-agent": { + "version": "10.0.0", + "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-10.0.0.tgz", + "integrity": "sha512-pyp2YR3mNxAMu0mGLtzs4g7O3uT4/9sQOLAKcViAkaS9fJWkud7nmaf6ZREFqQEi24IPkBcjfHjXhPTUWjo3uA==", + "dev": true, + "license": "MIT", + "dependencies": { + "agent-base": "9.0.0", + "debug": "^4.3.4", + "socks": "^2.8.3" + }, + "engines": { + "node": ">= 20" + } + }, + "node_modules/socks-proxy-agent/node_modules/agent-base": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-9.0.0.tgz", + "integrity": "sha512-TQf59BsZnytt8GdJKLPfUZ54g/iaUL2OWDSFCCvMOhsHduDQxO8xC4PNeyIkVcA5KwL2phPSv0douC0fgWzmnA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 20" + } + }, + "node_modules/socks-proxy-agent/node_modules/debug": { + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", + "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "dev": true, + "license": "MIT", + "dependencies": { + "ms": "^2.1.3" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/socks-proxy-agent/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/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "license": "BSD-3-Clause", + "optional": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/sparse-bitfield": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/sparse-bitfield/-/sparse-bitfield-3.0.3.tgz", + "integrity": "sha512-kvzhi7vqKTfkh0PZU+2D2PIllw2ymqJKujUcyPMd9Y75Nv4nPbGJZXNhxsgdQab2BmlDct1YnfQCguEvHr7VsQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "memory-pager": "^1.0.2" + } + }, + "node_modules/split2": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", + "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", + "dev": true, + "license": "ISC", + "optional": true, + "engines": { + "node": ">= 10.x" + } + }, + "node_modules/sprintf-js": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.1.3.tgz", + "integrity": "sha512-Oo+0REFV59/rz3gfJNKQiBlwfHaSESl1pcGyABQsnnIfWOFt6JNj5gCog2U6MLZ//IGYD+nA8nI+mTShREReaA==", + "dev": true, + "license": "BSD-3-Clause", + "optional": true + }, + "node_modules/stack-trace": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/stack-trace/-/stack-trace-0.0.10.tgz", + "integrity": "sha512-KGzahc7puUKkzyMt+IqAep+TVNbKP+k2Lmwhub39m1AsTSkaDutx56aDCo+HLDzf/D26BIHTJWNiTG1KAJiQCg==", + "dev": true, + "license": "MIT", + "engines": { + "node": "*" + } + }, + "node_modules/statuses": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.2.tgz", + "integrity": "sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/stdin-discarder": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/stdin-discarder/-/stdin-discarder-0.3.2.tgz", + "integrity": "sha512-eCPu1qRxPVkl5605OTWF8Wz40b4Mf45NY5LQmVPQ599knfs5QhASUm9GbJ5BDMDOXgrnh0wyEdvzmL//YMlw0A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/stopwords-iso": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/stopwords-iso/-/stopwords-iso-1.1.0.tgz", + "integrity": "sha512-I6GPS/E0zyieHehMRPQcqkiBMJKGgLta+1hREixhoLPqEA0AlVFiC43dl8uPpmkkeRdDMzYRWFWk5/l9x7nmNg==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.10.0" + } + }, + "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", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", + "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", + "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", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", + "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", + "dev": true, + "license": "MIT", + "dependencies": { + "ansi-regex": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-final-newline": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-4.0.0.tgz", + "integrity": "sha512-aulFJcD6YK8V1G7iRB5tigAP4TsHBZZrOV8pjV++zdUwmeV8uzbY7yn6h9MswN62adStNZFuCIx4haBnRuMDaw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/strnum": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/strnum/-/strnum-2.3.0.tgz", + "integrity": "sha512-ums3KNd42PGyx5xaoVTO1mjU1bH3NpY4vsrVlnv9PNGqQj8wd7rJ6nEypLrJ7z5vxK5RP0yMLo6J/Gsm62DI5Q==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/NaturalIntelligence" + } + ], + "license": "MIT" + }, + "node_modules/strtok3": { + "version": "10.3.5", + "resolved": "https://registry.npmjs.org/strtok3/-/strtok3-10.3.5.tgz", + "integrity": "sha512-ki4hZQfh5rX0QDLLkOCj+h+CVNkqmp/CMf8v8kZpkNVK6jGQooMytqzLZYUVYIZcFZ6yDB70EfD8POcFXiF5oA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@tokenizer/token": "^0.3.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Borewit" + } + }, + "node_modules/sylvester": { + "version": "0.0.21", + "resolved": "https://registry.npmjs.org/sylvester/-/sylvester-0.0.21.tgz", + "integrity": "sha512-yUT0ukFkFEt4nb+NY+n2ag51aS/u9UHXoZw+A4jgD77/jzZsBoSDHuqysrVCBC4CYR4TYvUJq54ONpXgDBH8tA==", + "dev": true, + "optional": true, + "engines": { + "node": ">=0.2.6" + } + }, + "node_modules/tar-fs": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.4.tgz", + "integrity": "sha512-mDAjwmZdh7LTT6pNleZ05Yt65HC3E+NiQzl672vQG38jIrehtJk/J3mNwIg+vShQPcLF/LV7CMnDW6vjj6sfYQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "chownr": "^1.1.1", + "mkdirp-classic": "^0.5.2", + "pump": "^3.0.0", + "tar-stream": "^2.1.4" + } + }, + "node_modules/tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/text-extensions": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/text-extensions/-/text-extensions-3.1.0.tgz", + "integrity": "sha512-anOjtXr8OT5w4vc/2mP4AYTCE0GWc/21icGmaHtBHnI7pN7o01a/oqG9m06/rGzoAsDm/WNzggBpqptuCmRlZQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18.20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/text-hex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/text-hex/-/text-hex-1.0.0.tgz", + "integrity": "sha512-uuVGNWzgJ4yhRaNSiubPY7OjISw4sw4E5Uv0wbjp+OzcbmVU/rsT8ujgcXJhn9ypzsgr5vlzpPqP+MBBKcGvbg==", + "dev": true, + "license": "MIT" + }, + "node_modules/textextensions": { + "version": "6.11.0", + "resolved": "https://registry.npmjs.org/textextensions/-/textextensions-6.11.0.tgz", + "integrity": "sha512-tXJwSr9355kFJI3lbCkPpUH5cP8/M0GGy2xLO34aZCjMXBaK3SoPnZwr/oWmo1FdCnELcs4npdCIOFtq9W3ruQ==", + "dev": true, + "license": "Artistic-2.0", + "dependencies": { + "editions": "^6.21.0" + }, + "engines": { + "node": ">=4" + }, + "funding": { + "url": "https://bevry.me/fund" + } + }, + "node_modules/tiny-emitter": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/tiny-emitter/-/tiny-emitter-2.1.0.tgz", + "integrity": "sha512-NB6Dk1A9xgQPMoGqC5CVXn123gWyte215ONT5Pp5a0yt4nlEoO1ZWeCwpncaekPHXO60i47ihFnZPiRPjRMq4Q==", + "dev": true, + "license": "MIT" + }, + "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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.6" + } + }, + "node_modules/token-types": { + "version": "6.1.2", + "resolved": "https://registry.npmjs.org/token-types/-/token-types-6.1.2.tgz", + "integrity": "sha512-dRXchy+C0IgK8WPC6xvCHFRIWYUbqqdEIKPaKo/AcTUNzwLTK6AH7RjdLWsEZcAN/TBdtfUw3PYEgPr5VPr6ww==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@borewit/text-codec": "^0.2.1", + "@tokenizer/token": "^0.3.0", + "ieee754": "^1.2.1" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Borewit" + } + }, + "node_modules/tough-cookie": { + "version": "4.1.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-4.1.3.tgz", + "integrity": "sha512-aX/y5pVRkfRnfmuX+OdbSdXvPe6ieKX/G2s7e98f4poJHnqH3281gDPm/metm6E/WRamfx7WC4HUqkWHfQHprw==", + "dev": true, + "license": "BSD-3-Clause", + "optional": true, + "dependencies": { + "psl": "^1.1.33", + "punycode": "^2.1.1", + "universalify": "^0.2.0", + "url-parse": "^1.5.3" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/triple-beam": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/triple-beam/-/triple-beam-1.4.1.tgz", + "integrity": "sha512-aZbgViZrg1QNcG+LULa7nhZpJTZSLm/mXnHXnbAbjmN5aSa0y7V+wvv6+4WaBtpISJzThKy+PIPxc1Nq1EJ9mg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/ts-algebra": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ts-algebra/-/ts-algebra-2.0.0.tgz", + "integrity": "sha512-FPAhNPFMrkwz76P7cdjdmiShwMynZYN6SgOujD1urY4oNm80Ou9oMdmbR45LotcKOXoy7wSmHkRFE6Mxbrhefw==", + "dev": true, + "license": "MIT" + }, + "node_modules/tslib": { + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", + "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", + "dev": true, + "license": "0BSD" + }, + "node_modules/tsx": { + "version": "4.22.3", + "resolved": "https://registry.npmjs.org/tsx/-/tsx-4.22.3.tgz", + "integrity": "sha512-mdoNxBC/cSQObGGVQ5Bpn5i+yv7j68gk3Nfm3wFjcJg3Z0Mix9jzAFfP12prmm5eVGmDKtp0yyArrs0Q+8gZHg==", + "dev": true, + "license": "MIT", + "dependencies": { + "esbuild": "~0.28.0" + }, + "bin": { + "tsx": "dist/cli.mjs" + }, + "engines": { + "node": ">=18.0.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.3" + } + }, + "node_modules/tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha512-McnNiV1l8RYeY8tBgEpuodCC1mLUdbSN+CYBL7kJsJNInOP8UjDDEwdk6Mw60vdLLrr5NHKZhMAOSrR2NZuQ+w==", + "dev": true, + "license": "Apache-2.0", + "dependencies": { + "safe-buffer": "^5.0.1" + }, + "engines": { + "node": "*" + } + }, + "node_modules/type-fest": { + "version": "0.13.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.13.1.tgz", + "integrity": "sha512-34R7HTnG0XIJcBSn5XhDd7nNFPRcXYRZrBB2O2jdKqYODldSzBAqzsWoZYYvduky73toYS/ESqxPvkDf/F0XMg==", + "dev": true, + "license": "(MIT OR CC0-1.0)", + "optional": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/type-is": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-2.1.0.tgz", + "integrity": "sha512-faYHw0anBbc/kWF3zFTEnxSFOAGUX9GFbOBthvDdLsIlEoWOFOtS0zgCiQYwIskL9iGXZL3kAXD8OoZ4GmMATA==", + "dev": true, + "license": "MIT", + "dependencies": { + "content-type": "^2.0.0", + "media-typer": "^1.1.0", + "mime-types": "^3.0.0" + }, + "engines": { + "node": ">= 18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/type-is/node_modules/content-type": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-2.0.0.tgz", + "integrity": "sha512-j/O/d7GcZCyNl7/hwZAb606rzqkyvaDctLmckbxLzHvFBzTJHuGEdodATcP3yIRoDrLHkIATJuvzbFlp/ki2cQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" + } + }, + "node_modules/typed-function": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/typed-function/-/typed-function-4.2.2.tgz", + "integrity": "sha512-VwaXim9Gp1bngi/q3do8hgttYn2uC3MoT/gfuMWylnj1IeZBUAyPddHZlo1K05BDoj8DYPpMdiHqH1dDYdJf2A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 18" + } + }, + "node_modules/uint8array-extras": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/uint8array-extras/-/uint8array-extras-1.5.0.tgz", + "integrity": "sha512-rvKSBiC5zqCCiDZ9kAOszZcDvdAHwwIKJG33Ykj43OKcWsnmcBRL09YTU4nOeHZ8Y2a7l1MgTd08SBe9A8Qj6A==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/underscore": { + "version": "1.13.8", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.8.tgz", + "integrity": "sha512-DXtD3ZtEQzc7M8m4cXotyHR+FAS18C64asBYY5vqZexfYryNNnDc02W4hKg3rdQuqOYas1jkseX0+nZXjTXnvQ==", + "dev": true, + "license": "MIT", + "optional": true + }, + "node_modules/undici": { + "version": "7.25.0", + "resolved": "https://registry.npmjs.org/undici/-/undici-7.25.0.tgz", + "integrity": "sha512-xXnp4kTyor2Zq+J1FfPI6Eq3ew5h6Vl0F/8d9XU5zZQf1tX9s2Su1/3PiMmUANFULpmksxkClamIZcaUqryHsQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=20.18.1" + } + }, + "node_modules/undici-types": { + "version": "7.24.6", + "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.24.6.tgz", + "integrity": "sha512-WRNW+sJgj5OBN4/0JpHFqtqzhpbnV0GuB+OozA9gCL7a993SmU+1JBZCzLNxYsbMfIeDL+lTsphD5jN5N+n0zg==", + "dev": true, + "license": "MIT" + }, + "node_modules/unicorn-magic": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/unicorn-magic/-/unicorn-magic-0.3.0.tgz", + "integrity": "sha512-+QBBXBCvifc56fsbuxZQ6Sic3wqqc3WWaqxs58gvJrcOuN83HGTCwz3oS5phzU9LthRNE9VrJCFCLUgHeeFnfA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/universalify": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.2.0.tgz", + "integrity": "sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">= 4.0.0" + } + }, + "node_modules/unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/unzipper": { + "version": "0.12.3", + "resolved": "https://registry.npmjs.org/unzipper/-/unzipper-0.12.3.tgz", + "integrity": "sha512-PZ8hTS+AqcGxsaQntl3IRBw65QrBI6lxzqDEL7IAo/XCEqRTKGfOX56Vea5TH9SZczRVxuzk1re04z/YjuYCJA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "bluebird": "~3.7.2", + "duplexer2": "~0.1.4", + "fs-extra": "^11.2.0", + "graceful-fs": "^4.2.2", + "node-int64": "^0.4.0" + } + }, + "node_modules/url-parse": { + "version": "1.5.10", + "resolved": "https://registry.npmjs.org/url-parse/-/url-parse-1.5.10.tgz", + "integrity": "sha512-WypcfiRhfeUP9vvF0j6rw0J3hrWrw6iZv3+22h6iRMJ/8z1Tj6XfLP4DsUix5MhMPnXpiHDoKyoZ/bdCkwBCiQ==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "querystringify": "^2.1.1", + "requires-port": "^1.0.0" + } + }, + "node_modules/url-template": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/url-template/-/url-template-2.0.8.tgz", + "integrity": "sha512-XdVKMF4SJ0nP/O7XIPB0JwAEuT9lDIYnNsK8yGVe43y0AWoKeJNdv3ZNWh7ksJ6KqQFjOO6ox/VEitLnaVNufw==", + "dev": true, + "license": "BSD" + }, + "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": "13.0.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-13.0.2.tgz", + "integrity": "sha512-vzi9uRZ926x4XV73S/4qQaTwPXM2JBj6/6lI/byHH1jOpCzb0zDbfytgA9LcN/hzb2l7WQSQnxITOVx5un/wGw==", + "dev": true, + "funding": [ + "https://github.com/sponsors/broofa", + "https://github.com/sponsors/ctavan" + ], + "license": "MIT", + "optional": true, + "bin": { + "uuid": "dist-node/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==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/version-range": { + "version": "4.15.0", + "resolved": "https://registry.npmjs.org/version-range/-/version-range-4.15.0.tgz", + "integrity": "sha512-Ck0EJbAGxHwprkzFO966t4/5QkRuzh+/I1RxhLgUKKwEn+Cd8NwM60mE3AqBZg5gYODoXW0EFsQvbZjRlvdqbg==", + "dev": true, + "license": "Artistic-2.0", + "engines": { + "node": ">=4" + }, + "funding": { + "url": "https://bevry.me/fund" + } + }, + "node_modules/web-streams-polyfill": { + "version": "3.3.3", + "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.3.3.tgz", + "integrity": "sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 8" + } + }, + "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==", + "dev": true, + "license": "BSD-2-Clause", + "optional": true + }, + "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==", + "dev": true, + "license": "MIT", + "optional": true, + "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==", + "dev": true, + "license": "ISC", + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "node-which": "bin/node-which" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/winston": { + "version": "3.19.0", + "resolved": "https://registry.npmjs.org/winston/-/winston-3.19.0.tgz", + "integrity": "sha512-LZNJgPzfKR+/J3cHkxcpHKpKKvGfDZVPS4hfJCc4cCG0CgYzvlD6yE/S3CIL/Yt91ak327YCpiF/0MyeZHEHKA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@colors/colors": "^1.6.0", + "@dabh/diagnostics": "^2.0.8", + "async": "^3.2.3", + "is-stream": "^2.0.0", + "logform": "^2.7.0", + "one-time": "^1.0.0", + "readable-stream": "^3.4.0", + "safe-stable-stringify": "^2.3.1", + "stack-trace": "0.0.x", + "triple-beam": "^1.3.0", + "winston-transport": "^4.9.0" + }, + "engines": { + "node": ">= 12.0.0" + } + }, + "node_modules/winston-transport": { + "version": "4.9.0", + "resolved": "https://registry.npmjs.org/winston-transport/-/winston-transport-4.9.0.tgz", + "integrity": "sha512-8drMJ4rkgaPo1Me4zD/3WLfI/zPdA9o2IipKODunnGDcuqbHwjsbB79ylv04LCGGzU0xQ6vTznOMpQGaLhhm6A==", + "dev": true, + "license": "MIT", + "dependencies": { + "logform": "^2.7.0", + "readable-stream": "^3.6.2", + "triple-beam": "^1.3.0" + }, + "engines": { + "node": ">= 12.0.0" + } + }, + "node_modules/winston/node_modules/@colors/colors": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.6.0.tgz", + "integrity": "sha512-Ir+AOibqzrIsL6ajt3Rz3LskB7OiMVHqltZmspbW/TJuTVuyOMirVqAkjfY6JISiLHgyNqicAC8AyHHGzNd/dA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/wordnet-db": { + "version": "3.1.14", + "resolved": "https://registry.npmjs.org/wordnet-db/-/wordnet-db-3.1.14.tgz", + "integrity": "sha512-zVyFsvE+mq9MCmwXUWHIcpfbrHHClZWZiVOzKSxNJruIcFn2RbY55zkhiAMMxM8zCVSmtNiViq8FsAZSFpMYag==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.6.0" + } + }, + "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==", + "dev": true, + "license": "ISC" + }, + "node_modules/ws": { + "version": "8.20.1", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.20.1.tgz", + "integrity": "sha512-It4dO0K5v//JtTXuPkfEOaI3uUN87iYPnqo/ZzqCoG3g8uhA66QUMs/SrM0YK7/NAu+r4LMh/9dq2A7k+rHs+w==", + "dev": true, + "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/wsl-utils": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/wsl-utils/-/wsl-utils-0.1.0.tgz", + "integrity": "sha512-h3Fbisa2nKGPxCpm89Hk33lBLsnaGBvctQopaBSOW/uIs6FTe1ATyAnKFJrzVs9vpGdsTe73WF3V4lIsk4Gacw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "is-wsl": "^3.1.0" + }, + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/xml-naming": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/xml-naming/-/xml-naming-0.1.0.tgz", + "integrity": "sha512-k8KO9hrMyNk6tUWqUfkTEZbezRRpONVOzUTnc97VnCvyj6Tf9lyUR9EDAIeiVLv56jsMcoXEwjW8Kv5yPY52lw==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/NaturalIntelligence" + } + ], + "license": "MIT", + "engines": { + "node": ">=16.0.0" + } + }, + "node_modules/xmlhttprequest-ssl": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/xmlhttprequest-ssl/-/xmlhttprequest-ssl-2.1.2.tgz", + "integrity": "sha512-TEU+nJVUUnA4CYJFLvK5X9AOeH4KvDvhIfm0vV1GaQRtchnG0hgK5p8hw/xjv8cunWYCsiPCSDzObPyhEwq3KQ==", + "dev": true, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "dev": true, + "license": "MIT", + "optional": true, + "engines": { + "node": ">=0.4" + } + }, + "node_modules/yaml": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.9.0.tgz", + "integrity": "sha512-2AvhNX3mb8zd6Zy7INTtSpl1F15HW6Wnqj0srWlkKLcpYl/gMIMJiyuGq2KeI2YFxUPjdlB+3Lc10seMLtL4cA==", + "dev": true, + "license": "ISC", + "optional": true, + "bin": { + "yaml": "bin.mjs" + }, + "engines": { + "node": ">= 14.6" + }, + "funding": { + "url": "https://github.com/sponsors/eemeli" + } + }, + "node_modules/yoctocolors": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/yoctocolors/-/yoctocolors-2.1.2.tgz", + "integrity": "sha512-CzhO+pFNo8ajLM2d2IW/R93ipy99LWjtwblvC1RsoSUMZgyLbYFr221TnSNT7GjGdYui6P459mw9JH/g/zW2ug==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=18" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/zod": { + "version": "3.25.76", + "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.76.tgz", + "integrity": "sha512-gzUt/qt81nXsFGKIFcC3YnfEAx5NkunCfnDlvuBSSFS02bcXu4Lmea0AFIUwbLWxWPx3d9p8S5QoaujKcNQxcQ==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/colinhacks" + } + }, + "node_modules/zod-to-json-schema": { + "version": "3.25.2", + "resolved": "https://registry.npmjs.org/zod-to-json-schema/-/zod-to-json-schema-3.25.2.tgz", + "integrity": "sha512-O/PgfnpT1xKSDeQYSCfRI5Gy3hPf91mKVDuYLUHZJMiDFptvP41MSnWofm8dnCm0256ZNfZIM7DSzuSMAFnjHA==", + "dev": true, + "license": "ISC", + "peerDependencies": { + "zod": "^3.25.28 || ^4" + } + } + } +} diff --git a/evals/package.json b/evals/package.json new file mode 100644 index 0000000..b2e2db2 --- /dev/null +++ b/evals/package.json @@ -0,0 +1,34 @@ +{ + "name": "@launchdarkly/skill-evals", + "private": true, + "type": "commonjs", + "scripts": { + "eval:aiconfig-create": "promptfoo eval -c shared/defaults.yaml -c aiconfig-create/promptfooconfig.yaml --env-file .env --no-cache -o aiconfig-create/results.json", + "eval:aiconfig-create:single": "promptfoo eval -c shared/defaults.yaml -c aiconfig-create/promptfooconfig.yaml --env-file .env --no-cache --filter-first-n 1", + "eval:aiconfig-update": "promptfoo eval -c shared/defaults.yaml -c aiconfig-update/promptfooconfig.yaml --env-file .env --no-cache -o aiconfig-update/results.json", + "eval:aiconfig-update:single": "promptfoo eval -c shared/defaults.yaml -c aiconfig-update/promptfooconfig.yaml --env-file .env --no-cache --filter-first-n 1", + "eval:aiconfig-tools": "promptfoo eval -c shared/defaults.yaml -c aiconfig-tools/promptfooconfig.yaml --env-file .env --no-cache -o aiconfig-tools/results.json", + "eval:aiconfig-tools:single": "promptfoo eval -c shared/defaults.yaml -c aiconfig-tools/promptfooconfig.yaml --env-file .env --no-cache --filter-first-n 1", + "eval:aiconfig-variations": "promptfoo eval -c shared/defaults.yaml -c aiconfig-variations/promptfooconfig.yaml --env-file .env --no-cache -o aiconfig-variations/results.json", + "eval:aiconfig-variations:single": "promptfoo eval -c shared/defaults.yaml -c aiconfig-variations/promptfooconfig.yaml --env-file .env --no-cache --filter-first-n 1", + "eval:flag-create": "promptfoo eval -c shared/defaults.yaml -c launchdarkly-flag-create/promptfooconfig.yaml --env-file .env --no-cache -o launchdarkly-flag-create/results.json", + "eval:flag-create:single": "promptfoo eval -c shared/defaults.yaml -c launchdarkly-flag-create/promptfooconfig.yaml --env-file .env --no-cache --filter-first-n 1", + "eval:all": "node scripts/aggregate.js --run", + "eval:aggregate": "node scripts/aggregate.js", + "eval:diff": "node scripts/diff-changed-skills.js", + "eval:badges": "node scripts/render-badges.js", + "test": "node --test tests/*.test.js", + "eval:view": "promptfoo view", + "eval:haiku": "node scripts/run-models.js --model=haiku", + "eval:sonnet": "node scripts/run-models.js --model=sonnet", + "eval:opus": "node scripts/run-models.js --model=opus", + "eval:matrix": "node scripts/run-models.js --models=haiku,sonnet,opus" + }, + "devDependencies": { + "promptfoo": "^0.121.0", + "zod": "^3.22.4" + }, + "dependencies": { + "@anthropic-ai/claude-agent-sdk": "^0.3.144" + } +} diff --git a/evals/providers/_jsonschema-to-zod.js b/evals/providers/_jsonschema-to-zod.js new file mode 100644 index 0000000..e289b03 --- /dev/null +++ b/evals/providers/_jsonschema-to-zod.js @@ -0,0 +1,84 @@ +/** + * Tiny JSON Schema -> Zod converter, scoped to the subset used by + * tools/definitions.json: type, properties, required, items, enum, + * description. Built so that the SDK provider can register the same tool + * surface as the legacy provider without hand-writing Zod schemas for every + * LaunchDarkly MCP tool. + * + * `inputSchemaToZodShape()` returns a raw Zod shape (object whose values are + * Zod schemas) so callers can spread it into the SDK's `tool()` helper. + * Anything unrecognised falls through to `z.any()`. + */ + +const { z } = require("zod"); + +function fieldToZod(field) { + if (!field || typeof field !== "object") return z.any(); + + if (Array.isArray(field.enum) && field.enum.length > 0) { + const values = field.enum.filter((v) => typeof v === "string"); + if (values.length === field.enum.length) { + let s = z.enum(values); + if (field.description) s = s.describe(field.description); + return s; + } + } + + let base; + switch (field.type) { + case "string": + base = z.string(); + break; + case "integer": + base = z.number().int(); + break; + case "number": + base = z.number(); + break; + case "boolean": + base = z.boolean(); + break; + case "array": + base = z.array(field.items ? fieldToZod(field.items) : z.any()); + break; + case "object": { + const shape = {}; + const required = new Set( + Array.isArray(field.required) ? field.required : [], + ); + for (const [k, v] of Object.entries(field.properties || {})) { + const inner = fieldToZod(v); + shape[k] = required.has(k) ? inner : inner.optional(); + } + base = z.object(shape).passthrough(); + break; + } + default: + base = z.any(); + } + + if (field.description) base = base.describe(field.description); + return base; +} + +/** + * Convert a JSON Schema describing a tool's `input_schema` into a Zod raw + * shape ready to spread into the SDK's `tool(...)` helper. Required fields + * stay required; everything else becomes optional. + */ +function inputSchemaToZodShape(schema) { + if (!schema || schema.type !== "object" || !schema.properties) { + return {}; + } + const required = new Set( + Array.isArray(schema.required) ? schema.required : [], + ); + const shape = {}; + for (const [k, v] of Object.entries(schema.properties)) { + const inner = fieldToZod(v); + shape[k] = required.has(k) ? inner : inner.optional(); + } + return shape; +} + +module.exports = { inputSchemaToZodShape, fieldToZod }; diff --git a/evals/providers/_mock.js b/evals/providers/_mock.js new file mode 100644 index 0000000..9eef7ce --- /dev/null +++ b/evals/providers/_mock.js @@ -0,0 +1,304 @@ +/** + * Mock-response renderer used by the provider to fill in canned tool + * responses from mocks/tool-responses.json before handing them back to the + * agent through the in-process MCP server. + * + * Two layers: + * + * 1. Stateless template rendering walks the parsed mock template object, + * substituting `{{placeholder}}` tokens inside string leaves with values + * from the tool input. Quote/backslash chars in inputs are safe because + * substitution only touches strings. + * + * 2. Stateful overlay keeps an in-memory map of configs per `callApi` + * invocation. Write tools (create/setup/update) record into state; read + * tools (get-ai-config, get-ai-config-health) build their response from + * state when one exists, falling back to the template otherwise. This + * prevents the agent from believing its own writes failed when the static + * template returns generic placeholder data. + */ + +const PLACEHOLDER_RE = /\{\{(\w+)\}\}/g; + +function buildReplacements(input) { + const safe = input || {}; + return { + flagKey: safe.flagKey || safe.key || "unknown-flag", + flagName: safe.flagName || safe.name || "Unknown Flag", + configKey: safe.configKey || safe.key || "unknown-config", + configName: safe.configName || safe.name || "Unknown Config", + variationKey: + safe.variationKey || safe.sourceVariationKey || safe.key || "default", + variationName: safe.variationName || safe.name || "Default", + toolKey: safe.toolKey || safe.key || "unknown-tool", + modelConfigKey: safe.modelConfigKey || "OpenAI.gpt-4o", + modelName: safe.modelName || "gpt-4o", + mode: safe.mode || "completion", + toolDescription: safe.description || "A tool", + projectKey: safe.projectKey || "my-project", + }; +} + +function renderString(value, replacements) { + return value.replace(PLACEHOLDER_RE, (match, key) => + Object.prototype.hasOwnProperty.call(replacements, key) + ? String(replacements[key]) + : match, + ); +} + +function walk(node, replacements) { + if (typeof node === "string") return renderString(node, replacements); + if (Array.isArray(node)) return node.map((item) => walk(item, replacements)); + if (node && typeof node === "object") { + const out = {}; + for (const k of Object.keys(node)) out[k] = walk(node[k], replacements); + return out; + } + return node; +} + +// --------------------------------------------------------------------------- +// Stateful overlay +// --------------------------------------------------------------------------- + +const SEED_CONFIGS = { + "support-chatbot": { + key: "support-chatbot", + name: "Support Chatbot", + mode: "agent", + description: "AI-powered support agent for customer tickets", + tags: ["support", "production"], + archived: false, + variations: [ + { + key: "default", + name: "Default", + modelConfigKey: "OpenAI.gpt-4o", + modelName: "gpt-4o", + instructions: + "You are a helpful assistant that answers questions concisely.", + parameters: { temperature: 0.7, max_tokens: 2048 }, + tools: [], + status: "active", + }, + ], + }, + "code-reviewer": { + key: "code-reviewer", + name: "Code Review Assistant", + mode: "completion", + description: "Automated code review assistant for pull requests", + tags: ["engineering"], + archived: false, + variations: [ + { + key: "default", + name: "Default", + modelConfigKey: "Anthropic.claude-sonnet-4-5", + modelName: "claude-sonnet-4-5", + messages: [ + { + role: "system", + content: "You review code for bugs, style, and security issues.", + }, + ], + parameters: { temperature: 0.3, max_tokens: 4096 }, + tools: [], + status: "active", + }, + ], + }, +}; + +/** + * Create fresh in-memory state for a single callApi invocation. Pass the + * returned object to every `renderMockResponse` call so stateful tools + * (create/update/get) share the same map. + */ +function createMockState() { + return { + configs: {}, // configKey -> config object + flags: {}, // flagKey -> flag object + }; +} + +/** + * Render a mock response for `toolName` given `input` (raw tool arguments). + * `state` is the per-invocation map from `createMockState()`. + * `templates` is the full parsed mocks/tool-responses.json. + */ +function renderMockResponse(template, input, toolName, state) { + const replacements = buildReplacements(input); + + // ---------- stateful reads ---------- + if (toolName === "get-ai-config") { + const key = input.configKey || input.key; + if (key) { + if (!state.configs[key] && SEED_CONFIGS[key]) { + state.configs[key] = JSON.parse(JSON.stringify(SEED_CONFIGS[key])); + } + if (state.configs[key]) return state.configs[key]; + } + } + + if (toolName === "get-ai-config-health") { + const key = input.configKey || input.key; + if (key && state.configs[key]) { + const cfg = state.configs[key]; + return { + key: cfg.key, + name: cfg.name, + mode: cfg.mode, + health: "healthy", + variationsCount: (cfg.variations || []).length, + issues: [], + variations: (cfg.variations || []).map((v) => ({ + key: v.key, + name: v.name, + hasModel: Boolean(v.modelConfigKey), + hasPrompts: Boolean(v.instructions || (v.messages && v.messages.length)), + toolsAttached: (v.tools || []).length, + })), + }; + } + } + + if (toolName === "list-ai-configs") { + // Merge state configs into the static template list for consistent reads. + // State entries always win over the static template for the same key, so + // an agent-created (or updated) config is reflected immediately. + const staticList = walk(template, replacements); + const stateConfigs = Object.values(state.configs).map((c) => ({ + key: c.key, + name: c.name, + mode: c.mode, + description: c.description || "", + tags: c.tags || [], + variationsCount: (c.variations || []).length, + archived: c.archived || false, + })); + if (stateConfigs.length > 0) { + const stateKeys = new Set(stateConfigs.map((c) => c.key)); + const staticOnly = (staticList.configs || []).filter((c) => !stateKeys.has(c.key)); + const merged = [...staticOnly, ...stateConfigs]; + return { + ...staticList, + configs: merged, + totalCount: merged.length, + }; + } + return staticList; + } + + if (toolName === "get-flag" || toolName === "get-feature-flag") { + const key = input.flagKey || input.key; + if (key && state.flags[key]) return state.flags[key]; + } + + // ---------- stateful writes ---------- + if (toolName === "setup-ai-config") { + const cfg = { + key: input.key, + name: input.name, + mode: input.mode, + description: input.description || "", + tags: input.tags || [], + archived: false, + variations: [ + { + key: input.variationKey || "default", + name: input.variationName || "Default", + modelConfigKey: input.modelConfigKey, + modelName: input.modelName, + ...(input.mode === "agent" + ? { instructions: input.instructions || "" } + : { messages: input.messages || [] }), + parameters: input.parameters || {}, + tools: input.tools || [], + status: "active", + }, + ], + }; + state.configs[input.key] = cfg; + return cfg; + } + + if (toolName === "create-ai-config") { + const cfg = { + key: input.key, + name: input.name, + mode: input.mode, + description: input.description || "", + tags: input.tags || [], + archived: false, + variations: [], + }; + state.configs[input.key] = cfg; + return cfg; + } + + if (toolName === "create-ai-config-variation") { + const cfg = state.configs[input.configKey]; + const variation = { + key: input.key, + name: input.name, + modelConfigKey: input.modelConfigKey, + modelName: input.modelName, + ...(input.instructions !== undefined + ? { instructions: input.instructions } + : {}), + ...(input.messages !== undefined ? { messages: input.messages } : {}), + parameters: input.parameters || {}, + tools: input.tools || [], + status: "active", + }; + if (cfg) { + cfg.variations = [...(cfg.variations || []), variation]; + } else { + // Parent config not in state — create a minimal stub so the variation + // is reachable via get-ai-config and list-ai-configs. The real API + // would 404 here; the mock recovers gracefully. + state.configs[input.configKey] = { + key: input.configKey, + name: input.configKey, + mode: "completion", + description: "", + tags: [], + archived: false, + variations: [variation], + }; + } + return { configKey: input.configKey, variation }; + } + + if (toolName === "update-ai-config-variation") { + const cfg = state.configs[input.configKey]; + if (cfg) { + const VARIATION_FIELDS = [ + "key", "name", "modelConfigKey", "modelName", + "instructions", "messages", "parameters", "tools", "status", + ]; + cfg.variations = (cfg.variations || []).map((v) => { + if (v.key !== input.variationKey) return v; + const patch = {}; + for (const k of VARIATION_FIELDS) { + if (input[k] !== undefined) patch[k] = input[k]; + } + return { ...v, ...patch }; + }); + } + return walk(template, replacements); + } + + if (toolName === "create-flag" || toolName === "create-feature-flag") { + const flag = walk(template, replacements); + state.flags[input.key || input.flagKey] = flag; + return flag; + } + + // Default: stateless template render + return walk(template, replacements); +} + +module.exports = { renderMockResponse, createMockState }; diff --git a/evals/providers/claude-skill-agent-sdk.js b/evals/providers/claude-skill-agent-sdk.js new file mode 100644 index 0000000..90d5205 --- /dev/null +++ b/evals/providers/claude-skill-agent-sdk.js @@ -0,0 +1,542 @@ +/** + * Promptfoo provider that runs a Claude agent via @anthropic-ai/claude-agent-sdk + * with the skill loaded the way a real Claude Code session would load it: by + * dropping it into `.claude/skills//SKILL.md` and letting the SDK + * preload it through the agent definition's `skills` field. + * + * Why use the SDK loader instead of packing SKILL.md as a system prompt: + * - Real Claude Code reads SKILL.md off disk, prepends its own system prompt, + * has its own tool naming, and triggers skills through agent definitions. + * Inlining SKILL.md as `system` would measure the skill in a clean room but + * bypass every one of those real-world mechanics. The SDK provider keeps the + * eval on the same path users hit when they install the skill. + * - Tool calls go through SDK MCP plumbing into an in-process mock server, so + * the trajectory output is { response, first_assistant_text, kickoff_text, + * assistant_turns, trajectory, tools_called, turn_count, terminated } and + * every existing assertion keeps working without modification. + * + * Promptfoo provider config (set via `config:` in promptfooconfig.yaml): + * skill_slug - REQUIRED. Folder name of the skill to load. + * Resolved under skills/// or + * skills// (whichever exists). + * allow_builtins - When true, expose Claude Code's built-in tools + * (Read/Grep/Glob/Bash/Edit/Write/...). Default false. + * expose_mcp_tools - Default true. Set false for skills that should never + * call LaunchDarkly MCP tools (routing/advisory skills). + * force_skill_invocation - Default false. When true, set initialPrompt to + * `/` to explicitly invoke the skill via + * slash command. Use for routing/advisory skills whose + * description-based activation is unreliable in eval. + * expose_ask_question - Default false. When true, expose a second in-process + * MCP server with an `ask-question` tool that records + * calls into the trajectory and returns a canned answer. + * + * Test-level vars: + * user_request - the user turn the agent sees + * codebase_context - optional snippets appended in a tag + * max_turns - per-test override, clamped to 1..30 (default 15) + * mock_ask_question_answers - optional array of `selected` arrays returned by + * successive `ask-question` calls + * mock_files - optional object mapping relative file paths to + * string content, written into the isolated cwd + * before the agent runs + * + * Environment variables: + * AGENT_MODEL - SUT model (default claude-sonnet-4-6). + * ANTHROPIC_API_KEY - Auth for the SDK's child Claude Code process. + * SKILL_EVAL_DEBUG=1 - Dump every SDK message to a temp file for inspection. + */ + +const fs = require("node:fs"); +const os = require("node:os"); +const path = require("node:path"); + +const { z } = require("zod"); + +const { renderMockResponse, createMockState } = require("./_mock"); +const { inputSchemaToZodShape } = require("./_jsonschema-to-zod"); + +const DEFAULT_MAX_TURNS = 15; +const MODEL = process.env.AGENT_MODEL || "claude-sonnet-4-6"; + +const REPO_ROOT = path.resolve(__dirname, "..", ".."); +const SKILLS_ROOT = path.join(REPO_ROOT, "skills"); + +const toolDefs = JSON.parse( + fs.readFileSync(path.join(__dirname, "../tools/definitions.json"), "utf-8"), +); + +const mockTemplates = JSON.parse( + fs.readFileSync(path.join(__dirname, "../mocks/tool-responses.json"), "utf-8"), +); + +/** + * Find the on-disk path to the skill folder named `slug`. Skills live under + * either `skills///SKILL.md` or `skills//SKILL.md` for + * uncategorised skills. Returns the absolute directory or null. + */ +function resolveSkillSource(slug) { + const direct = path.join(SKILLS_ROOT, slug); + if (fs.existsSync(path.join(direct, "SKILL.md"))) return direct; + + for (const category of fs.readdirSync(SKILLS_ROOT, { withFileTypes: true })) { + if (!category.isDirectory()) continue; + const candidate = path.join(SKILLS_ROOT, category.name, slug); + if (fs.existsSync(path.join(candidate, "SKILL.md"))) return candidate; + } + return null; +} + +/** + * Create a fully-isolated cwd for a single test invocation. Each callApi call + * gets its own temp directory so concurrent tests for the same skill slug + * cannot interfere with each other. + * + * /ld-eval--XXXXXX/ + * .claude/skills// -> symlink to skill source + * .isolated-claude-config/ + * .mcp.json (empty stub so SDK doesn't walk up to real .mcp.json) + */ +function createInvocationCwd(slug, skillSource) { + const cwd = fs.mkdtempSync(path.join(os.tmpdir(), `ld-eval-${slug}-`)); + + const skillsDir = path.join(cwd, ".claude", "skills"); + fs.mkdirSync(skillsDir, { recursive: true }); + fs.symlinkSync(skillSource, path.join(skillsDir, slug), "dir"); + + const isolatedConfig = path.join(cwd, ".isolated-claude-config"); + fs.mkdirSync(isolatedConfig, { recursive: true }); + + // Empty .mcp.json prevents the SDK from walking up and finding the repo-root + // .mcp.json, which points at the real hosted LaunchDarkly MCP server. + fs.writeFileSync( + path.join(cwd, ".mcp.json"), + JSON.stringify({ mcpServers: {} }, null, 2), + ); + + return { cwd, isolatedConfig }; +} + +function scaffoldMockFiles(cwd, mockFiles) { + if (!mockFiles || typeof mockFiles !== "object") return; + for (const [relPath, content] of Object.entries(mockFiles)) { + const absPath = path.join(cwd, relPath); + fs.mkdirSync(path.dirname(absPath), { recursive: true }); + fs.writeFileSync( + absPath, + typeof content === "string" ? content : JSON.stringify(content, null, 2), + "utf-8", + ); + } +} + +function clampMaxTurns(raw) { + const n = Number(raw); + if (!Number.isFinite(n) || n <= 0) return DEFAULT_MAX_TURNS; + return Math.min(30, Math.max(1, Math.floor(n))); +} + +function previewMock(mock) { + const s = JSON.stringify(mock); + return s.length > 200 ? s.slice(0, 200) + "..." : s; +} + +let sdkPromise = null; +function loadSdk() { + if (!sdkPromise) { + sdkPromise = import("@anthropic-ai/claude-agent-sdk"); + } + return sdkPromise; +} + +class ClaudeSkillAgentSdk { + constructor(options = {}) { + const config = options.config || {}; + if (!config.skill_slug) { + throw new Error( + "claude-skill-agent-sdk requires `config.skill_slug` (the folder name under skills/).", + ); + } + this.skillSlug = config.skill_slug; + this.allowBuiltins = Boolean(config.allow_builtins); + this.exposeMcpTools = config.expose_mcp_tools !== false; + this.forceSkillInvocation = Boolean(config.force_skill_invocation); + this.exposeAskQuestion = Boolean(config.expose_ask_question); + + const source = resolveSkillSource(this.skillSlug); + if (!source) { + throw new Error( + `claude-skill-agent-sdk: could not find SKILL.md for slug "${this.skillSlug}" under ${SKILLS_ROOT}/`, + ); + } + this.skillSource = source; + } + + id() { + return `claude-skill-agent-sdk:${this.skillSlug}`; + } + + async callApi(_prompt, context) { + const apiKey = process.env.ANTHROPIC_API_KEY; + if (!apiKey) { + return { error: "ANTHROPIC_API_KEY environment variable is not set" }; + } + + const userRequest = + context?.vars?.user_request || "Help me with LaunchDarkly"; + const codebaseContext = context?.vars?.codebase_context || ""; + const maxTurns = clampMaxTurns(context?.vars?.max_turns); + const askQuestionAnswers = Array.isArray( + context?.vars?.mock_ask_question_answers, + ) + ? context.vars.mock_ask_question_answers + : []; + const mockFiles = context?.vars?.mock_files || {}; + + let userMessage = userRequest; + if (codebaseContext) { + userMessage += `\n\n\n${codebaseContext}\n`; + } + + const { cwd, isolatedConfig } = createInvocationCwd( + this.skillSlug, + this.skillSource, + ); + scaffoldMockFiles(cwd, mockFiles); + + const sdk = await loadSdk(); + const { query, createSdkMcpServer, tool } = sdk; + + const trajectory = []; + let currentTurn = 0; + const mockState = createMockState(); + + const mcpTools = this.exposeMcpTools + ? toolDefs.map((def) => + tool( + def.name, + def.description, + inputSchemaToZodShape(def.input_schema), + async (args) => { + const template = mockTemplates[def.name]; + const mock = template + ? renderMockResponse(template, args, def.name, mockState) + : { error: `No mock configured for tool: ${def.name}` }; + + trajectory.push({ + tool: def.name, + arguments: args, + turn: currentTurn, + mock_response_preview: previewMock(mock), + }); + + return { + content: [{ type: "text", text: JSON.stringify(mock) }], + }; + }, + ), + ) + : []; + + const mockServer = this.exposeMcpTools + ? createSdkMcpServer({ name: "launchdarkly-mocks", tools: mcpTools }) + : null; + + let askQuestionCallCount = 0; + const askQuestionTools = this.exposeAskQuestion + ? [ + tool( + "ask-question", + "Ask the user a structured, blocking question with a list of options and wait for their selection.", + { + prompt: z.string().describe("The question to display to the user."), + options: z + .array( + z.object({ + id: z.string().describe("Stable identifier for the option."), + label: z.string().describe("Display text shown to the user."), + }), + ) + .min(2) + .describe("At least two options for the user to choose from."), + multi: z + .boolean() + .optional() + .describe("If true, the user can select multiple options."), + }, + async (args) => { + const idx = askQuestionCallCount++; + const override = askQuestionAnswers[idx]; + let selected; + if (Array.isArray(override) && override.length > 0) { + selected = override; + } else if (Array.isArray(args.options) && args.options.length > 0) { + selected = [args.options[0].id]; + } else { + selected = []; + } + const response = { selected }; + + trajectory.push({ + tool: "ask-question", + arguments: args, + turn: currentTurn, + mock_response_preview: previewMock(response), + }); + + return { + content: [{ type: "text", text: JSON.stringify(response) }], + }; + }, + ), + ] + : []; + + const harnessServer = this.exposeAskQuestion + ? createSdkMcpServer({ name: "harness-ux", tools: askQuestionTools }) + : null; + + const allowedMcpToolNames = []; + if (this.exposeMcpTools) { + for (const def of toolDefs) { + allowedMcpToolNames.push(`mcp__launchdarkly-mocks__${def.name}`); + } + } + if (this.exposeAskQuestion) { + allowedMcpToolNames.push("mcp__harness-ux__ask-question"); + } + + const agentTools = this.allowBuiltins ? undefined : allowedMcpToolNames; + + const harnessPrompt = [ + `You are running under an evaluation harness. The skill "${this.skillSlug}" is loaded into your context.`, + this.exposeMcpTools + ? "LaunchDarkly MCP tools are exposed as in-process mocks for this run; treat them as pre-authorized and call them when the skill directs you to." + : "No LaunchDarkly MCP tools are available for this run.", + this.exposeAskQuestion + ? "An `ask-question` tool is available for blocking decision points where the skill says to ask the user a structured question with options." + : null, + "If the user message includes a block, treat it as the authoritative description of the project. If you can also read files directly (Read/Glob/Bash), you may do so — the scaffolded files will match what the context describes.", + "Do not run package manager install commands (`npm install`, `npm ci`, `yarn add`, `pnpm add`, `pnpm install`). Simulate them as having completed successfully.", + "Do not start dev servers or run port checks. When the skill instructs you to start a server, skip the Bash call and immediately tell the user the server is running on its default port, then proceed to the next step.", + ] + .filter(Boolean) + .join("\n\n"); + + const mcpServersMap = {}; + if (mockServer) mcpServersMap["launchdarkly-mocks"] = mockServer; + if (harnessServer) mcpServersMap["harness-ux"] = harnessServer; + + const queryOptions = { + cwd, + settingSources: ["project"], + mcpServers: mcpServersMap, + model: MODEL, + maxTurns, + permissionMode: "bypassPermissions", + allowDangerouslySkipPermissions: true, + persistSession: false, + env: { + ...process.env, + CLAUDE_CONFIG_DIR: isolatedConfig, + }, + agent: "eval-agent", + agents: { + "eval-agent": { + description: "Evaluation harness agent for LaunchDarkly skills.", + prompt: harnessPrompt, + skills: [this.skillSlug], + ...(this.forceSkillInvocation + ? { initialPrompt: `/${this.skillSlug}` } + : {}), + ...(agentTools ? { tools: agentTools } : {}), + }, + }, + }; + + if (!this.allowBuiltins) { + queryOptions.tools = []; + } + + let finalText = ""; + let firstAssistantText = ""; + let lastAssistantText = ""; + const assistantTurns = []; + let kickoffText = ""; + let kickoffSealed = false; + let resultMessage = null; + let terminationReason = null; + const debug = process.env.SKILL_EVAL_DEBUG === "1"; + const allMessages = []; + + const isMaxTurnsMessage = (text) => + typeof text === "string" && /maximum number of turns/i.test(text); + + const extractAssistantText = (msg) => { + const content = + (msg && msg.message && msg.message.content) || + (msg && msg.content) || + null; + if (!Array.isArray(content)) return ""; + return content + .filter((b) => b && b.type === "text" && typeof b.text === "string") + .map((b) => b.text) + .join("\n") + .trim(); + }; + + // Internal orchestration tools that fire before the skill's instructed + // kickoff prose — not "agent took action" signals. + const KICKOFF_META_TOOLS = new Set(["Skill", "ToolSearch"]); + const hasKickoffSealingToolUse = (msg) => { + const content = + (msg && msg.message && msg.message.content) || + (msg && msg.content) || + null; + if (!Array.isArray(content)) return false; + return content.some( + (b) => + b && + b.type === "tool_use" && + !KICKOFF_META_TOOLS.has(b.name), + ); + }; + + try { + const q = query({ prompt: userMessage, options: queryOptions }); + for await (const msg of q) { + if (debug) allMessages.push(msg); + if (msg.type === "assistant") { + currentTurn += 1; + const text = extractAssistantText(msg); + if (text) { + if (!firstAssistantText) firstAssistantText = text; + lastAssistantText = text; + assistantTurns.push({ turn: currentTurn, text }); + if (!kickoffSealed) { + kickoffText += (kickoffText ? "\n\n" : "") + text; + } + } + if (!kickoffSealed && hasKickoffSealingToolUse(msg)) { + kickoffSealed = true; + } + + // Track builtin tool calls (Bash, Read, Write, Edit, Glob, Grep, + // etc.) in the trajectory. MCP calls are already recorded via their + // mock callbacks. Internal framework tools are excluded. + const msgContent = + (msg && msg.message && msg.message.content) || + (msg && msg.content) || + null; + if (Array.isArray(msgContent)) { + for (const block of msgContent) { + if ( + block && + block.type === "tool_use" && + typeof block.name === "string" && + !block.name.startsWith("mcp__") && + !KICKOFF_META_TOOLS.has(block.name) + ) { + trajectory.push({ + tool: block.name, + arguments: block.input || {}, + turn: currentTurn, + mock_response_preview: null, + }); + } + } + } + } else if (msg.type === "result") { + resultMessage = msg; + if (msg.subtype === "success" && typeof msg.result === "string") { + finalText = msg.result; + } else if (typeof msg.subtype === "string") { + terminationReason = msg.subtype; + } + } + } + } catch (err) { + const errMessage = err && err.message ? err.message : String(err); + if (isMaxTurnsMessage(errMessage)) { + terminationReason = terminationReason || "max_turns"; + } else { + return { error: `claude-skill-agent-sdk failed: ${errMessage}` }; + } + } finally { + try { + fs.rmSync(cwd, { recursive: true, force: true }); + } catch { + // ignore cleanup errors + } + } + + if (!finalText && lastAssistantText) { + finalText = lastAssistantText; + } + + if (debug) { + const debugDump = path.join( + os.tmpdir(), + `ld-eval-debug-${this.skillSlug}-${Date.now()}.json`, + ); + try { + fs.writeFileSync( + debugDump, + JSON.stringify(allMessages, (_k, v) => { + if (v && typeof v === "object" && typeof v.then === "function") + return "[Promise]"; + return v; + }, 2), + ); + console.error(`[skill-eval-debug] wrote ${debugDump}`); + } catch (e) { + console.error(`[skill-eval-debug] failed to write dump: ${e.message}`); + } + } + + const modelUsage = resultMessage?.modelUsage || {}; + let inputTokens = 0; + let outputTokens = 0; + for (const entry of Object.values(modelUsage)) { + inputTokens += + (entry?.inputTokens || 0) + + (entry?.cacheReadInputTokens || 0) + + (entry?.cacheCreationInputTokens || 0); + outputTokens += entry?.outputTokens || 0; + } + if (inputTokens === 0 && outputTokens === 0) { + inputTokens = resultMessage?.usage?.input_tokens || 0; + outputTokens = resultMessage?.usage?.output_tokens || 0; + } + + const cost = + typeof resultMessage?.total_cost_usd === "number" + ? resultMessage.total_cost_usd + : 0; + const turnCount = + typeof resultMessage?.num_turns === "number" + ? resultMessage.num_turns + : currentTurn; + + return { + output: JSON.stringify({ + response: finalText || "(no final response captured)", + first_assistant_text: firstAssistantText, + kickoff_text: kickoffText, + assistant_turns: assistantTurns, + trajectory, + tools_called: trajectory.map((t) => t.tool), + turn_count: turnCount, + terminated: terminationReason, + }), + tokenUsage: { + total: inputTokens + outputTokens, + prompt: inputTokens, + completion: outputTokens, + }, + cost, + }; + } +} + +module.exports = ClaudeSkillAgentSdk; diff --git a/evals/scripts/_manifest.js b/evals/scripts/_manifest.js new file mode 100644 index 0000000..358db9a --- /dev/null +++ b/evals/scripts/_manifest.js @@ -0,0 +1,59 @@ +/** + * Single source of truth mapping eval suites to the skills they cover. + * + * Used by: + * - scripts/aggregate.js (runs suites, emits eval-scores.json) + * - scripts/diff-changed-skills.js (decides which suites to re-run in CI) + * - scripts/render-badges.js (writes per-skill README badges) + * + * Field meanings: + * suite - directory under evals/ containing promptfooconfig.yaml + * skillKey - identifier used in eval-scores.json and README badges + * skillDir - path from repo root to the skill source directory + * readme - skill README path from repo root for badge rendering + */ +const SUITES = [ + { + suite: "aiconfig-create", + skillKey: "ai-configs/aiconfig-create", + skillDir: "skills/ai-configs/aiconfig-create", + readme: "skills/ai-configs/aiconfig-create/README.md", + }, + { + suite: "aiconfig-update", + skillKey: "ai-configs/aiconfig-update", + skillDir: "skills/ai-configs/aiconfig-update", + readme: "skills/ai-configs/aiconfig-update/README.md", + }, + { + suite: "aiconfig-tools", + skillKey: "ai-configs/aiconfig-tools", + skillDir: "skills/ai-configs/aiconfig-tools", + readme: "skills/ai-configs/aiconfig-tools/README.md", + }, + { + suite: "aiconfig-variations", + skillKey: "ai-configs/aiconfig-variations", + skillDir: "skills/ai-configs/aiconfig-variations", + readme: "skills/ai-configs/aiconfig-variations/README.md", + }, + { + suite: "launchdarkly-flag-create", + skillKey: "feature-flags/launchdarkly-flag-create", + skillDir: "skills/feature-flags/launchdarkly-flag-create", + readme: "skills/feature-flags/launchdarkly-flag-create/README.md", + }, +]; + +/** + * Paths that, when changed, invalidate every suite (force re-run all). + * Relative to repo root. + */ +const GLOBAL_TRIGGERS = [ + "evals/providers", + "evals/shared", + "evals/tools", + "evals/mocks", +]; + +module.exports = { SUITES, GLOBAL_TRIGGERS }; diff --git a/evals/scripts/_models.js b/evals/scripts/_models.js new file mode 100644 index 0000000..3396767 --- /dev/null +++ b/evals/scripts/_models.js @@ -0,0 +1,42 @@ +/** + * Agent (system-under-test) model aliases for the cross-model eval runner. + * + * Edit the right-hand side here when newer Anthropic models ship; nothing + * else in the repo needs to change. To run an unmapped model id directly: + * + * node scripts/run-models.js --model=claude-something-newer-2026 + * + * These are raw Anthropic model strings consumed by @anthropic-ai/claude-agent-sdk + * via AGENT_MODEL — NOT the `provider:type:model` strings promptfoo uses for + * its rubric grader (RUBRIC_MODEL). Don't confuse the two formats. + */ +const MODEL_ALIASES = { + haiku: "claude-haiku-4-5-20251001", + sonnet: "claude-sonnet-4-6", + opus: "claude-opus-4-6", +}; + +/** + * Resolve a CLI argument (alias or raw model id) to the model id sent to the + * Anthropic API. Unknown values pass through untouched so users can point at a + * freshly-released model without editing this file. + */ +function resolveModel(input) { + if (!input) return null; + const trimmed = String(input).trim(); + return MODEL_ALIASES[trimmed] || trimmed; +} + +/** + * Reverse-lookup a friendly alias for a model id, falling back to the model + * id itself. Used to label per-model output files like + * `aiconfig-create/results.haiku.json`. + */ +function aliasFor(modelId) { + for (const [alias, id] of Object.entries(MODEL_ALIASES)) { + if (id === modelId) return alias; + } + return modelId; +} + +module.exports = { MODEL_ALIASES, resolveModel, aliasFor }; diff --git a/evals/scripts/aggregate.js b/evals/scripts/aggregate.js new file mode 100644 index 0000000..42e96ab --- /dev/null +++ b/evals/scripts/aggregate.js @@ -0,0 +1,165 @@ +#!/usr/bin/env node +/** + * Run skill eval suites and aggregate results into eval-scores.json at the + * repo root. + * + * Modes: + * node scripts/aggregate.js # rebuild from existing results.json + * node scripts/aggregate.js --run # run every suite then aggregate + * node scripts/aggregate.js --run --only=aiconfig-create,aiconfig-update + * + * Exits 0 on success, 1 on failure. + */ + +const { spawnSync } = require("node:child_process"); +const fs = require("node:fs"); +const path = require("node:path"); + +const { SUITES } = require("./_manifest"); + +const REPO_ROOT = path.resolve(__dirname, "../.."); +const EVALS_DIR = path.resolve(__dirname, ".."); +const SCORES_PATH = path.join(REPO_ROOT, "eval-scores.json"); +const PROMPTFOO_BIN = path.join(EVALS_DIR, "node_modules", ".bin", "promptfoo"); + +function parseArgs(argv) { + const args = { run: false, only: null }; + for (const arg of argv.slice(2)) { + if (arg === "--run") args.run = true; + else if (arg.startsWith("--only=")) { + args.only = arg.slice("--only=".length).split(",").map((s) => s.trim()).filter(Boolean); + } else if (arg === "--help" || arg === "-h") { + process.stdout.write("Usage: aggregate.js [--run] [--only=]\n"); + process.exit(0); + } + } + return args; +} + +function selectSuites(only) { + if (!only || only.length === 0) return SUITES.slice(); + const set = new Set(only); + const matched = SUITES.filter((s) => set.has(s.suite)); + const unknown = only.filter((s) => !SUITES.find((suite) => suite.suite === s)); + if (unknown.length > 0) { + console.error(`aggregate.js: unknown suite slugs: ${unknown.join(", ")}`); + console.error(`Known suites: ${SUITES.map((s) => s.suite).join(", ")}`); + process.exit(1); + } + return matched; +} + +function headCommit() { + const r = spawnSync("git", ["rev-parse", "--short", "HEAD"], { + cwd: REPO_ROOT, + encoding: "utf-8", + }); + return r.status === 0 ? r.stdout.trim() : null; +} + +function runSuite(suite) { + const outFile = path.join(EVALS_DIR, suite.suite, "results.json"); + console.log(`\n▶ Running eval suite: ${suite.suite}`); + + const result = spawnSync( + PROMPTFOO_BIN, + [ + "eval", + "-c", path.join(EVALS_DIR, "shared", "defaults.yaml"), + "-c", path.join(EVALS_DIR, suite.suite, "promptfooconfig.yaml"), + "--env-file", path.join(EVALS_DIR, ".env"), + "--no-cache", + "-o", outFile, + ], + { cwd: EVALS_DIR, stdio: "inherit", env: { ...process.env } }, + ); + + if (result.status !== 0) { + console.error(`✗ Suite ${suite.suite} exited with status ${result.status}`); + return false; + } + return true; +} + +function readResults(suite) { + const outFile = path.join(EVALS_DIR, suite.suite, "results.json"); + if (!fs.existsSync(outFile)) { + console.error(`aggregate.js: results.json not found for "${suite.suite}" — run with --run first`); + return null; + } + try { + return JSON.parse(fs.readFileSync(outFile, "utf-8")); + } catch (e) { + console.error(`aggregate.js: failed to parse results.json for "${suite.suite}": ${e.message}`); + return null; + } +} + +function summarize(suite, results, commit) { + const tests = results?.results?.results || results?.results || []; + const arr = Array.isArray(tests) ? tests : []; + const total = arr.length; + const passed = arr.filter((t) => t.success).length; + const score = total > 0 ? Math.round((passed / total) * 100) : 0; + const perTest = arr.map((t) => ({ + description: t.description || t.vars?.user_request?.slice(0, 80) || "", + pass: t.success, + score: t.score ?? (t.success ? 1.0 : 0.0), + })); + + return { + score, + passed, + total, + status: score >= 75 ? "passing" : "failing", + lastCommit: commit || null, + lastRun: new Date().toISOString(), + perTest, + }; +} + +function main() { + const args = parseArgs(process.argv); + const suites = selectSuites(args.only); + const commit = headCommit(); + + if (args.run) { + let anyFailed = false; + for (const suite of suites) { + if (!runSuite(suite)) anyFailed = true; + } + if (anyFailed) { + console.error("\naggregate.js: one or more suites failed to run."); + process.exit(1); + } + } + + let existing = {}; + if (fs.existsSync(SCORES_PATH)) { + try { + existing = JSON.parse(fs.readFileSync(SCORES_PATH, "utf-8")).skills || {}; + } catch { + existing = {}; + } + } + + const skills = { ...existing }; + let anyError = false; + + for (const suite of suites) { + const results = readResults(suite); + if (!results) { anyError = true; continue; } + skills[suite.skillKey] = summarize(suite, results, commit); + const s = skills[suite.skillKey]; + const icon = s.status === "passing" ? "✓" : "✗"; + console.log(`${icon} ${suite.skillKey}: ${s.passed}/${s.total} passed (${s.score}%)`); + } + + const output = { schemaVersion: 1, updatedAt: new Date().toISOString(), skills }; + fs.writeFileSync(SCORES_PATH, JSON.stringify(output, null, 2) + "\n"); + console.log(`\nWrote ${SCORES_PATH}`); + + if (anyError) process.exit(1); +} + +main(); diff --git a/evals/scripts/diff-changed-skills.js b/evals/scripts/diff-changed-skills.js new file mode 100644 index 0000000..5bf3ab5 --- /dev/null +++ b/evals/scripts/diff-changed-skills.js @@ -0,0 +1,155 @@ +#!/usr/bin/env node +/** + * Print the suite slugs whose source has changed since their last recorded + * `lastCommit` in eval-scores.json. Output is one slug per line on stdout, + * suitable for: + * + * node scripts/aggregate.js --run --only=$(node scripts/diff-changed-skills.js | paste -sd,) + * + * Modes: + * - No eval-scores.json on disk → every suite is flagged (first run). + * - A suite's lastCommit missing or unreachable → treated as changed. + * - GLOBAL_TRIGGERS (evals/providers, evals/shared, evals/tools, evals/mocks) + * changed since the most-recent recorded commit → every suite flagged. + * + * Flags: + * --json emit a JSON array instead of newline-separated slugs + * --verbose log reasoning to stderr + * --base=SHA compare all suites against this commit instead of their + * recorded lastCommit (useful for pre-merge analysis) + */ + +const { spawnSync } = require("node:child_process"); +const fs = require("node:fs"); +const path = require("node:path"); + +const { SUITES, GLOBAL_TRIGGERS } = require("./_manifest"); + +const REPO_ROOT = path.resolve(__dirname, "../.."); +const SCORES_PATH = path.join(REPO_ROOT, "eval-scores.json"); + +function parseArgs(argv) { + const args = { json: false, verbose: false, base: null }; + for (const arg of argv.slice(2)) { + if (arg === "--json") args.json = true; + else if (arg === "--verbose" || arg === "-v") args.verbose = true; + else if (arg.startsWith("--base=")) args.base = arg.slice("--base=".length); + else if (arg === "--help" || arg === "-h") { + process.stdout.write("Usage: diff-changed-skills.js [--json] [--verbose] [--base=]\n"); + process.exit(0); + } + } + return args; +} + +function log(verbose, msg) { + if (verbose) process.stderr.write(`[diff] ${msg}\n`); +} + +function loadScores() { + if (!fs.existsSync(SCORES_PATH)) return null; + try { + return JSON.parse(fs.readFileSync(SCORES_PATH, "utf-8")); + } catch (e) { + process.stderr.write(`[diff] eval-scores.json unparseable: ${e.message}\n`); + return null; + } +} + +function git(args) { + return spawnSync("git", args, { cwd: REPO_ROOT, encoding: "utf-8" }); +} + +function commitExists(sha) { + if (!sha) return false; + return git(["cat-file", "-e", `${sha}^{commit}`]).status === 0; +} + +/** Returns true if any commit in sinceSha..HEAD touched any of `paths`. */ +function hasChangesIn(sinceSha, paths) { + const r = git(["log", `${sinceSha}..HEAD`, "--name-only", "--pretty=format:", "--", ...paths]); + if (r.status !== 0) return null; + const touched = r.stdout.split("\n").map((s) => s.trim()).filter(Boolean); + return touched.length > 0; +} + +function pathsForSuite(suite) { + return [ + `${suite.skillDir}/SKILL.md`, + `${suite.skillDir}/references`, + `${suite.skillDir}/marketplace.json`, + `evals/${suite.suite}`, + ]; +} + +/** Pick the most recent lastCommit across all suites as the global baseline. */ +function newestRecordedCommit(skillsRecord) { + const entries = Object.values(skillsRecord || {}).filter((e) => e && e.lastCommit); + if (entries.length === 0) return null; + entries.sort((a, b) => (Date.parse(b.lastRun || "") || 0) - (Date.parse(a.lastRun || "") || 0)); + return entries[0].lastCommit; +} + +function emit(args, slugs) { + if (args.json) { + process.stdout.write(JSON.stringify(slugs) + "\n"); + } else { + for (const slug of slugs) process.stdout.write(slug + "\n"); + } +} + +function main() { + const args = parseArgs(process.argv); + const scores = loadScores(); + const changed = []; + + if (!scores) { + log(args.verbose, "no eval-scores.json — flagging every suite as changed"); + emit(args, SUITES.map((s) => s.suite)); + return; + } + + const skillsRecord = scores.skills || {}; + const globalBaseline = newestRecordedCommit(skillsRecord); + + if (globalBaseline) { + const globalChanged = hasChangesIn(globalBaseline, GLOBAL_TRIGGERS); + if (globalChanged) { + log(args.verbose, `global triggers changed since ${globalBaseline} — flagging every suite`); + emit(args, SUITES.map((s) => s.suite)); + return; + } + } + + for (const suite of SUITES) { + const record = skillsRecord[suite.skillKey]; + const baseline = args.base || (record && record.lastCommit) || null; + + if (!baseline) { + log(args.verbose, `${suite.suite}: no recorded lastCommit — flagging as changed`); + changed.push(suite.suite); + continue; + } + + if (!commitExists(baseline)) { + log(args.verbose, `${suite.suite}: baseline ${baseline} not in history — flagging as changed`); + changed.push(suite.suite); + continue; + } + + const result = hasChangesIn(baseline, pathsForSuite(suite)); + if (result === null) { + log(args.verbose, `${suite.suite}: git log failed — flagging as changed`); + changed.push(suite.suite); + } else if (result) { + log(args.verbose, `${suite.suite}: changes since ${baseline} — flagging`); + changed.push(suite.suite); + } else { + log(args.verbose, `${suite.suite}: no changes since ${baseline} — skipping`); + } + } + + emit(args, changed); +} + +main(); diff --git a/evals/scripts/render-badges.js b/evals/scripts/render-badges.js new file mode 100644 index 0000000..b2dc8e5 --- /dev/null +++ b/evals/scripts/render-badges.js @@ -0,0 +1,96 @@ +#!/usr/bin/env node +/** + * Sync per-skill README badges from eval-scores.json. + * + * Locates the marker block in each skill's README: + * + * ... + * + * + * and rewrites only the contents between markers. If markers are missing the + * block is appended to the end of the README. If no README exists a minimal + * stub is created. + * + * Run via `npm run eval:badges` from evals/. + */ + +const fs = require("node:fs"); +const path = require("node:path"); + +const { SUITES } = require("./_manifest"); + +const REPO_ROOT = path.resolve(__dirname, "../.."); +const SCORES_PATH = path.join(REPO_ROOT, "eval-scores.json"); +const START = ""; +const END = ""; + +function loadScores() { + if (!fs.existsSync(SCORES_PATH)) { + console.error(`[render-badges] no eval-scores.json at ${SCORES_PATH}; run \`npm run eval:all\` first`); + process.exit(1); + } + return JSON.parse(fs.readFileSync(SCORES_PATH, "utf-8")); +} + +function badgeContent(entry) { + if (!entry || typeof entry.score !== "number") { + return [START, "_Eval score not yet recorded._", END].join("\n"); + } + const date = (entry.lastRun || "").slice(0, 10) || "unknown"; + const status = entry.status === "passing" ? "passing" : "needs attention"; + return [ + START, + `**Eval score:** ${entry.score}/100 (${entry.passed}/${entry.total} passing, ${status}) — last run ${date}`, + END, + ].join("\n"); +} + +function rewriteReadme(content, block) { + const startIdx = content.indexOf(START); + const endIdx = content.indexOf(END); + if (startIdx === -1 || endIdx === -1 || endIdx < startIdx) { + return content.replace(/\n+$/, "") + "\n\n" + block + "\n"; + } + return content.slice(0, startIdx) + block + content.slice(endIdx + END.length); +} + +function main() { + const scores = loadScores(); + const entries = scores.skills || {}; + let updated = 0, skipped = 0, stubs = 0; + + for (const suite of SUITES) { + if (!suite.readme) { skipped++; continue; } + const readmePath = path.join(REPO_ROOT, suite.readme); + const readmeDir = path.dirname(readmePath); + + if (!fs.existsSync(readmeDir)) { + console.warn(`[render-badges] skipping ${suite.skillKey}: directory not found`); + skipped++; + continue; + } + + const isNewStub = !fs.existsSync(readmePath); + const before = isNewStub + ? `# ${suite.skillKey}\n\nSee [SKILL.md](./SKILL.md) for the skill's contents.\n` + : fs.readFileSync(readmePath, "utf-8"); + + const block = badgeContent(entries[suite.skillKey]); + const after = rewriteReadme(before, block); + + if (after === before && !isNewStub) { skipped++; continue; } + + fs.writeFileSync(readmePath, after, "utf-8"); + if (isNewStub) { + stubs++; + console.log(`[render-badges] created ${path.relative(REPO_ROOT, readmePath)} (stub)`); + } else { + updated++; + console.log(`[render-badges] updated ${path.relative(REPO_ROOT, readmePath)}`); + } + } + + console.log(`[render-badges] done: ${updated} updated, ${stubs} stubs created, ${skipped} unchanged`); +} + +main(); diff --git a/evals/scripts/run-models.js b/evals/scripts/run-models.js new file mode 100644 index 0000000..ad4804c --- /dev/null +++ b/evals/scripts/run-models.js @@ -0,0 +1,210 @@ +#!/usr/bin/env node +/** + * Run skill eval suites under one or more agent (system-under-test) models. + * + * The default eval flow (`npm run eval:all`) runs each suite once on the model + * named by AGENT_MODEL (claude-sonnet-4-6 by default). This script lets you + * compare the same suites across multiple models — e.g. "does my SKILL.md + * still pass on Haiku, or did I overfit to Sonnet?" — without juggling .env edits. + * + * Usage: + * node scripts/run-models.js --model=haiku + * node scripts/run-models.js --model=sonnet --only=aiconfig-create + * node scripts/run-models.js --models=haiku,sonnet,opus + * + * Output: + * - /results..json per (model, suite) + * - Summary table comparing pass-counts and average scores across all pairs + * - Does NOT touch eval-scores.json — that baseline is only written by `eval:all` + * + * To promote a model run to the canonical scores, copy + * `/results..json` -> `/results.json` then run `eval:aggregate`. + */ + +const { spawnSync } = require("node:child_process"); +const fs = require("node:fs"); +const path = require("node:path"); + +const { SUITES } = require("./_manifest"); +const { resolveModel, aliasFor, MODEL_ALIASES } = require("./_models"); + +const EVALS_DIR = path.resolve(__dirname, ".."); +const PROMPTFOO_BIN = path.join(EVALS_DIR, "node_modules", ".bin", "promptfoo"); + +function parseArgs(argv) { + const args = { models: [], only: null }; + for (const arg of argv.slice(2)) { + if (arg.startsWith("--model=")) { + args.models.push(arg.slice("--model=".length)); + } else if (arg.startsWith("--models=")) { + args.models.push( + ...arg + .slice("--models=".length) + .split(",") + .map((s) => s.trim()) + .filter(Boolean), + ); + } else if (arg.startsWith("--only=")) { + args.only = arg + .slice("--only=".length) + .split(",") + .map((s) => s.trim()) + .filter(Boolean); + } else if (arg === "--help" || arg === "-h") { + console.log(usage()); + process.exit(0); + } else { + console.error(`run-models.js: unknown arg "${arg}"`); + console.log(usage()); + process.exit(1); + } + } + if (args.models.length === 0) { + console.error("run-models.js: at least one --model= is required"); + console.log(usage()); + process.exit(1); + } + return args; +} + +function usage() { + return [ + "Usage: node scripts/run-models.js --model= [--only=]", + " node scripts/run-models.js --models=haiku,sonnet,opus", + "", + "Aliases:", + ...Object.entries(MODEL_ALIASES).map(([a, id]) => ` ${a.padEnd(8)}${id}`), + "", + "Examples:", + " npm run eval:haiku", + " npm run eval:matrix", + " node scripts/run-models.js --model=haiku --only=aiconfig-create", + ].join("\n"); +} + +function selectSuites(only) { + if (!only || only.length === 0) return SUITES.slice(); + const set = new Set(only); + const matched = SUITES.filter((s) => set.has(s.suite)); + const unknown = only.filter((s) => !SUITES.find((suite) => suite.suite === s)); + if (unknown.length > 0) { + console.error(`run-models.js: unknown suites: ${unknown.join(", ")}`); + process.exit(1); + } + return matched; +} + +function runSuiteWithModel(suite, modelId, alias) { + const outputPath = path.join(EVALS_DIR, suite.suite, `results.${alias}.json`); + console.log(`\n[run-models] suite=${suite.suite} model=${alias} (${modelId})`); + + const result = spawnSync( + PROMPTFOO_BIN, + [ + "eval", + "-c", "shared/defaults.yaml", + "-c", `${suite.suite}/promptfooconfig.yaml`, + "-o", outputPath, + "--env-file", ".env", + "--no-cache", + ], + { cwd: EVALS_DIR, stdio: "inherit", env: { ...process.env, AGENT_MODEL: modelId } }, + ); + + if (result.error) { + console.error(`[run-models] launch error: ${result.error.message}`); + return false; + } + if (result.status !== 0) { + console.error(`[run-models] suite ${suite.suite} exited with status ${result.status}`); + return false; + } + return true; +} + +function readResults(suite, alias) { + const p = path.join(EVALS_DIR, suite.suite, `results.${alias}.json`); + if (!fs.existsSync(p)) return { error: `missing results.${alias}.json` }; + try { + return { parsed: JSON.parse(fs.readFileSync(p, "utf-8")) }; + } catch (e) { + return { error: `unparseable: ${e.message}` }; + } +} + +function summarise(parsed) { + const rawResults = parsed.results?.results || parsed.results || []; + const arr = Array.isArray(rawResults) ? rawResults : []; + const successes = arr.filter((r) => r && r.success).length; + const total = arr.length; + const scores = arr + .map((r) => r?.score ?? r?.gradingResult?.score) + .filter((s) => typeof s === "number"); + const avgScore = + scores.length > 0 + ? Math.round((scores.reduce((a, b) => a + b, 0) / scores.length) * 100) + : null; + return { successes, total, avgScore }; +} + +function pad(s, n) { + s = String(s); + return s.length >= n ? s : s + " ".repeat(n - s.length); +} + +function printMatrix(rows, aliases, suites) { + const suiteWidth = Math.max(6, ...suites.map((s) => s.suite.length)); + const header = " " + pad("suite", suiteWidth) + " " + aliases.map((a) => pad(a, 16)).join(" "); + const sep = " " + "-".repeat(suiteWidth) + " " + aliases.map(() => "-".repeat(16)).join(" "); + console.log("\n[run-models] Summary (passed/total · avg_score%):"); + console.log(header); + console.log(sep); + for (const suite of suites) { + const cells = aliases.map((alias) => { + const cell = rows[`${alias}::${suite.suite}`]; + if (!cell) return pad("(no results)", 16); + if (cell.error) return pad("error", 16); + return pad(`${cell.successes}/${cell.total} · ${cell.avgScore ?? "-"}%`, 16); + }); + console.log(" " + pad(suite.suite, suiteWidth) + " " + cells.join(" ")); + } +} + +function main() { + const args = parseArgs(process.argv); + const suites = selectSuites(args.only); + const modelEntries = args.models.map((m) => ({ + id: resolveModel(m), + alias: aliasFor(resolveModel(m)), + })); + + console.log("[run-models] models = " + modelEntries.map((m) => `${m.alias}(${m.id})`).join(", ")); + console.log("[run-models] suites = " + suites.map((s) => s.suite).join(", ")); + + let launchFailures = 0; + for (const m of modelEntries) { + for (const suite of suites) { + if (!runSuiteWithModel(suite, m.id, m.alias)) launchFailures++; + } + } + + const rows = {}; + let aggFailures = 0; + for (const m of modelEntries) { + for (const suite of suites) { + const key = `${m.alias}::${suite.suite}`; + const { parsed, error } = readResults(suite, m.alias); + rows[key] = error ? { error } : summarise(parsed); + if (error) aggFailures++; + } + } + + printMatrix(rows, modelEntries.map((m) => m.alias), suites); + + if (launchFailures > 0 || aggFailures > 0) { + console.error(`\n[run-models] ${launchFailures} launch failure(s), ${aggFailures} missing result(s)`); + process.exit(1); + } +} + +main(); diff --git a/evals/shared/assertions.js b/evals/shared/assertions.js new file mode 100644 index 0000000..54f0396 --- /dev/null +++ b/evals/shared/assertions.js @@ -0,0 +1,129 @@ +/** + * Trajectory helpers shared across every suite. + * + * The agent provider returns output as a parsed object (via shared/transform.js): + * { + * response: "", + * trajectory: [ + * { tool: "list-ai-configs", arguments: {...}, turn: 1 }, + * { tool: "setup-ai-config", arguments: {...}, turn: 2 }, + * ... + * ], + * tools_called: ["list-ai-configs", "setup-ai-config"], + * turn_count: 3 + * } + * + * Convention for "X happens after Y" trajectory checks: + * - Use the FIRST occurrence of the prerequisite (Y): tools.indexOf(Y) + * - Use the LAST occurrence of the verifier (X): tools.lastIndexOf(X) + * - Rationale: agents often call `get-foo` before AND after mutating. Using + * indexOf for both would silently pass against the pre-mutation call. + * + * NOTE: promptfoo evaluates inline `type: javascript` assertions via + * new Function("output", "context", "process", body) + * which means `require` is NOT available. So this module is used by scripts + * (aggregate, diff-changed-skills) — inline YAML assertions implement the + * same patterns by hand using indexOf / lastIndexOf directly. + */ + +function getTools(output) { + if (!output || typeof output !== "object") return []; + return Array.isArray(output.tools_called) ? output.tools_called : []; +} + +function getTrajectory(output) { + if (!output || typeof output !== "object") return []; + return Array.isArray(output.trajectory) ? output.trajectory : []; +} + +/** First call of a named tool. Returns { call, idx } — idx is -1 if not found. */ +function firstCallOf(output, name) { + const trajectory = getTrajectory(output); + for (let i = 0; i < trajectory.length; i++) { + if (trajectory[i] && trajectory[i].tool === name) { + return { call: trajectory[i], idx: i }; + } + } + return { call: null, idx: -1 }; +} + +/** Last call of a named tool. Returns { call, idx } — idx is -1 if not found. */ +function lastCallOf(output, name) { + const trajectory = getTrajectory(output); + for (let i = trajectory.length - 1; i >= 0; i--) { + if (trajectory[i] && trajectory[i].tool === name) { + return { call: trajectory[i], idx: i }; + } + } + return { call: null, idx: -1 }; +} + +function called(output, name) { + return getTools(output).includes(name); +} + +function calledAny(output, names) { + const tools = getTools(output); + return names.some((n) => tools.includes(n)); +} + +function calledNone(output, names) { + const tools = getTools(output); + return names.every((n) => !tools.includes(n)); +} + +/** + * Assert that the LAST occurrence of `after` happens after the FIRST + * occurrence of `before`. Returns a promptfoo-shaped grading result. + */ +function expectAfter(output, { before, after }) { + const beforeIdx = firstCallOf(output, before).idx; + const afterIdx = lastCallOf(output, after).idx; + const pass = beforeIdx >= 0 && afterIdx > beforeIdx; + return { + pass, + score: pass ? 1 : 0, + reason: `${before}@${beforeIdx} ${after}@${afterIdx}`, + }; +} + +/** Assert that none of the listed tools were called. */ +function expectNotCalled(output, names) { + const tools = getTools(output); + const hits = names.filter((n) => tools.includes(n)); + const pass = hits.length === 0; + return { + pass, + score: pass ? 1 : 0, + reason: pass + ? `correctly avoided ${names.join(", ")}` + : `called forbidden tools: ${hits.join(", ")}`, + }; +} + +/** Assert that at least one of the listed tools was called. */ +function expectAnyCalled(output, names) { + const tools = getTools(output); + const hit = names.find((n) => tools.includes(n)); + const pass = Boolean(hit); + return { + pass, + score: pass ? 1 : 0, + reason: pass + ? `called ${hit}` + : `none of [${names.join(", ")}] called; tools: ${tools.join(" -> ") || "(none)"}`, + }; +} + +module.exports = { + getTools, + getTrajectory, + firstCallOf, + lastCallOf, + called, + calledAny, + calledNone, + expectAfter, + expectNotCalled, + expectAnyCalled, +}; diff --git a/evals/shared/defaults.yaml b/evals/shared/defaults.yaml new file mode 100644 index 0000000..4d7f593 --- /dev/null +++ b/evals/shared/defaults.yaml @@ -0,0 +1,33 @@ +# yaml-language-server: $schema=https://promptfoo.dev/config-schema.json +# +# Shared defaults for every skill eval suite under evals//. +# +# Wired into each suite at run time via: +# promptfoo eval -c shared/defaults.yaml -c /promptfooconfig.yaml +# +# promptfoo's combineConfigs deep-merges defaultTest.options, concatenates +# defaultTest.assert arrays, and dedupes providers, so each suite only needs +# to declare what's specific to it (description, prompts, providers, tests, +# and any extra suite-specific assertions). +description: "shared defaults" + +prompts: [] +providers: [] + +defaultTest: + # Each test case must reach this weighted-average score to count as + # passing. Evaluated per-test so a single critical path failure can't + # be masked by other tests passing. + threshold: 0.75 + options: + provider: "{{env.RUBRIC_MODEL}}" + transform: file://./transform.js + assert: + - type: javascript + value: file://./output-valid.js + weight: 0 + metric: output_valid + # 180s accommodates multi-turn flows (60-150s typical). Fast single-action + # skills can override per-suite if a tighter cap matters. + - type: latency + threshold: 180000 diff --git a/evals/shared/output-valid.js b/evals/shared/output-valid.js new file mode 100644 index 0000000..911818b --- /dev/null +++ b/evals/shared/output-valid.js @@ -0,0 +1,18 @@ +/** + * Sanity assertion: did the transform succeed in parsing the agent's output? + * + * Weight 0 in shared/defaults.yaml so it does not affect the score — it just + * surfaces a clear "output was not JSON" reason when the provider's + * serialization breaks, instead of letting suite assertions throw with + * confusing stack traces. + */ +module.exports = (output) => { + const isObj = output !== null && typeof output === "object"; + return { + pass: isObj, + score: isObj ? 1 : 0, + reason: isObj + ? "output parsed as JSON object" + : "output was not parseable as JSON object", + }; +}; diff --git a/evals/shared/transform.js b/evals/shared/transform.js new file mode 100644 index 0000000..36fad73 --- /dev/null +++ b/evals/shared/transform.js @@ -0,0 +1,21 @@ +/** + * Default output transform applied to every test via shared/defaults.yaml. + * + * The skill-agent provider serializes its result as a JSON string so the + * promptfoo runner has a single string to render in its UI. Parsing it here + * once means every assertion downstream receives `output` already as an object + * with { response, first_assistant_text, kickoff_text, assistant_turns, + * trajectory, tools_called, turn_count, terminated } instead of a raw string. + * + * If parsing fails the raw string is returned unchanged so `output_valid` + * can flag the failure clearly. + */ +module.exports = (output) => { + if (output && typeof output === "object") return output; + if (typeof output !== "string") return output; + try { + return JSON.parse(output); + } catch (_err) { + return output; + } +}; diff --git a/evals/tests/assertions.test.js b/evals/tests/assertions.test.js new file mode 100644 index 0000000..812360f --- /dev/null +++ b/evals/tests/assertions.test.js @@ -0,0 +1,174 @@ +const { test } = require("node:test"); +const assert = require("node:assert/strict"); + +const { + getTools, + getTrajectory, + firstCallOf, + lastCallOf, + called, + calledAny, + calledNone, + expectAfter, + expectNotCalled, + expectAnyCalled, +} = require("../shared/assertions"); + +// Fixture helpers +function makeOutput(tools) { + const trajectory = tools.map((tool, i) => ({ + tool, + arguments: {}, + turn: i + 1, + })); + return { tools_called: tools, trajectory }; +} + +// --------------------------------------------------------------------------- +// getTools / getTrajectory +// --------------------------------------------------------------------------- + +test("getTools returns tools_called array", () => { + const out = makeOutput(["list-ai-configs", "setup-ai-config"]); + assert.deepEqual(getTools(out), ["list-ai-configs", "setup-ai-config"]); +}); + +test("getTools returns [] for missing/invalid output", () => { + assert.deepEqual(getTools(null), []); + assert.deepEqual(getTools({}), []); + assert.deepEqual(getTools({ tools_called: "bad" }), []); +}); + +test("getTrajectory returns trajectory array", () => { + const out = makeOutput(["setup-ai-config"]); + assert.equal(getTrajectory(out).length, 1); + assert.equal(getTrajectory(out)[0].tool, "setup-ai-config"); +}); + +test("getTrajectory returns [] for missing/invalid output", () => { + assert.deepEqual(getTrajectory(null), []); + assert.deepEqual(getTrajectory({}), []); +}); + +// --------------------------------------------------------------------------- +// firstCallOf / lastCallOf +// --------------------------------------------------------------------------- + +test("firstCallOf returns first occurrence", () => { + const out = makeOutput(["get-ai-config", "setup-ai-config", "get-ai-config"]); + const { call, idx } = firstCallOf(out, "get-ai-config"); + assert.equal(idx, 0); + assert.equal(call.tool, "get-ai-config"); +}); + +test("lastCallOf returns last occurrence", () => { + const out = makeOutput(["get-ai-config", "setup-ai-config", "get-ai-config"]); + const { call, idx } = lastCallOf(out, "get-ai-config"); + assert.equal(idx, 2); + assert.equal(call.tool, "get-ai-config"); +}); + +test("firstCallOf returns idx=-1 when not found", () => { + const out = makeOutput(["setup-ai-config"]); + assert.equal(firstCallOf(out, "missing-tool").idx, -1); + assert.equal(firstCallOf(out, "missing-tool").call, null); +}); + +test("lastCallOf returns idx=-1 when not found", () => { + const out = makeOutput([]); + assert.equal(lastCallOf(out, "anything").idx, -1); +}); + +// --------------------------------------------------------------------------- +// called / calledAny / calledNone +// --------------------------------------------------------------------------- + +test("called returns true when tool is present", () => { + const out = makeOutput(["setup-ai-config"]); + assert.equal(called(out, "setup-ai-config"), true); + assert.equal(called(out, "delete-ai-config"), false); +}); + +test("calledAny returns true if at least one tool matches", () => { + const out = makeOutput(["create-ai-config"]); + assert.equal(calledAny(out, ["setup-ai-config", "create-ai-config"]), true); + assert.equal(calledAny(out, ["setup-ai-config", "delete-ai-config"]), false); +}); + +test("calledNone returns true only if no tools match", () => { + const out = makeOutput(["list-ai-configs", "setup-ai-config"]); + assert.equal(calledNone(out, ["delete-ai-config", "archive-flag"]), true); + assert.equal(calledNone(out, ["setup-ai-config"]), false); +}); + +// --------------------------------------------------------------------------- +// expectAfter +// --------------------------------------------------------------------------- + +test("expectAfter passes when after follows before", () => { + const out = makeOutput(["list-ai-configs", "setup-ai-config"]); + const r = expectAfter(out, { before: "list-ai-configs", after: "setup-ai-config" }); + assert.equal(r.pass, true); + assert.equal(r.score, 1); +}); + +test("expectAfter fails when before is absent", () => { + const out = makeOutput(["setup-ai-config"]); + const r = expectAfter(out, { before: "list-ai-configs", after: "setup-ai-config" }); + assert.equal(r.pass, false); + assert.equal(r.score, 0); +}); + +test("expectAfter fails when after is absent", () => { + const out = makeOutput(["list-ai-configs"]); + const r = expectAfter(out, { before: "list-ai-configs", after: "setup-ai-config" }); + assert.equal(r.pass, false); +}); + +test("expectAfter uses last occurrence of after vs first occurrence of before", () => { + // get-ai-config appears before AND after setup; last get-ai-config should be after setup + const out = makeOutput(["get-ai-config", "setup-ai-config", "get-ai-config"]); + const r = expectAfter(out, { before: "setup-ai-config", after: "get-ai-config" }); + assert.equal(r.pass, true); +}); + +test("expectAfter fails when after only appears before before", () => { + const out = makeOutput(["get-ai-config", "setup-ai-config"]); + // last get-ai-config is at idx 0, setup-ai-config (before) is at idx 1 — so after < before + const r = expectAfter(out, { before: "setup-ai-config", after: "get-ai-config" }); + assert.equal(r.pass, false); +}); + +// --------------------------------------------------------------------------- +// expectNotCalled / expectAnyCalled +// --------------------------------------------------------------------------- + +test("expectNotCalled passes when none of the tools appear", () => { + const out = makeOutput(["setup-ai-config"]); + const r = expectNotCalled(out, ["delete-ai-config", "archive-flag"]); + assert.equal(r.pass, true); + assert.equal(r.score, 1); +}); + +test("expectNotCalled fails when a forbidden tool appears", () => { + const out = makeOutput(["setup-ai-config", "delete-ai-config"]); + const r = expectNotCalled(out, ["delete-ai-config"]); + assert.equal(r.pass, false); + assert.equal(r.score, 0); + assert.match(r.reason, /delete-ai-config/); +}); + +test("expectAnyCalled passes when at least one tool appears", () => { + const out = makeOutput(["create-ai-config"]); + const r = expectAnyCalled(out, ["setup-ai-config", "create-ai-config"]); + assert.equal(r.pass, true); + assert.equal(r.score, 1); + assert.match(r.reason, /create-ai-config/); +}); + +test("expectAnyCalled fails when no matching tool appears", () => { + const out = makeOutput(["list-ai-configs"]); + const r = expectAnyCalled(out, ["setup-ai-config", "create-ai-config"]); + assert.equal(r.pass, false); + assert.equal(r.score, 0); +}); diff --git a/evals/tests/jsonschema-to-zod.test.js b/evals/tests/jsonschema-to-zod.test.js new file mode 100644 index 0000000..7a99e40 --- /dev/null +++ b/evals/tests/jsonschema-to-zod.test.js @@ -0,0 +1,126 @@ +const { test } = require("node:test"); +const assert = require("node:assert/strict"); + +const { inputSchemaToZodShape, fieldToZod } = require("../providers/_jsonschema-to-zod"); +const { z } = require("zod"); + +// --------------------------------------------------------------------------- +// fieldToZod +// --------------------------------------------------------------------------- + +test("string field parses a string", () => { + const schema = fieldToZod({ type: "string" }); + assert.doesNotThrow(() => schema.parse("hello")); + assert.throws(() => schema.parse(42)); +}); + +test("integer field parses integers and rejects floats", () => { + const schema = fieldToZod({ type: "integer" }); + assert.doesNotThrow(() => schema.parse(3)); + assert.throws(() => schema.parse(3.14)); +}); + +test("number field parses floats", () => { + const schema = fieldToZod({ type: "number" }); + assert.doesNotThrow(() => schema.parse(3.14)); +}); + +test("boolean field parses booleans", () => { + const schema = fieldToZod({ type: "boolean" }); + assert.doesNotThrow(() => schema.parse(true)); + assert.throws(() => schema.parse("true")); +}); + +test("array field parses arrays", () => { + const schema = fieldToZod({ type: "array", items: { type: "string" } }); + assert.doesNotThrow(() => schema.parse(["a", "b"])); + assert.throws(() => schema.parse([1, 2])); +}); + +test("array without items accepts any element", () => { + const schema = fieldToZod({ type: "array" }); + assert.doesNotThrow(() => schema.parse([1, "two", true])); +}); + +test("object field with required and optional properties", () => { + const schema = fieldToZod({ + type: "object", + properties: { + name: { type: "string" }, + count: { type: "integer" }, + }, + required: ["name"], + }); + // required field present + assert.doesNotThrow(() => schema.parse({ name: "foo" })); + // optional field absent — ok + assert.doesNotThrow(() => schema.parse({ name: "foo" })); + // required field absent — fails + assert.throws(() => schema.parse({ count: 1 })); +}); + +test("object field uses passthrough for unknown keys", () => { + const schema = fieldToZod({ + type: "object", + properties: { name: { type: "string" } }, + required: ["name"], + }); + const result = schema.parse({ name: "foo", extra: "bar" }); + assert.equal(result.extra, "bar"); +}); + +test("enum field with all-string values", () => { + const schema = fieldToZod({ enum: ["a", "b", "c"] }); + assert.doesNotThrow(() => schema.parse("a")); + assert.throws(() => schema.parse("d")); +}); + +test("mixed-type enum falls back to base type handling", () => { + // mixed enum (string + number) does not produce a z.enum, falls through to type handling + const schema = fieldToZod({ enum: ["a", 1], type: "string" }); + // should fall through to z.string() + assert.doesNotThrow(() => schema.parse("anything")); +}); + +test("description is attached when provided", () => { + const schema = fieldToZod({ type: "string", description: "A label" }); + assert.equal(schema.description, "A label"); +}); + +test("unknown type falls back to z.any()", () => { + const schema = fieldToZod({ type: "banana" }); + assert.doesNotThrow(() => schema.parse(42)); + assert.doesNotThrow(() => schema.parse("foo")); +}); + +test("null/undefined input falls back to z.any()", () => { + assert.doesNotThrow(() => fieldToZod(null).parse("anything")); + assert.doesNotThrow(() => fieldToZod(undefined).parse(42)); +}); + +// --------------------------------------------------------------------------- +// inputSchemaToZodShape +// --------------------------------------------------------------------------- + +test("converts a top-level input_schema to a Zod shape", () => { + const shape = inputSchemaToZodShape({ + type: "object", + properties: { + projectKey: { type: "string" }, + limit: { type: "integer" }, + }, + required: ["projectKey"], + }); + // required field present + assert.doesNotThrow(() => shape.projectKey.parse("my-project")); + // optional field + assert.doesNotThrow(() => shape.limit.parse(undefined)); + // required field rejects wrong type + assert.throws(() => shape.projectKey.parse(42)); +}); + +test("returns empty shape for non-object schema", () => { + assert.deepEqual(inputSchemaToZodShape(null), {}); + assert.deepEqual(inputSchemaToZodShape({ type: "string" }), {}); + assert.deepEqual(inputSchemaToZodShape({}), {}); +}); diff --git a/evals/tests/mock.test.js b/evals/tests/mock.test.js new file mode 100644 index 0000000..85274e7 --- /dev/null +++ b/evals/tests/mock.test.js @@ -0,0 +1,321 @@ +const { test } = require("node:test"); +const assert = require("node:assert/strict"); + +const { renderMockResponse, createMockState } = require("../providers/_mock"); + +const TEMPLATES = require("../mocks/tool-responses.json"); + +// --------------------------------------------------------------------------- +// createMockState +// --------------------------------------------------------------------------- + +test("createMockState returns fresh empty state each call", () => { + const a = createMockState(); + const b = createMockState(); + assert.deepEqual(a, { configs: {}, flags: {} }); + a.configs["x"] = {}; + assert.deepEqual(b.configs, {}); // independent +}); + +// --------------------------------------------------------------------------- +// setup-ai-config (stateful write) +// --------------------------------------------------------------------------- + +test("setup-ai-config stores config in state and returns it", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "my-bot", + name: "My Bot", + mode: "agent", + variationKey: "v1", + variationName: "V1", + modelConfigKey: "Anthropic.claude-sonnet-4-6", + modelName: "claude-sonnet-4-6", + instructions: "Be helpful.", + }, "setup-ai-config", state); + + assert.equal(result.key, "my-bot"); + assert.equal(result.mode, "agent"); + assert.equal(state.configs["my-bot"].name, "My Bot"); + assert.equal(state.configs["my-bot"].variations.length, 1); + assert.equal(state.configs["my-bot"].variations[0].instructions, "Be helpful."); +}); + +// --------------------------------------------------------------------------- +// create-ai-config (stateful write) +// --------------------------------------------------------------------------- + +test("create-ai-config stores config with empty variations", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-ai-config"], { + key: "new-config", + name: "New Config", + mode: "completion", + }, "create-ai-config", state); + + assert.ok(state.configs["new-config"]); + assert.deepEqual(state.configs["new-config"].variations, []); +}); + +// --------------------------------------------------------------------------- +// create-ai-config-variation +// --------------------------------------------------------------------------- + +test("create-ai-config-variation appends to existing config", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-ai-config"], { + key: "my-config", name: "My Config", mode: "agent", + }, "create-ai-config", state); + + renderMockResponse(TEMPLATES["create-ai-config-variation"], { + configKey: "my-config", + key: "v1", + name: "Variation 1", + modelConfigKey: "OpenAI.gpt-4o", + modelName: "gpt-4o", + instructions: "Help the user.", + }, "create-ai-config-variation", state); + + assert.equal(state.configs["my-config"].variations.length, 1); + assert.equal(state.configs["my-config"].variations[0].key, "v1"); +}); + +test("create-ai-config-variation creates stub when parent config missing", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-ai-config-variation"], { + configKey: "orphan-config", + key: "v1", + name: "V1", + modelConfigKey: "OpenAI.gpt-4o", + modelName: "gpt-4o", + }, "create-ai-config-variation", state); + + assert.ok(state.configs["orphan-config"], "stub config should be created"); + assert.equal(state.configs["orphan-config"].variations.length, 1); +}); + +// --------------------------------------------------------------------------- +// update-ai-config-variation +// --------------------------------------------------------------------------- + +test("update-ai-config-variation patches only variation fields", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "bot", + name: "Bot", + mode: "agent", + variationKey: "default", + variationName: "Default", + modelConfigKey: "OpenAI.gpt-4o", + modelName: "gpt-4o", + instructions: "Original.", + }, "setup-ai-config", state); + + renderMockResponse(TEMPLATES["update-ai-config-variation"], { + configKey: "bot", + variationKey: "default", + modelConfigKey: "OpenAI.gpt-4o-mini", + modelName: "gpt-4o-mini", + }, "update-ai-config-variation", state); + + const v = state.configs["bot"].variations[0]; + assert.equal(v.modelConfigKey, "OpenAI.gpt-4o-mini"); + assert.equal(v.modelName, "gpt-4o-mini"); + assert.equal(v.instructions, "Original."); // unchanged + // input-only fields must NOT bleed into the variation + assert.ok(!("configKey" in v), "configKey must not appear on variation"); + assert.ok(!("variationKey" in v), "variationKey must not appear on variation"); +}); + +test("update-ai-config-variation is a no-op when config not in state", () => { + const state = createMockState(); + // Should not throw + assert.doesNotThrow(() => + renderMockResponse(TEMPLATES["update-ai-config-variation"], { + configKey: "nonexistent", + variationKey: "default", + modelConfigKey: "OpenAI.gpt-4o-mini", + }, "update-ai-config-variation", state) + ); + assert.deepEqual(state.configs, {}); +}); + +// --------------------------------------------------------------------------- +// get-ai-config (stateful read) +// --------------------------------------------------------------------------- + +test("get-ai-config returns state config when present", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "bot", name: "Bot", mode: "agent", + variationKey: "default", variationName: "Default", + modelConfigKey: "OpenAI.gpt-4o", modelName: "gpt-4o", + }, "setup-ai-config", state); + + const result = renderMockResponse(TEMPLATES["get-ai-config"], { + configKey: "bot", + }, "get-ai-config", state); + + assert.equal(result.key, "bot"); + assert.equal(result.name, "Bot"); +}); + +test("get-ai-config loads SEED_CONFIGS when key matches", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["get-ai-config"], { + configKey: "support-chatbot", + }, "get-ai-config", state); + + assert.equal(result.key, "support-chatbot"); + assert.ok(result.variations.length > 0); + // seed should now be in state for subsequent calls + assert.ok(state.configs["support-chatbot"]); +}); + +test("get-ai-config falls back to template for unknown key", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["get-ai-config"], { + configKey: "mystery-config", + }, "get-ai-config", state); + + assert.equal(result.key, "mystery-config"); // template substitution +}); + +// --------------------------------------------------------------------------- +// list-ai-configs (stateful merge) +// --------------------------------------------------------------------------- + +test("list-ai-configs returns static list when state is empty", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["list-ai-configs"], {}, "list-ai-configs", state); + assert.ok(result.configs.length > 0); +}); + +test("list-ai-configs merges state configs, state wins for duplicate keys", () => { + const state = createMockState(); + // write over a seed key + renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "support-chatbot", + name: "My Custom Chatbot", + mode: "completion", + variationKey: "default", + variationName: "Default", + modelConfigKey: "OpenAI.gpt-4o", + modelName: "gpt-4o", + }, "setup-ai-config", state); + + const result = renderMockResponse(TEMPLATES["list-ai-configs"], {}, "list-ai-configs", state); + const entry = result.configs.find((c) => c.key === "support-chatbot"); + assert.ok(entry, "support-chatbot should appear in list"); + assert.equal(entry.name, "My Custom Chatbot", "state entry should win over static template"); + // should appear exactly once + const count = result.configs.filter((c) => c.key === "support-chatbot").length; + assert.equal(count, 1); +}); + +test("list-ai-configs adds newly created configs not in static list", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-ai-config"], { + key: "brand-new", name: "Brand New", mode: "agent", + }, "create-ai-config", state); + + const result = renderMockResponse(TEMPLATES["list-ai-configs"], {}, "list-ai-configs", state); + const entry = result.configs.find((c) => c.key === "brand-new"); + assert.ok(entry); + assert.equal(result.totalCount, result.configs.length); +}); + +// --------------------------------------------------------------------------- +// get-ai-config-health +// --------------------------------------------------------------------------- + +test("get-ai-config-health reflects state when config is present", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "bot", name: "Bot", mode: "agent", + variationKey: "default", variationName: "Default", + modelConfigKey: "OpenAI.gpt-4o", modelName: "gpt-4o", + instructions: "Be helpful.", + }, "setup-ai-config", state); + + const health = renderMockResponse(TEMPLATES["get-ai-config-health"], { + configKey: "bot", + }, "get-ai-config-health", state); + + assert.equal(health.key, "bot"); + assert.equal(health.health, "healthy"); + assert.equal(health.variationsCount, 1); + assert.equal(health.variations[0].hasModel, true); + assert.equal(health.variations[0].hasPrompts, true); +}); + +test("get-ai-config-health falls back to template for unknown key", () => { + const state = createMockState(); + const health = renderMockResponse(TEMPLATES["get-ai-config-health"], { + configKey: "unknown-config", + }, "get-ai-config-health", state); + // template fallback — key should be substituted + assert.equal(health.key, "unknown-config"); +}); + +// --------------------------------------------------------------------------- +// create-flag / get-flag (flag state) +// --------------------------------------------------------------------------- + +test("create-flag stores flag in state", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-flag"], { + key: "my-new-flag", + name: "My New Flag", + }, "create-flag", state); + + assert.ok(state.flags["my-new-flag"]); +}); + +test("get-flag returns state flag when present", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-flag"], { + key: "my-flag", + name: "My Flag", + }, "create-flag", state); + + const result = renderMockResponse(TEMPLATES["get-flag"], { + flagKey: "my-flag", + }, "get-flag", state); + + assert.equal(result.key, "my-flag"); +}); + +test("get-flag falls back to template substitution for unknown flag", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["get-flag"], { + flagKey: "unknown-flag", + flagName: "Unknown Flag", + }, "get-flag", state); + assert.equal(result.key, "unknown-flag"); +}); + +// --------------------------------------------------------------------------- +// stateless template rendering ({{placeholder}} substitution) +// --------------------------------------------------------------------------- + +test("template substitution fills {{configKey}} and {{configName}}", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["create-ai-config"], { + key: "my-config", + name: "My Config", + mode: "completion", + }, "create-ai-config", state); + // result from stateful handler, not template — check state + assert.equal(state.configs["my-config"].key, "my-config"); +}); + +test("update-ai-config uses template substitution", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["update-ai-config"], { + configKey: "bot", + configName: "Bot", + }, "update-ai-config", state); + assert.equal(result.key, "bot"); + assert.equal(result.name, "Bot"); +}); diff --git a/evals/tests/output-valid.test.js b/evals/tests/output-valid.test.js new file mode 100644 index 0000000..7ace382 --- /dev/null +++ b/evals/tests/output-valid.test.js @@ -0,0 +1,45 @@ +const { test } = require("node:test"); +const assert = require("node:assert/strict"); + +const outputValid = require("../shared/output-valid"); + +test("passes for a plain object", () => { + const r = outputValid({ response: "hello" }); + assert.equal(r.pass, true); + assert.equal(r.score, 1); +}); + +test("passes for an empty object", () => { + const r = outputValid({}); + assert.equal(r.pass, true); + assert.equal(r.score, 1); +}); + +test("fails for a raw string (unparsed output)", () => { + const r = outputValid("not an object"); + assert.equal(r.pass, false); + assert.equal(r.score, 0); +}); + +test("fails for null", () => { + const r = outputValid(null); + assert.equal(r.pass, false); + assert.equal(r.score, 0); +}); + +test("fails for undefined", () => { + const r = outputValid(undefined); + assert.equal(r.pass, false); + assert.equal(r.score, 0); +}); + +test("fails for a number", () => { + const r = outputValid(42); + assert.equal(r.pass, false); + assert.equal(r.score, 0); +}); + +test("result always includes a reason string", () => { + assert.equal(typeof outputValid({}).reason, "string"); + assert.equal(typeof outputValid("bad").reason, "string"); +}); diff --git a/evals/tests/transform.test.js b/evals/tests/transform.test.js new file mode 100644 index 0000000..4f22a58 --- /dev/null +++ b/evals/tests/transform.test.js @@ -0,0 +1,28 @@ +const { test } = require("node:test"); +const assert = require("node:assert/strict"); + +const transform = require("../shared/transform"); + +test("returns parsed object when given valid JSON string", () => { + const input = JSON.stringify({ response: "hello", tools_called: ["setup-ai-config"] }); + const result = transform(input); + assert.deepEqual(result, { response: "hello", tools_called: ["setup-ai-config"] }); +}); + +test("returns object unchanged when already an object", () => { + const input = { response: "hello" }; + const result = transform(input); + assert.equal(result, input); +}); + +test("returns raw string when JSON.parse fails", () => { + const bad = "not json {{"; + const result = transform(bad); + assert.equal(result, bad); +}); + +test("returns non-string, non-object values unchanged", () => { + assert.equal(transform(null), null); + assert.equal(transform(42), 42); + assert.equal(transform(undefined), undefined); +}); diff --git a/evals/tools/definitions.json b/evals/tools/definitions.json new file mode 100644 index 0000000..32e69f2 --- /dev/null +++ b/evals/tools/definitions.json @@ -0,0 +1,513 @@ +[ + { + "name": "list-flags", + "description": "Search and browse feature flags in a project. Returns a paginated list scoped to a single environment. Use query to search by name/key, tags to filter by tag, state to filter by lifecycle state (active, inactive, new, launched, archived), and type to filter by temporary or permanent.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "env": { "type": "string", "description": "Environment key (defaults to production)" }, + "query": { "type": "string", "description": "Search by flag name or key" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Filter by tags" }, + "state": { "type": "string", "enum": ["active", "inactive", "archived", "new", "launched"], "description": "Filter by lifecycle state" }, + "type": { "type": "string", "enum": ["temporary", "permanent"], "description": "Filter by temporary or permanent" }, + "limit": { "type": "number", "description": "Max number of results (default 20)" } + }, + "required": ["projectKey"] + } + }, + { + "name": "get-flag", + "description": "Get detailed configuration for a single feature flag scoped to a specific environment. Returns the full targeting tree including rules, individual targets, fallthrough, prerequisites, and variation details.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "flagKey": { "type": "string", "description": "The flag key" }, + "env": { "type": "string", "description": "Environment key (defaults to production)" } + }, + "required": ["projectKey", "flagKey"] + } + }, + { + "name": "create-flag", + "description": "Create a new feature flag in a project. Defaults to a boolean temporary flag. After creation the flag is OFF in all environments: use toggle-flag to enable it. For multivariate flags, provide variations array with {value, name} entries.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "name": { "type": "string", "description": "Human-readable flag name" }, + "key": { "type": "string", "description": "Unique flag key (immutable)" }, + "kind": { "type": "string", "enum": ["boolean", "multivariate"], "description": "Flag kind (default: boolean)" }, + "description": { "type": "string", "description": "Description of the flag's purpose" }, + "temporary": { "type": "boolean", "description": "Whether the flag is temporary (default: true)" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Tags for organization" }, + "variations": { + "type": "array", + "items": { + "type": "object", + "properties": { + "value": { "description": "The variation value" }, + "name": { "type": "string", "description": "Variation name" } + } + }, + "description": "Custom variations (for multivariate flags)" + }, + "clientSideAvailability": { + "type": "object", + "properties": { + "usingMobileKey": { "type": "boolean" }, + "usingEnvironmentId": { "type": "boolean" } + }, + "description": "Client-side SDK availability" + } + }, + "required": ["projectKey", "name", "key"] + } + }, + { + "name": "update-flag-settings", + "description": "Update a flag's top-level settings: name, description, tags, temporary/permanent status, or maintainer. Does NOT modify targeting, rollouts, or rules: use the targeting tools for those. Supported instruction kinds: updateName, updateDescription, addTags, removeTags, markTemporary, markPermanent, updateMaintainerMember.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "flagKey": { "type": "string", "description": "The flag key" }, + "instructions": { + "type": "array", + "items": { "type": "object" }, + "description": "Array of semantic patch instructions" + }, + "comment": { "type": "string", "description": "Optional comment for audit log" } + }, + "required": ["projectKey", "flagKey", "instructions"] + } + }, + { + "name": "toggle-flag", + "description": "Turn a feature flag's targeting on or off in a specific environment. Returns the previous and new state.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "flagKey": { "type": "string", "description": "The flag key" }, + "env": { "type": "string", "description": "Environment key" }, + "on": { "type": "boolean", "description": "Whether to turn targeting on or off" }, + "comment": { "type": "string", "description": "Optional comment" } + }, + "required": ["projectKey", "flagKey", "env", "on"] + } + }, + { + "name": "list-ai-configs", + "description": "Search and browse AI Configs in a project. Returns a paginated list with key, name, mode (agent or completion), tags, and variation count. Use query to search by name or key.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "query": { "type": "string", "description": "Search by name or key" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Filter by tags" }, + "limit": { "type": "number", "description": "Max number of results (default 20)" } + }, + "required": ["projectKey"] + } + }, + { + "name": "get-ai-config", + "description": "Get detailed configuration for a single AI Config including all its variations. Each variation includes its model, instructions or messages, parameters, and attached tools.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" } + }, + "required": ["projectKey", "configKey"] + } + }, + { + "name": "create-ai-config", + "description": "Create a new AI Config in a project. This creates the config shell: use create-ai-config-variation next to add a model, prompts, and parameters. Mode determines whether variations use 'instructions' (agent) or 'messages' (completion).", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "key": { "type": "string", "description": "Unique config key (lowercase, hyphens)" }, + "name": { "type": "string", "description": "Human-readable config name" }, + "mode": { "type": "string", "enum": ["agent", "completion"], "description": "Agent uses instructions; completion uses messages" }, + "description": { "type": "string", "description": "Description of the config's purpose" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Tags for organization" } + }, + "required": ["projectKey", "key", "name", "mode"] + } + }, + { + "name": "update-ai-config", + "description": "Update an AI Config's metadata: name, description, tags, or archive status. Does NOT modify variations: use update-ai-config-variation for model, prompt, or parameter changes. Set archived: true to archive (reversible).", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" }, + "name": { "type": "string", "description": "New config name" }, + "description": { "type": "string", "description": "New description" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Replacement tags" }, + "archived": { "type": "boolean", "description": "Set true to archive, false to unarchive" } + }, + "required": ["projectKey", "configKey"] + } + }, + { + "name": "delete-ai-config", + "description": "Permanently delete an AI Config. THIS IS IRREVERSIBLE. Requires confirm=true to execute. Prefer archiving (update-ai-config with archived: true) when possible.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" }, + "confirm": { "type": "boolean", "description": "Must be true to execute deletion" } + }, + "required": ["projectKey", "configKey", "confirm"] + } + }, + { + "name": "setup-ai-config", + "description": "Create an AI Config with its first variation in one step. This is the recommended way to set up a new AI Config: it creates the config, adds a variation with model and prompts, and verifies everything is configured correctly. Returns the full config detail with variation. To attach AI tools, pass the 'tools' array with {key, version} entries. Use create-ai-config + create-ai-config-variation separately only when you need more control.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "key": { "type": "string", "description": "Unique config key (lowercase, hyphens)" }, + "name": { "type": "string", "description": "Human-readable config name" }, + "mode": { "type": "string", "enum": ["agent", "completion"], "description": "Agent uses instructions; completion uses messages" }, + "description": { "type": "string", "description": "Description of the config's purpose" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Tags for organization" }, + "variationKey": { "type": "string", "description": "Key for the first variation" }, + "variationName": { "type": "string", "description": "Name for the first variation" }, + "modelConfigKey": { "type": "string", "description": "Provider.model-id format (e.g. OpenAI.gpt-4o)" }, + "modelName": { "type": "string", "description": "The model identifier (e.g. gpt-4o)" }, + "instructions": { "type": "string", "description": "System instructions (agent mode)" }, + "messages": { + "type": "array", + "items": { + "type": "object", + "properties": { + "role": { "type": "string", "description": "Message role (system, user, assistant)" }, + "content": { "type": "string", "description": "Message content" } + }, + "required": ["role", "content"] + }, + "description": "Message array (completion mode)" + }, + "parameters": { "type": "object", "description": "Model parameters (temperature, maxTokens, etc.)" }, + "tools": { + "type": "array", + "items": { + "type": "object", + "properties": { + "key": { "type": "string", "description": "AI tool key" }, + "version": { "type": "number", "description": "Tool version" } + }, + "required": ["key", "version"] + }, + "description": "AI tools to attach" + } + }, + "required": ["projectKey", "key", "name", "mode", "variationKey", "variationName", "modelConfigKey", "modelName"] + } + }, + { + "name": "get-ai-config-health", + "description": "Health check for an AI Config. Detects common issues: missing models (NO MODEL in UI), missing prompts, orphaned tool references, and empty configs with no variations. Returns a health verdict (healthy, warning, unhealthy) with specific issues and per-variation summaries. Run before updating or experimenting with a config.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" } + }, + "required": ["projectKey", "configKey"] + } + }, + { + "name": "create-ai-config-variation", + "description": "Create a variation for an AI Config. A variation defines the model, prompts, parameters, and tools. modelConfigKey must be in Provider.model-id format (e.g. OpenAI.gpt-4o, Anthropic.claude-sonnet-4-5) for models to display correctly in the UI. Agent-mode configs use 'instructions' (a string); completion-mode configs use 'messages' (an array of {role, content} objects). To attach AI tools, pass the 'tools' array with {key, version} entries (create tools first with create-ai-tool).", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" }, + "key": { "type": "string", "description": "Unique variation key" }, + "name": { "type": "string", "description": "Human-readable variation name" }, + "modelConfigKey": { "type": "string", "description": "Provider.model-id format (e.g. OpenAI.gpt-4o)" }, + "modelName": { "type": "string", "description": "The model identifier (e.g. gpt-4o)" }, + "instructions": { "type": "string", "description": "System instructions (agent mode)" }, + "messages": { + "type": "array", + "items": { + "type": "object", + "properties": { + "role": { "type": "string", "description": "Message role" }, + "content": { "type": "string", "description": "Message content" } + }, + "required": ["role", "content"] + }, + "description": "Message array (completion mode)" + }, + "parameters": { "type": "object", "description": "Model parameters (temperature, maxTokens, etc.)" }, + "tools": { + "type": "array", + "items": { + "type": "object", + "properties": { + "key": { "type": "string", "description": "AI tool key" }, + "version": { "type": "number", "description": "Tool version" } + }, + "required": ["key", "version"] + }, + "description": "AI tools to attach" + } + }, + "required": ["projectKey", "configKey", "key", "name", "modelConfigKey", "modelName"] + } + }, + { + "name": "update-ai-config-variation", + "description": "Update an AI Config variation's model, instructions/messages, parameters, or attached tools. All fields are optional: only provided fields are updated. To attach tools, pass the 'tools' array with {key, version} entries (create tools first with create-ai-tool). Pass an empty tools array to detach all tools.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" }, + "variationKey": { "type": "string", "description": "The variation key to update" }, + "modelConfigKey": { "type": "string", "description": "New Provider.model-id format key" }, + "modelName": { "type": "string", "description": "New model identifier" }, + "instructions": { "type": "string", "description": "New system instructions (agent mode)" }, + "messages": { + "type": "array", + "items": { + "type": "object", + "properties": { + "role": { "type": "string", "description": "Message role" }, + "content": { "type": "string", "description": "Message content" } + }, + "required": ["role", "content"] + }, + "description": "New message array (completion mode)" + }, + "parameters": { "type": "object", "description": "New model parameters" }, + "tools": { + "type": "array", + "items": { + "type": "object", + "properties": { + "key": { "type": "string", "description": "AI tool key" }, + "version": { "type": "number", "description": "Tool version" } + }, + "required": ["key", "version"] + }, + "description": "Tools to attach (replaces existing)" + } + }, + "required": ["projectKey", "configKey", "variationKey"] + } + }, + { + "name": "delete-ai-config-variation", + "description": "Permanently delete an AI Config variation. THIS IS IRREVERSIBLE. Requires confirm=true to execute.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" }, + "variationKey": { "type": "string", "description": "The variation key to delete" }, + "confirm": { "type": "boolean", "description": "Must be true to execute deletion" } + }, + "required": ["projectKey", "configKey", "variationKey", "confirm"] + } + }, + { + "name": "clone-ai-config-variation", + "description": "Clone an existing AI Config variation with selective overrides. Reads the source variation, applies any provided overrides (model, instructions, messages, parameters, tools), and creates a new variation. Returns both the source and created variation so you can compare the diff. Use this for A/B experimentation: change one thing at a time while keeping everything else constant.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "configKey": { "type": "string", "description": "The AI Config key" }, + "sourceVariationKey": { "type": "string", "description": "Key of the variation to clone from" }, + "key": { "type": "string", "description": "Key for the new variation" }, + "name": { "type": "string", "description": "Name for the new variation" }, + "modelConfigKey": { "type": "string", "description": "Override Provider.model-id format key" }, + "modelName": { "type": "string", "description": "Override model identifier" }, + "instructions": { "type": "string", "description": "Override system instructions" }, + "messages": { + "type": "array", + "items": { + "type": "object", + "properties": { + "role": { "type": "string", "description": "Message role" }, + "content": { "type": "string", "description": "Message content" } + }, + "required": ["role", "content"] + }, + "description": "Override message array" + }, + "parameters": { "type": "object", "description": "Override model parameters" }, + "tools": { + "type": "array", + "items": { + "type": "object", + "properties": { + "key": { "type": "string", "description": "AI tool key" }, + "version": { "type": "number", "description": "Tool version" } + }, + "required": ["key", "version"] + }, + "description": "Override tools to attach" + } + }, + "required": ["projectKey", "configKey", "sourceVariationKey", "key", "name"] + } + }, + { + "name": "list-ai-tools", + "description": "List AI tool definitions in a project. Returns each tool's key, description, and schema. Tools are attached to AI Config variations to give models function-calling capabilities.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "limit": { "type": "number", "description": "Max number of results (default 20)" } + }, + "required": ["projectKey"] + } + }, + { + "name": "get-ai-tool", + "description": "Get a single AI tool definition including its full schema. Use to inspect a tool's parameters before attaching it to an AI Config variation.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "toolKey": { "type": "string", "description": "The AI tool key" } + }, + "required": ["projectKey", "toolKey"] + } + }, + { + "name": "create-ai-tool", + "description": "Create a new AI tool definition in a project. The schema should be a raw JSON Schema object with type, properties, and required fields (e.g. {\"type\": \"object\", \"properties\": {...}}). Do NOT use the OpenAI function calling wrapper format. After creation, attach the tool to a variation using update-ai-config-variation.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "key": { "type": "string", "description": "Unique tool key" }, + "description": { "type": "string", "description": "Tool description (LLM uses this to decide when to call it)" }, + "schema": { "type": "object", "description": "Raw JSON Schema with type, properties, and required" } + }, + "required": ["projectKey", "key", "description", "schema"] + } + }, + { + "name": "get-environments", + "description": "List all environments for a project. Returns each environment's key, name, color, and the credentials that the SDKs need: SDK key (server-side), client-side ID (browser/edge), and mobile key. Use this as the single source for all key types when wiring up an SDK during onboarding -- do not make separate per-key requests.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" } + }, + "required": ["projectKey"] + } + }, + { + "name": "list-feature-flags", + "description": "List feature flags in a project, scoped to a single environment. Returns each flag's key, name, kind, tags, and whether targeting is on. Pagination via limit/offset.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "environmentKey": { "type": "string", "description": "Environment key (defaults to production)" }, + "limit": { "type": "number", "description": "Max number of results (default 20)" }, + "offset": { "type": "number", "description": "Pagination offset (default 0)" } + }, + "required": ["projectKey"] + } + }, + { + "name": "get-feature-flag", + "description": "Get detailed configuration for a single feature flag in a specific environment. Returns the full targeting tree: rules, individual targets, fallthrough, prerequisites, and variation details.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "flagKey": { "type": "string", "description": "The flag key" }, + "environmentKey": { "type": "string", "description": "Environment key (defaults to production)" } + }, + "required": ["projectKey", "flagKey"] + } + }, + { + "name": "create-feature-flag", + "description": "Create a new feature flag in a project. Defaults to a boolean temporary flag. After creation the flag is OFF in every environment: use update-feature-flag with {on: true} to turn it on. Use kebab-case keys.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "key": { "type": "string", "description": "Unique flag key (kebab-case, immutable)" }, + "name": { "type": "string", "description": "Human-readable flag name" }, + "kind": { "type": "string", "enum": ["boolean", "multivariate"], "description": "Flag kind (default: boolean)" }, + "description": { "type": "string", "description": "Description of the flag's purpose" }, + "temporary": { "type": "boolean", "description": "Whether the flag is temporary (default: true)" }, + "tags": { "type": "array", "items": { "type": "string" }, "description": "Tags for organization" }, + "variations": { + "type": "array", + "items": { + "type": "object", + "properties": { + "value": { "description": "The variation value" }, + "name": { "type": "string", "description": "Variation name" } + } + }, + "description": "Custom variations (for multivariate flags)" + }, + "clientSideAvailability": { + "type": "object", + "properties": { + "usingMobileKey": { "type": "boolean" }, + "usingEnvironmentId": { "type": "boolean" } + }, + "description": "Client-side SDK availability" + } + }, + "required": ["projectKey", "key", "name"] + } + }, + { + "name": "update-feature-flag", + "description": "Update or toggle a feature flag in a specific environment. Pass {on: true} or {on: false} to flip targeting; pass `instructions` (semantic patch instructions) for richer changes (rules, fallthrough, etc.). Returns the previous and new state.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" }, + "flagKey": { "type": "string", "description": "The flag key" }, + "environmentKey": { "type": "string", "description": "Environment key" }, + "on": { "type": "boolean", "description": "Whether to turn targeting on or off" }, + "instructions": { + "type": "array", + "items": { "type": "object" }, + "description": "Semantic patch instructions for richer changes" + }, + "comment": { "type": "string", "description": "Optional comment for the audit log" } + }, + "required": ["projectKey", "flagKey", "environmentKey"] + } + }, + { + "name": "get-project", + "description": "Get a project by key. Returns the project's key, name, and environments.", + "input_schema": { + "type": "object", + "properties": { + "projectKey": { "type": "string", "description": "The project key" } + }, + "required": ["projectKey"] + } + } +] diff --git a/package.json b/package.json index 4cf4d53..215b3dd 100644 --- a/package.json +++ b/package.json @@ -1,8 +1,10 @@ { "name": "launchdarkly-ai-tooling", "private": true, - "description": "LaunchDarkly agent skills; use scripts here for repo-wide dev tasks (see tests/ for eval tooling).", + "description": "LaunchDarkly agent skills; use scripts here for repo-wide dev tasks.", "scripts": { - "test:llm-evals": "npm run test:llm-evals --prefix tests" + "eval": "npm run eval:all --prefix evals", + "eval:all": "npm run eval:all --prefix evals", + "eval:view": "npm run eval:view --prefix evals" } } From 51151868804414831620e11fac49e83b490033bd Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Tue, 19 May 2026 16:18:40 -0700 Subject: [PATCH 02/16] consolidated MCP server for LD --- .mcp.json | 9 ++------- .../references/mcp-config-templates.md | 16 +++++++++------- 2 files changed, 11 insertions(+), 14 deletions(-) diff --git a/.mcp.json b/.mcp.json index db7f522..6bb3074 100644 --- a/.mcp.json +++ b/.mcp.json @@ -1,13 +1,8 @@ { "mcpServers": { - "LaunchDarkly Feature Management": { + "LaunchDarkly": { "type": "http", - "url": "https://mcp.launchdarkly.com/mcp/fm", - "headers": {} - }, - "LaunchDarkly AI Configs": { - "type": "http", - "url": "https://mcp.launchdarkly.com/mcp/aiconfigs", + "url": "https://mcp.launchdarkly.com/mcp/launchdarkly", "headers": {} } } diff --git a/skills/onboarding/mcp-configure/references/mcp-config-templates.md b/skills/onboarding/mcp-configure/references/mcp-config-templates.md index 484ebbb..bee52ca 100644 --- a/skills/onboarding/mcp-configure/references/mcp-config-templates.md +++ b/skills/onboarding/mcp-configure/references/mcp-config-templates.md @@ -102,26 +102,28 @@ If the user has the old npx-based server configured, replace it: Also remove any `LD_ACCESS_TOKEN` or `LAUNCHDARKLY_API_KEY` environment variables that were used for the local server. The hosted server handles authentication via OAuth. -### From the deprecated AgentControl server +### From deprecated split servers (`mcp/fm` and `mcp/aiconfigs`) -The `mcp/aiconfigs` endpoint is deprecated. The unified server (`mcp/launchdarkly`) and its mirror (`mcp/fm`) both handle AgentControl now. +Both `mcp/fm` and `mcp/aiconfigs` are deprecated. All functionality is now in the unified server (`mcp/launchdarkly`). -If the user has `mcp/aiconfigs` configured, **ask before removing** — see the edge case flow in [SKILL.md](../SKILL.md#edge-cases). The user should confirm the migration. +If the user has either endpoint configured, **ask before removing** — see the edge case flow in [SKILL.md](../SKILL.md#edge-cases). The user should confirm the migration. -**Entry to remove (after user confirms):** +**Entries to remove (after user confirms):** ```json { "mcpServers": { + "LaunchDarkly Feature Management": { + "url": "https://mcp.launchdarkly.com/mcp/fm" + }, "LaunchDarkly AgentControl": { - "url": "https://mcp.launchdarkly.com/mcp/aiconfigs", - "headers": {} + "url": "https://mcp.launchdarkly.com/mcp/aiconfigs" } } } ``` -**Ensure the unified server is present** (see sections above). If they already have `mcp/fm` configured, that works — it mirrors `mcp/launchdarkly`. +**Replace with the single unified server** (see sections above). ## Local server via `npx` From 7c08190e3e49f77c812663feadf87e1a206e2deb Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Tue, 19 May 2026 16:26:52 -0700 Subject: [PATCH 03/16] Add CI workflow for skill evals (port from #54 + unit-test job) --- .github/workflows/eval-skills.yml | 273 ++++++++++++++++++++++++++++++ 1 file changed, 273 insertions(+) create mode 100644 .github/workflows/eval-skills.yml diff --git a/.github/workflows/eval-skills.yml b/.github/workflows/eval-skills.yml new file mode 100644 index 0000000..3293ab2 --- /dev/null +++ b/.github/workflows/eval-skills.yml @@ -0,0 +1,273 @@ +name: Skill Evals + +# Diff-gated evaluation runner for the public-facing skills under skills/. +# +# Triggers: +# - pull_request: comment score diff vs main; do not commit anything. +# - schedule: nightly run on changed skills, commit refreshed +# eval-scores.json + per-skill README badges back to main. +# - workflow_dispatch: manual full or partial re-run. +# +# Cost shape: only suites whose source has actually changed (per +# evals/scripts/diff-changed-skills.js) get re-evaluated, so a typical PR +# touching one skill costs roughly one suite's worth of API tokens. + +on: + pull_request: + paths: + - "skills/**" + - "evals/**" + - ".github/workflows/eval-skills.yml" + schedule: + # 09:17 UTC daily - off the hour to avoid lining up with API rate limits. + - cron: "17 9 * * *" + workflow_dispatch: + inputs: + run_all: + description: "Re-run every suite regardless of diff" + type: boolean + default: false + +concurrency: + group: skill-evals-${{ github.ref }} + cancel-in-progress: true + +permissions: + # contents: write is needed only on `schedule` / `workflow_dispatch` so the + # aggregate job can push the refreshed eval-scores.json and per-skill README + # badges back to main. Pull requests use the same workflow but the commit + # step is gated on event_name, so PR runs effectively only need read. + contents: write + pull-requests: write + +jobs: + unit-test: + name: "Unit tests" + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + + - name: Setup Node.js + uses: actions/setup-node@v4 + with: + node-version: "22" + cache: "npm" + cache-dependency-path: evals/package-lock.json + + - name: Install eval dependencies + run: npm ci + working-directory: evals + + - name: Run unit tests + run: npm test + working-directory: evals + + diff: + name: "Compute changed suites" + runs-on: ubuntu-latest + outputs: + slugs: ${{ steps.compute.outputs.slugs }} + has_changes: ${{ steps.compute.outputs.has_changes }} + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: Compute changed suites + id: compute + run: | + if [[ "${{ inputs.run_all }}" == "true" ]]; then + # run_all overrides: list every suite + slugs="$(node -e 'const m=require("./evals/scripts/_manifest");process.stdout.write(JSON.stringify(m.SUITES.map(s=>s.suite)))')" + else + slugs="$(node evals/scripts/diff-changed-skills.js --json --verbose)" + fi + echo "slugs=${slugs}" >> "$GITHUB_OUTPUT" + if [[ "${slugs}" == "[]" ]]; then + echo "has_changes=false" >> "$GITHUB_OUTPUT" + else + echo "has_changes=true" >> "$GITHUB_OUTPUT" + fi + echo "Changed suites: ${slugs}" + + evaluate: + name: "Evaluate ${{ matrix.suite }}" + needs: [unit-test, diff] + if: needs.diff.outputs.has_changes == 'true' + runs-on: ubuntu-latest + strategy: + fail-fast: false + max-parallel: 3 + matrix: + suite: ${{ fromJson(needs.diff.outputs.slugs) }} + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: Setup Node.js + uses: actions/setup-node@v4 + with: + node-version: "22" + cache: "npm" + cache-dependency-path: evals/package-lock.json + + - name: Install eval dependencies + run: npm ci + working-directory: evals + + - name: Run eval suite + env: + ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }} + OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }} + AGENT_MODEL: ${{ vars.AGENT_MODEL || 'claude-sonnet-4-6' }} + RUBRIC_MODEL: ${{ vars.RUBRIC_MODEL || 'anthropic:messages:claude-haiku-4-5-20251001' }} + run: node scripts/aggregate.js --run --only=${{ matrix.suite }} + working-directory: evals + + - name: Upload suite results + uses: actions/upload-artifact@v4 + with: + name: results-${{ matrix.suite }} + path: evals/${{ matrix.suite }}/results.json + retention-days: 14 + + aggregate: + name: "Aggregate scores" + needs: [diff, evaluate] + if: needs.diff.outputs.has_changes == 'true' && always() && needs.evaluate.result != 'cancelled' + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + token: ${{ secrets.GITHUB_TOKEN }} + + - name: Setup Node.js + uses: actions/setup-node@v4 + with: + node-version: "22" + + - name: Install eval dependencies + run: npm ci + working-directory: evals + + - name: Download all suite results + uses: actions/download-artifact@v4 + with: + path: artifact-results + pattern: results-* + merge-multiple: false + + - name: Stage suite results into evals//results.json + run: | + set -e + shopt -s nullglob + for d in artifact-results/results-*; do + name=$(basename "$d" | sed 's/^results-//') + mkdir -p "evals/$name" + if [[ -f "$d/results.json" ]]; then + cp "$d/results.json" "evals/$name/results.json" + echo "Staged evals/$name/results.json" + fi + done + + - name: Save previous eval-scores.json for diff + run: | + if [[ -f eval-scores.json ]]; then + cp eval-scores.json /tmp/eval-scores-before.json + else + echo '{"schemaVersion":1,"updatedAt":null,"skills":{}}' > /tmp/eval-scores-before.json + fi + + - name: Aggregate + env: + SUITES_JSON: ${{ needs.diff.outputs.slugs }} + run: | + slugs=$(echo "$SUITES_JSON" | node -e 'let s="";process.stdin.on("data",c=>s+=c);process.stdin.on("end",()=>{const a=JSON.parse(s);process.stdout.write(a.join(","))})') + if [[ -z "$slugs" ]]; then + echo "No suites to aggregate" + exit 0 + fi + node scripts/aggregate.js --only="$slugs" + working-directory: evals + + - name: Render README badges + run: node evals/scripts/render-badges.js + + - name: PR comment with score diff + if: github.event_name == 'pull_request' + uses: actions/github-script@v7 + env: + BEFORE_PATH: /tmp/eval-scores-before.json + AFTER_PATH: ${{ github.workspace }}/eval-scores.json + with: + script: | + const fs = require('node:fs'); + const before = JSON.parse(fs.readFileSync(process.env.BEFORE_PATH, 'utf-8')); + const after = JSON.parse(fs.readFileSync(process.env.AFTER_PATH, 'utf-8')); + const lines = [ + '', + '## Skill eval results', + '', + '| Skill | Before | After | Δ |', + '|-------|-------:|------:|----:|', + ]; + const keys = new Set([ + ...Object.keys(before.skills || {}), + ...Object.keys(after.skills || {}), + ]); + for (const key of [...keys].sort()) { + const b = (before.skills || {})[key]; + const a = (after.skills || {})[key]; + if (!a) continue; + const beforeStr = b && b.score !== null ? `${b.score}/100 (${b.passed}/${b.total})` : '-'; + const afterStr = a.score !== null ? `${a.score}/100 (${a.passed}/${a.total})` : 'errored'; + const delta = (b && b.score !== null && a.score !== null) + ? (a.score - b.score === 0 ? 'no change' : (a.score - b.score > 0 ? `+${a.score - b.score}` : `${a.score - b.score}`)) + : 'new'; + lines.push(`| \`${key}\` | ${beforeStr} | ${afterStr} | ${delta} |`); + } + lines.push(''); + lines.push('_Only suites whose source actually changed since their last recorded score were re-run. Soft-failing while we stabilise the baseline._'); + const body = lines.join('\n'); + + const { data: comments } = await github.rest.issues.listComments({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.issue.number, + }); + const existing = comments.find((c) => c.body && c.body.startsWith('')); + if (existing) { + await github.rest.issues.updateComment({ + owner: context.repo.owner, + repo: context.repo.repo, + comment_id: existing.id, + body, + }); + } else { + await github.rest.issues.createComment({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.issue.number, + body, + }); + } + + - name: Commit refreshed scores and badges + if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' + run: | + if git diff --quiet eval-scores.json skills/; then + echo "No score or badge changes to commit" + exit 0 + fi + git config user.name 'github-actions[bot]' + git config user.email '41898282+github-actions[bot]@users.noreply.github.com' + git add eval-scores.json + git add skills/**/README.md + git commit -m "chore(evals): refresh eval-scores.json and README badges" + git push origin HEAD:${{ github.ref_name }} From 8760d0dac90e9a72d113a6c955cd0fd510683a5e Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 09:54:16 -0700 Subject: [PATCH 04/16] Update evals/shared/output-valid.js Co-authored-by: ari-launchdarkly --- evals/shared/output-valid.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/evals/shared/output-valid.js b/evals/shared/output-valid.js index 911818b..895a0b4 100644 --- a/evals/shared/output-valid.js +++ b/evals/shared/output-valid.js @@ -7,7 +7,7 @@ * confusing stack traces. */ module.exports = (output) => { - const isObj = output !== null && typeof output === "object"; + const isObj = output !== null && typeof output === "object" && !Array.isArray(output); return { pass: isObj, score: isObj ? 1 : 0, From f86a128e8027d4e9fc574bb4ed794fc779fb995f Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 10:52:32 -0700 Subject: [PATCH 05/16] npm ci calls need --legacy-peer-deps --- .github/workflows/eval-skills.yml | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/.github/workflows/eval-skills.yml b/.github/workflows/eval-skills.yml index 3293ab2..cad8aec 100644 --- a/.github/workflows/eval-skills.yml +++ b/.github/workflows/eval-skills.yml @@ -56,7 +56,7 @@ jobs: cache-dependency-path: evals/package-lock.json - name: Install eval dependencies - run: npm ci + run: npm ci --legacy-peer-deps working-directory: evals - name: Run unit tests @@ -116,7 +116,7 @@ jobs: cache-dependency-path: evals/package-lock.json - name: Install eval dependencies - run: npm ci + run: npm ci --legacy-peer-deps working-directory: evals - name: Run eval suite @@ -151,9 +151,11 @@ jobs: uses: actions/setup-node@v4 with: node-version: "22" + cache: "npm" + cache-dependency-path: evals/package-lock.json - name: Install eval dependencies - run: npm ci + run: npm ci --legacy-peer-deps working-directory: evals - name: Download all suite results From f5ffd15be88b607d2e8bef80bf67ec7a50741a4b Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 11:16:49 -0700 Subject: [PATCH 06/16] fix .env detection --- evals/scripts/aggregate.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/evals/scripts/aggregate.js b/evals/scripts/aggregate.js index 42e96ab..5d260d3 100644 --- a/evals/scripts/aggregate.js +++ b/evals/scripts/aggregate.js @@ -67,7 +67,7 @@ function runSuite(suite) { "eval", "-c", path.join(EVALS_DIR, "shared", "defaults.yaml"), "-c", path.join(EVALS_DIR, suite.suite, "promptfooconfig.yaml"), - "--env-file", path.join(EVALS_DIR, ".env"), + ...(fs.existsSync(path.join(EVALS_DIR, ".env")) ? ["--env-file", path.join(EVALS_DIR, ".env")] : []), "--no-cache", "-o", outFile, ], From 3ecda5df7e2a8d1dd7d75c68cf759113eb5e2539 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 11:32:17 -0700 Subject: [PATCH 07/16] fail CI only if score drops below 75% --- .github/workflows/eval-skills.yml | 1 + eval-scores.json | 20 ++++++++++---------- evals/scripts/aggregate.js | 8 +++++++- 3 files changed, 18 insertions(+), 11 deletions(-) diff --git a/.github/workflows/eval-skills.yml b/.github/workflows/eval-skills.yml index cad8aec..01be86f 100644 --- a/.github/workflows/eval-skills.yml +++ b/.github/workflows/eval-skills.yml @@ -97,6 +97,7 @@ jobs: needs: [unit-test, diff] if: needs.diff.outputs.has_changes == 'true' runs-on: ubuntu-latest + continue-on-error: true strategy: fail-fast: false max-parallel: 3 diff --git a/eval-scores.json b/eval-scores.json index 170d8d4..c8b08f6 100644 --- a/eval-scores.json +++ b/eval-scores.json @@ -1,34 +1,34 @@ { "schemaVersion": 1, - "updatedAt": "2026-05-19T22:29:45.928Z", + "updatedAt": "2026-05-20T18:26:38.373Z", "skills": { "ai-configs/aiconfig-create": { - "score": 100, - "passed": 4, + "score": 75, + "passed": 3, "total": 4, "status": "passing", - "lastCommit": "fc69376", - "lastRun": "2026-05-19T22:29:45.923Z", + "lastCommit": "f5ffd15", + "lastRun": "2026-05-20T18:26:38.372Z", "perTest": [ { "description": "Create an AI Config for my customer support bot. It uses LangGraph and needs per", "pass": true, - "score": 1 + "score": 0 }, { "description": "I need an AI Config for our blog summarizer. We call the OpenAI API directly wit", "pass": true, - "score": 1 + "score": 0 }, { "description": "Create a new AI Config for our analytics agent. Project key is \"data-platform\".\n", "pass": true, - "score": 1 + "score": 0 }, { "description": "Create an AI Config called \"email-assistant\" for composing emails. Project is \"c", - "pass": true, - "score": 0.8333333333333334 + "pass": false, + "score": 0 } ] }, diff --git a/evals/scripts/aggregate.js b/evals/scripts/aggregate.js index 5d260d3..0223708 100644 --- a/evals/scripts/aggregate.js +++ b/evals/scripts/aggregate.js @@ -159,7 +159,13 @@ function main() { fs.writeFileSync(SCORES_PATH, JSON.stringify(output, null, 2) + "\n"); console.log(`\nWrote ${SCORES_PATH}`); - if (anyError) process.exit(1); + const belowThreshold = suites + .filter((suite) => skills[suite.skillKey] && skills[suite.skillKey].score < 75) + .map((suite) => suite.skillKey); + if (belowThreshold.length > 0) { + console.error(`\naggregate.js: suites below 75% threshold: ${belowThreshold.join(", ")}`); + } + if (anyError || belowThreshold.length > 0) process.exit(1); } main(); From 8441bf2dd32c8eb7b6f574c52215e5f41a9a1ebd Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 11:49:05 -0700 Subject: [PATCH 08/16] bug in suite eval --- .github/workflows/eval-skills.yml | 1 + evals/scripts/aggregate.js | 4 +++- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/.github/workflows/eval-skills.yml b/.github/workflows/eval-skills.yml index 01be86f..11d40a2 100644 --- a/.github/workflows/eval-skills.yml +++ b/.github/workflows/eval-skills.yml @@ -130,6 +130,7 @@ jobs: working-directory: evals - name: Upload suite results + if: always() uses: actions/upload-artifact@v4 with: name: results-${{ matrix.suite }} diff --git a/evals/scripts/aggregate.js b/evals/scripts/aggregate.js index 0223708..7218375 100644 --- a/evals/scripts/aggregate.js +++ b/evals/scripts/aggregate.js @@ -74,7 +74,9 @@ function runSuite(suite) { { cwd: EVALS_DIR, stdio: "inherit", env: { ...process.env } }, ); - if (result.status !== 0) { + // promptfoo exits 100 when tests ran but some failed — that's a valid run, + // results.json is still written. Treat any other non-zero as a hard failure. + if (result.status !== 0 && result.status !== 100) { console.error(`✗ Suite ${suite.suite} exited with status ${result.status}`); return false; } From 587a9b2df5d835fd585cddc26bcd1260b14601d6 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 12:20:09 -0700 Subject: [PATCH 09/16] fix mocking issue --- eval-scores.json | 52 ++++++++++++++++----------------- evals/mocks/tool-responses.json | 24 +-------------- 2 files changed, 27 insertions(+), 49 deletions(-) diff --git a/eval-scores.json b/eval-scores.json index c8b08f6..e250665 100644 --- a/eval-scores.json +++ b/eval-scores.json @@ -1,34 +1,34 @@ { "schemaVersion": 1, - "updatedAt": "2026-05-20T18:26:38.373Z", + "updatedAt": "2026-05-20T19:16:00.938Z", "skills": { "ai-configs/aiconfig-create": { - "score": 75, - "passed": 3, + "score": 100, + "passed": 4, "total": 4, "status": "passing", - "lastCommit": "f5ffd15", - "lastRun": "2026-05-20T18:26:38.372Z", + "lastCommit": "8441bf2", + "lastRun": "2026-05-20T19:16:00.930Z", "perTest": [ { "description": "Create an AI Config for my customer support bot. It uses LangGraph and needs per", "pass": true, - "score": 0 + "score": 1 }, { "description": "I need an AI Config for our blog summarizer. We call the OpenAI API directly wit", "pass": true, - "score": 0 + "score": 1 }, { "description": "Create a new AI Config for our analytics agent. Project key is \"data-platform\".\n", "pass": true, - "score": 0 + "score": 1 }, { "description": "Create an AI Config called \"email-assistant\" for composing emails. Project is \"c", - "pass": false, - "score": 0 + "pass": true, + "score": 0.8333333333333334 } ] }, @@ -37,8 +37,8 @@ "passed": 4, "total": 5, "status": "passing", - "lastCommit": "fc69376", - "lastRun": "2026-05-19T22:29:45.925Z", + "lastCommit": "8441bf2", + "lastRun": "2026-05-20T19:16:00.934Z", "perTest": [ { "description": "I need to switch the model on the default variation of our support-chatbot confi", @@ -58,7 +58,7 @@ { "description": "The old code-reviewer config in project \"dev-tools\" is completely obsolete. We s", "pass": false, - "score": 0.4166666666666667 + "score": 0.5 }, { "description": "Update the temperature parameter on the default variation of our support-chatbot", @@ -72,8 +72,8 @@ "passed": 3, "total": 4, "status": "passing", - "lastCommit": "fc69376", - "lastRun": "2026-05-19T22:29:45.926Z", + "lastCommit": "8441bf2", + "lastRun": "2026-05-20T19:16:00.936Z", "perTest": [ { "description": "I need to give our support-chatbot AI Config the ability to search our knowledge", @@ -88,7 +88,7 @@ { "description": "I want to add a tool to our support-chatbot for looking up customer orders. Befo", "pass": false, - "score": 0.25 + "score": 0.3125 }, { "description": "Attach a new \"fetch-weather\" tool to the travel-assistant config's default varia", @@ -102,8 +102,8 @@ "passed": 4, "total": 5, "status": "passing", - "lastCommit": "fc69376", - "lastRun": "2026-05-19T22:29:45.927Z", + "lastCommit": "8441bf2", + "lastRun": "2026-05-20T19:16:00.937Z", "perTest": [ { "description": "I want to test if gpt-4o-mini can handle our support chatbot as well as gpt-4o b", @@ -123,7 +123,7 @@ { "description": "I want to replace the default variation of support-chatbot with a new Claude-bas", "pass": false, - "score": 0.4166666666666667 + "score": 0.3333333333333333 }, { "description": "Clone the default variation of content-writer to test gpt-4o-mini. Project key i", @@ -133,12 +133,12 @@ ] }, "feature-flags/launchdarkly-flag-create": { - "score": 67, - "passed": 2, + "score": 100, + "passed": 3, "total": 3, - "status": "failing", - "lastCommit": "fc69376", - "lastRun": "2026-05-19T22:29:45.928Z", + "status": "passing", + "lastCommit": "8441bf2", + "lastRun": "2026-05-20T19:16:00.938Z", "perTest": [ { "description": "I need to wrap our new checkout flow in a feature flag so we can roll it out gra", @@ -147,8 +147,8 @@ }, { "description": "Add a feature flag for our new dark mode feature. Project key is \"web-app\".\n", - "pass": false, - "score": 0.375 + "pass": true, + "score": 1 }, { "description": "Create a feature flag for our A/B test of the new onboarding flow. Project key i", diff --git a/evals/mocks/tool-responses.json b/evals/mocks/tool-responses.json index 8bdf8ab..8c1aa92 100644 --- a/evals/mocks/tool-responses.json +++ b/evals/mocks/tool-responses.json @@ -23,28 +23,6 @@ } ] }, - { - "key": "dark-mode", - "name": "Dark Mode", - "kind": "boolean", - "description": "Dark mode theme toggle", - "temporary": true, - "tags": [ - "frontend", - "ui" - ], - "on": false, - "variations": [ - { - "value": true, - "name": "On" - }, - { - "value": false, - "name": "Off" - } - ] - }, { "key": "search-v2", "name": "Search V2", @@ -68,7 +46,7 @@ ] } ], - "totalCount": 3, + "totalCount": 2, "pageInfo": { "limit": 20, "offset": 0 From 29267353b4943ccc0192285586f8215aaebf7dc0 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 12:38:55 -0700 Subject: [PATCH 10/16] API key comment on .env.example --- evals/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/evals/.env.example b/evals/.env.example index dbd2857..95e682f 100644 --- a/evals/.env.example +++ b/evals/.env.example @@ -3,7 +3,7 @@ # REQUIRED: API key for both the agent (system under test) and the rubric # grader unless you switch the grader to a non-Anthropic provider via # RUBRIC_MODEL below. -# Get yours at https://console.anthropic.com +# Request access via #ask-app-eng to get an API key. ANTHROPIC_API_KEY= # OPTIONAL: the system-under-test model. Stays on Claude because that's what From 234481e822872c56955adb9d492763da3869074a Mon Sep 17 00:00:00 2001 From: ari-launchdarkly Date: Wed, 20 May 2026 14:22:44 -0700 Subject: [PATCH 11/16] Add eval-gate job for required status checks (#66) Add eval-gate job for required status check and remove continue-on-error from evaluate --- .github/workflows/eval-skills.yml | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/.github/workflows/eval-skills.yml b/.github/workflows/eval-skills.yml index 11d40a2..1c7ca77 100644 --- a/.github/workflows/eval-skills.yml +++ b/.github/workflows/eval-skills.yml @@ -97,7 +97,6 @@ jobs: needs: [unit-test, diff] if: needs.diff.outputs.has_changes == 'true' runs-on: ubuntu-latest - continue-on-error: true strategy: fail-fast: false max-parallel: 3 @@ -275,3 +274,22 @@ jobs: git add skills/**/README.md git commit -m "chore(evals): refresh eval-scores.json and README badges" git push origin HEAD:${{ github.ref_name }} + + eval-gate: + name: "Evaluate gate" + needs: [diff, evaluate] + if: always() + runs-on: ubuntu-latest + steps: + - name: Check evaluate results + run: | + if [[ "${{ needs.diff.outputs.has_changes }}" != "true" ]]; then + echo "No suites changed — gate passes" + exit 0 + fi + if [[ "${{ needs.evaluate.result }}" == "success" ]]; then + echo "All evaluate jobs passed" + exit 0 + fi + echo "One or more evaluate jobs failed (result: ${{ needs.evaluate.result }})" + exit 1 From 7665ed276e6ba7b55bc95e75a67e3067360717c9 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Wed, 20 May 2026 15:40:57 -0700 Subject: [PATCH 12/16] address Devin feedback --- CONTRIBUTING.md | 4 ++-- evals/providers/_mock.js | 12 ++++++++++++ evals/scripts/run-models.js | 2 +- 3 files changed, 15 insertions(+), 3 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 9deb428..5fdebce 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -40,10 +40,10 @@ The metrics skills have a Promptfoo suite under `tests/`. Run it before merging ```bash export ANTHROPIC_API_KEY=sk-ant-... -npm run test:llm-evals +npm run eval:all ``` -Run from the repository root, or from `tests/` with `npm run test:llm-evals` (same as `npm run eval`). For a single skill, use `npm run eval:create`, `eval:choose`, or `eval:instrument` inside `tests/`. +Run from the repository root. To run a single suite, use `npm run eval:` (e.g., `eval:aiconfig-create`). View results with `npm run eval:view`. ## Documentation diff --git a/evals/providers/_mock.js b/evals/providers/_mock.js index 9eef7ce..188aab9 100644 --- a/evals/providers/_mock.js +++ b/evals/providers/_mock.js @@ -272,6 +272,18 @@ function renderMockResponse(template, input, toolName, state) { return { configKey: input.configKey, variation }; } + if (toolName === "update-ai-config") { + const cfg = state.configs[input.key || input.configKey]; + if (cfg) { + const CONFIG_FIELDS = ["name", "description", "tags", "archived"]; + for (const k of CONFIG_FIELDS) { + if (input[k] !== undefined) cfg[k] = input[k]; + } + return { ...cfg }; + } + return walk(template, replacements); + } + if (toolName === "update-ai-config-variation") { const cfg = state.configs[input.configKey]; if (cfg) { diff --git a/evals/scripts/run-models.js b/evals/scripts/run-models.js index ad4804c..2e5b5c8 100644 --- a/evals/scripts/run-models.js +++ b/evals/scripts/run-models.js @@ -115,7 +115,7 @@ function runSuiteWithModel(suite, modelId, alias) { console.error(`[run-models] launch error: ${result.error.message}`); return false; } - if (result.status !== 0) { + if (result.status !== 0 && result.status !== 100) { console.error(`[run-models] suite ${suite.suite} exited with status ${result.status}`); return false; } From 6280c336a3799b00e978a3b5c59f78a1662bfab7 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Thu, 21 May 2026 11:34:54 -0700 Subject: [PATCH 13/16] more devin feedback --- .github/workflows/eval-skills.yml | 5 +++-- evals/mocks/tool-responses.json | 2 +- evals/providers/_mock.js | 2 +- 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/.github/workflows/eval-skills.yml b/.github/workflows/eval-skills.yml index 1c7ca77..e8d3a5e 100644 --- a/.github/workflows/eval-skills.yml +++ b/.github/workflows/eval-skills.yml @@ -200,10 +200,11 @@ jobs: working-directory: evals - name: Render README badges + if: always() run: node evals/scripts/render-badges.js - name: PR comment with score diff - if: github.event_name == 'pull_request' + if: always() && github.event_name == 'pull_request' uses: actions/github-script@v7 env: BEFORE_PATH: /tmp/eval-scores-before.json @@ -262,7 +263,7 @@ jobs: } - name: Commit refreshed scores and badges - if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' + if: always() && (github.event_name == 'schedule' || github.event_name == 'workflow_dispatch') run: | if git diff --quiet eval-scores.json skills/; then echo "No score or badge changes to commit" diff --git a/evals/mocks/tool-responses.json b/evals/mocks/tool-responses.json index 8c1aa92..75817de 100644 --- a/evals/mocks/tool-responses.json +++ b/evals/mocks/tool-responses.json @@ -314,7 +314,7 @@ "name": "{{configName}}", "description": "", "tags": [], - "archived": "{{archived}}" + "archived": false }, "delete-ai-config": { "deleted": true, diff --git a/evals/providers/_mock.js b/evals/providers/_mock.js index 188aab9..0750701 100644 --- a/evals/providers/_mock.js +++ b/evals/providers/_mock.js @@ -28,7 +28,7 @@ function buildReplacements(input) { configKey: safe.configKey || safe.key || "unknown-config", configName: safe.configName || safe.name || "Unknown Config", variationKey: - safe.variationKey || safe.sourceVariationKey || safe.key || "default", + safe.variationKey || safe.key || safe.sourceVariationKey || "default", variationName: safe.variationName || safe.name || "Default", toolKey: safe.toolKey || safe.key || "unknown-tool", modelConfigKey: safe.modelConfigKey || "OpenAI.gpt-4o", From fde1b2bed9f4688c6e34d792e04efc8e22ab7adf Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Thu, 21 May 2026 11:50:05 -0700 Subject: [PATCH 14/16] more devin feedback --- evals/providers/_mock.js | 30 ++++++++++++++ evals/tests/mock.test.js | 85 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 115 insertions(+) diff --git a/evals/providers/_mock.js b/evals/providers/_mock.js index 0750701..6defcb7 100644 --- a/evals/providers/_mock.js +++ b/evals/providers/_mock.js @@ -303,6 +303,36 @@ function renderMockResponse(template, input, toolName, state) { return walk(template, replacements); } + if (toolName === "clone-ai-config-variation") { + const configKey = input.configKey; + if (!state.configs[configKey] && SEED_CONFIGS[configKey]) { + state.configs[configKey] = JSON.parse(JSON.stringify(SEED_CONFIGS[configKey])); + } + const cfg = state.configs[configKey]; + if (cfg) { + const sourceVariation = (cfg.variations || []).find( + (v) => v.key === input.sourceVariationKey, + ); + if (sourceVariation) { + const newVariation = { + ...sourceVariation, + key: input.key, + name: input.name !== undefined ? input.name : sourceVariation.name, + ...(input.modelConfigKey !== undefined ? { modelConfigKey: input.modelConfigKey } : {}), + ...(input.modelName !== undefined ? { modelName: input.modelName } : {}), + ...(input.instructions !== undefined ? { instructions: input.instructions } : {}), + ...(input.messages !== undefined ? { messages: input.messages } : {}), + ...(input.parameters !== undefined ? { parameters: input.parameters } : {}), + ...(input.tools !== undefined ? { tools: input.tools } : {}), + status: "active", + }; + cfg.variations = [...(cfg.variations || []), newVariation]; + return { configKey, source: sourceVariation, created: newVariation }; + } + } + return walk(template, replacements); + } + if (toolName === "create-flag" || toolName === "create-feature-flag") { const flag = walk(template, replacements); state.flags[input.key || input.flagKey] = flag; diff --git a/evals/tests/mock.test.js b/evals/tests/mock.test.js index 85274e7..a82d7a2 100644 --- a/evals/tests/mock.test.js +++ b/evals/tests/mock.test.js @@ -258,6 +258,91 @@ test("get-ai-config-health falls back to template for unknown key", () => { assert.equal(health.key, "unknown-config"); }); +// --------------------------------------------------------------------------- +// clone-ai-config-variation +// --------------------------------------------------------------------------- + +test("clone-ai-config-variation appends cloned variation to state", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "my-bot", name: "My Bot", mode: "agent", + variationKey: "default", variationName: "Default", + modelConfigKey: "OpenAI.gpt-4o", modelName: "gpt-4o", + instructions: "Original instructions.", + }, "setup-ai-config", state); + + const result = renderMockResponse(TEMPLATES["clone-ai-config-variation"], { + configKey: "my-bot", + sourceVariationKey: "default", + key: "cost-test", + name: "Cost Test", + modelConfigKey: "OpenAI.gpt-4o-mini", + modelName: "gpt-4o-mini", + }, "clone-ai-config-variation", state); + + assert.equal(result.created.key, "cost-test"); + assert.equal(result.created.modelConfigKey, "OpenAI.gpt-4o-mini"); + assert.equal(result.source.key, "default"); + assert.equal(state.configs["my-bot"].variations.length, 2); + assert.equal(state.configs["my-bot"].variations[1].key, "cost-test"); +}); + +test("clone-ai-config-variation reflects in subsequent get-ai-config", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["setup-ai-config"], { + key: "bot", name: "Bot", mode: "agent", + variationKey: "default", variationName: "Default", + modelConfigKey: "OpenAI.gpt-4o", modelName: "gpt-4o", + instructions: "Help.", + }, "setup-ai-config", state); + + renderMockResponse(TEMPLATES["clone-ai-config-variation"], { + configKey: "bot", + sourceVariationKey: "default", + key: "new-var", + name: "New Variation", + }, "clone-ai-config-variation", state); + + const cfg = renderMockResponse(TEMPLATES["get-ai-config"], { + configKey: "bot", + }, "get-ai-config", state); + + assert.equal(cfg.variations.length, 2); + assert.ok(cfg.variations.find((v) => v.key === "new-var"), "cloned variation should appear in get-ai-config"); +}); + +test("clone-ai-config-variation works with SEED_CONFIGS source", () => { + const state = createMockState(); + const result = renderMockResponse(TEMPLATES["clone-ai-config-variation"], { + configKey: "support-chatbot", + sourceVariationKey: "default", + key: "experimental", + name: "Experimental", + }, "clone-ai-config-variation", state); + + assert.equal(result.created.key, "experimental"); + assert.equal(result.source.key, "default"); + assert.ok(state.configs["support-chatbot"], "seed config should be loaded into state"); + assert.equal(state.configs["support-chatbot"].variations.length, 2); +}); + +test("clone-ai-config-variation falls back to template when source variation not found", () => { + const state = createMockState(); + renderMockResponse(TEMPLATES["create-ai-config"], { + key: "my-config", name: "My Config", mode: "agent", + }, "create-ai-config", state); + + // source variation doesn't exist — should fall back to template render, not throw + assert.doesNotThrow(() => + renderMockResponse(TEMPLATES["clone-ai-config-variation"], { + configKey: "my-config", + sourceVariationKey: "nonexistent", + key: "new-var", + name: "New", + }, "clone-ai-config-variation", state) + ); +}); + // --------------------------------------------------------------------------- // create-flag / get-flag (flag state) // --------------------------------------------------------------------------- From a3452ece019aaf523673f9d100cb6d9ea275bb78 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Thu, 21 May 2026 12:06:59 -0700 Subject: [PATCH 15/16] Update CONTRIBUTING.md Co-authored-by: devin-ai-integration[bot] <158243242+devin-ai-integration[bot]@users.noreply.github.com> --- CONTRIBUTING.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 5fdebce..d32d2e7 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -43,7 +43,8 @@ export ANTHROPIC_API_KEY=sk-ant-... npm run eval:all ``` -Run from the repository root. To run a single suite, use `npm run eval:` (e.g., `eval:aiconfig-create`). View results with `npm run eval:view`. +Run from the repository root. To run a single suite, `cd evals` and use `npm run eval:` (e.g., `eval:aiconfig-create`). View results with `npm run eval:view`. + ## Documentation From 1ee25586cb25abe3986557861e811ecfc928e7b7 Mon Sep 17 00:00:00 2001 From: Dakota Sanchez Date: Thu, 21 May 2026 12:17:25 -0700 Subject: [PATCH 16/16] mcp-configure skill update for /fm MCP deprecation --- skills/onboarding/mcp-configure/SKILL.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/skills/onboarding/mcp-configure/SKILL.md b/skills/onboarding/mcp-configure/SKILL.md index 803eb37..ab5450e 100644 --- a/skills/onboarding/mcp-configure/SKILL.md +++ b/skills/onboarding/mcp-configure/SKILL.md @@ -128,17 +128,17 @@ Then ask how they want to add the token to the MCP config: ## Edge Cases - **User already has MCP configured:** Verify by checking for existing LD MCP entries in the config. - - `mcp/launchdarkly` or `mcp/fm` → working, skip configuration (both point to the unified server) - - `mcp/aiconfigs` → deprecated, ask before migrating: - + - `mcp/launchdarkly` → working, skip configuration + - `mcp/fm` or `mcp/aiconfigs` → deprecated, ask before migrating: + **D-MIGRATE -- BLOCKING:** Call your structured question tool now. - - question: "I see you have the old AgentControl MCP server configured (`mcp/aiconfigs`). That endpoint is deprecated — the unified server at `mcp/launchdarkly` now handles both feature management and AgentControl. Want me to update your config?" + - question: "I see you have a deprecated MCP server configured (`mcp/fm` and/or `mcp/aiconfigs`). Those endpoints are deprecated — the unified server at `mcp/launchdarkly` now handles both feature management and AgentControl. Want me to update your config?" - options: - "Yes, update my config to use the unified server" - "No, leave it as is for now" - STOP. Do not modify the MCP config before the user selects an option. - - If they agree, remove the `mcp/aiconfigs` entry and ensure the unified `mcp/launchdarkly` (or `mcp/fm`) config is present. See [MCP Config Templates](references/mcp-config-templates.md). If they decline, note the deprecation and continue. + + If they agree, remove the deprecated entries and ensure the unified `mcp/launchdarkly` config is present. See [MCP Config Templates](references/mcp-config-templates.md). If they decline, note the deprecation and continue. - **User has the old npx-based local server:** Migrate them. Remove the old `npx @launchdarkly/mcp-server` entry and any `LD_ACCESS_TOKEN` env vars. Replace with the hosted server config. See [MCP Config Templates — Migration](references/mcp-config-templates.md#migrating-from-old-configurations). - **Federal or EU instances:** The hosted MCP server is not available for federal or EU environments. Use [local MCP server docs](https://launchdarkly.com/docs/home/getting-started/mcp-local) and the **Local server via `npx`** section in [MCP Config Templates](references/mcp-config-templates.md). Follow the [Local MCP: Access Token Setup](#local-mcp-access-token-setup) flow for token handling. - **Agent not in known list:** Provide the generic pattern: the user needs to add an MCP server entry pointing to `https://mcp.launchdarkly.com/mcp/launchdarkly` using whatever format their agent expects.