From 463806bbd99719ce595a02f39310e379a2e32485 Mon Sep 17 00:00:00 2001 From: "sentry-junior[bot]" <264270552+sentry-junior[bot]@users.noreply.github.com> Date: Sat, 7 Nov 2026 05:51:58 +0000 Subject: [PATCH] chore(evals): Switch Sonnet defaults to GPT 6 Luna Move every eval suite, scenario YAML, judge, and verification default from Claude Sonnet 4.6 to openai/gpt-6-luna, and point the CI eval default at openrouter/openai/gpt-6-luna. Bump Pi to 0.87.1, the first release whose model catalog includes GPT 6 Luna. Co-Authored-By: David Cramer <23610+dcramer@users.noreply.github.com> --- .github/workflows/evals.yml | 2 +- packages/evals/README.md | 24 +-- packages/evals/eval-bug-detection.yaml | 2 +- packages/evals/eval-precision.yaml | 2 +- packages/evals/eval-security-scanning.yaml | 2 +- packages/evals/src/code-review.eval.ts | 2 +- packages/evals/src/harness.test.ts | 6 +- packages/evals/src/index.test.ts | 10 +- packages/evals/src/integrity-review.eval.ts | 2 +- packages/evals/src/judge.test.ts | 12 +- packages/evals/src/judge.ts | 2 +- packages/evals/src/provider.test.ts | 32 +-- packages/evals/src/provider.ts | 19 +- packages/evals/src/runner.test.ts | 16 +- packages/evals/src/security-review.eval.ts | 2 +- packages/evals/src/types.ts | 4 +- packages/evals/src/verify.eval.ts | 2 +- packages/evals/src/verify.test.ts | 2 +- packages/evals/src/verify.ts | 2 +- packages/warden/package.json | 4 +- packages/warden/src/cli/commands/build.ts | 2 +- packages/warden/src/cli/main.ts | 2 +- pnpm-lock.yaml | 213 ++++++-------------- 23 files changed, 137 insertions(+), 229 deletions(-) diff --git a/.github/workflows/evals.yml b/.github/workflows/evals.yml index 4cac0e619..6d74fe9ab 100644 --- a/.github/workflows/evals.yml +++ b/.github/workflows/evals.yml @@ -86,7 +86,7 @@ jobs: env: # Pi provider/model selector for every eval and the judge. Override with the # WARDEN_EVAL_MODEL repo variable; add the matching WARDEN__API_KEY below. - WARDEN_EVAL_MODEL: ${{ vars.WARDEN_EVAL_MODEL || 'openrouter/anthropic/claude-sonnet-4.6' }} + WARDEN_EVAL_MODEL: ${{ vars.WARDEN_EVAL_MODEL || 'openrouter/openai/gpt-6-luna' }} WARDEN_EVAL_JUDGE_MODEL: ${{ vars.WARDEN_EVAL_JUDGE_MODEL }} WARDEN_OPENROUTER_API_KEY: ${{ secrets.WARDEN_OPENROUTER_API_KEY }} WARDEN_ANTHROPIC_API_KEY: ${{ secrets.WARDEN_ANTHROPIC_API_KEY }} diff --git a/packages/evals/README.md b/packages/evals/README.md index 8250c342d..6c28c9863 100644 --- a/packages/evals/README.md +++ b/packages/evals/README.md @@ -32,7 +32,7 @@ name, such as `packages/evals/code-review/` or `packages/evals/security-review/` ```yaml skill: skills/bug-detection.md runtime: pi -model: anthropic/claude-sonnet-4-6 +model: openai/gpt-6-luna evals: - name: null-property-access @@ -121,7 +121,7 @@ Eval test names are formatted as: ``` The suite chooses runtime and model. The current full-pipeline suites run Pi -with `anthropic/claude-sonnet-4-6`; future suites can matrix the same fixtures +with `openai/gpt-6-luna`; future suites can matrix the same fixtures over multiple runtimes or models without changing case identity. The Vitest entrypoints are intentionally split by eval layer: @@ -139,8 +139,8 @@ The Vitest entrypoints are intentionally split by eval layer: | Field | Required | Description | |-------|----------|-------------| | `skill` | Yes | Path to test skill, relative to `packages/evals/` | -| `runtime` | No | Default runtime for all evals: `claude` or `pi` (default: `claude`) | -| `model` | No | Default model for all evals (default: `claude-sonnet-4-6`; Pi models must use provider/model format, e.g. `anthropic/claude-sonnet-4-6`) | +| `runtime` | No | Default runtime for all evals: `claude` or `pi` (default: `pi`) | +| `model` | No | Default model for all evals (default: `openai/gpt-6-luna`; Pi models must use provider/model format) | | `evals` | Yes | List of eval scenarios (at least one) | ### Per-eval fields @@ -198,11 +198,11 @@ positive. # through its dist/ entry point pnpm build -# Run all evals with the checked-in Anthropic models -WARDEN_ANTHROPIC_API_KEY=sk-ant-... pnpm evals +# Run all evals with the checked-in OpenAI models +WARDEN_OPENAI_API_KEY=sk-... pnpm evals # Run all evals through another provider -WARDEN_EVAL_MODEL=openrouter/anthropic/claude-sonnet-4.6 \ +WARDEN_EVAL_MODEL=openrouter/openai/gpt-6-luna \ WARDEN_OPENROUTER_API_KEY=sk-or-... pnpm evals # Run evals for a specific skill @@ -228,9 +228,9 @@ pnpm evals:scaffold https://github.com/getsentry/sentry/pull/12345 ``` Evals make real API calls. Suites choose the runtime and model; the checked-in -suites run Pi with `anthropic/claude-sonnet-4-6`, and the judge uses the same -model. With only that default, evals are skipped unless `ANTHROPIC_API_KEY` or -`WARDEN_ANTHROPIC_API_KEY` is set. +suites run Pi with `openai/gpt-6-luna`, and the judge uses the same +model. With only that default, evals are skipped unless `OPENAI_API_KEY` or +`WARDEN_OPENAI_API_KEY` is set. To run against any other provider, set: @@ -249,7 +249,7 @@ CI runs evals when eval files or harness code change on a PR, when changes land on `main`, or when a maintainer adds the `run-evals` label to a same-repository PR. Fork PRs do not receive eval secrets. -CI defaults `WARDEN_EVAL_MODEL` to `openrouter/anthropic/claude-sonnet-4.6` +CI defaults `WARDEN_EVAL_MODEL` to `openrouter/openai/gpt-6-luna` with `WARDEN_OPENROUTER_API_KEY`. Set the `WARDEN_EVAL_MODEL` (and optionally `WARDEN_EVAL_JUDGE_MODEL`) repository variable to switch providers, and add the matching `WARDEN__API_KEY` secret to the workflow env. @@ -350,6 +350,6 @@ them in CLI output. Review that list before committing the eval. 4. **Context**: Build `EventContext` from real `git diff main...eval` 5. **Execution**: Run the skill via `runSkill()` with the real SDK pipeline; the agent operates in the temp repo with Read/Grep tools -6. **Judgment**: An LLM judge (Sonnet) evaluates findings against assertions +6. **Judgment**: An LLM judge (GPT 6 Luna by default) evaluates findings against assertions 7. **Verdict**: Pass if all required `should_find` are met and no `should_not_find` are violated diff --git a/packages/evals/eval-bug-detection.yaml b/packages/evals/eval-bug-detection.yaml index 7726618de..c582f0dca 100644 --- a/packages/evals/eval-bug-detection.yaml +++ b/packages/evals/eval-bug-detection.yaml @@ -1,6 +1,6 @@ skill: skills/bug-detection.md runtime: pi -model: anthropic/claude-sonnet-4-6 +model: openai/gpt-6-luna evals: - name: null-property-access diff --git a/packages/evals/eval-precision.yaml b/packages/evals/eval-precision.yaml index 5099d08de..46086b091 100644 --- a/packages/evals/eval-precision.yaml +++ b/packages/evals/eval-precision.yaml @@ -1,6 +1,6 @@ skill: skills/precision.md runtime: pi -model: anthropic/claude-sonnet-4-6 +model: openai/gpt-6-luna evals: - name: ignores-style-issues diff --git a/packages/evals/eval-security-scanning.yaml b/packages/evals/eval-security-scanning.yaml index 2f8df994e..ffcb9872c 100644 --- a/packages/evals/eval-security-scanning.yaml +++ b/packages/evals/eval-security-scanning.yaml @@ -1,6 +1,6 @@ skill: skills/security-scanning.md runtime: pi -model: anthropic/claude-sonnet-4-6 +model: openai/gpt-6-luna evals: - name: sql-injection diff --git a/packages/evals/src/code-review.eval.ts b/packages/evals/src/code-review.eval.ts index 9b19539fb..862164cc6 100644 --- a/packages/evals/src/code-review.eval.ts +++ b/packages/evals/src/code-review.eval.ts @@ -14,7 +14,7 @@ const evals = discoverEvalScenarios({ category: 'code-review', skill: '../warden/src/builtin-skills/code-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', }); const CODE_REVIEW_RUN_TIMEOUT_MS = 120_000; const CODE_REVIEW_EVAL_TIMEOUT_MS = CODE_REVIEW_RUN_TIMEOUT_MS + 60_000; diff --git a/packages/evals/src/harness.test.ts b/packages/evals/src/harness.test.ts index 820015d29..f741fa70d 100644 --- a/packages/evals/src/harness.test.ts +++ b/packages/evals/src/harness.test.ts @@ -101,7 +101,7 @@ describe('createWardenEvalJudge', () => { usage: emptyUsage(), }); - const judge = createWardenEvalJudge({ apiKey: 'test-key', model: 'anthropic/claude-sonnet-4-6' }); + const judge = createWardenEvalJudge({ apiKey: 'test-key', model: 'openai/gpt-6-luna' }); const result = await judge.assess(makeJudgeContext(meta, findings)); expect(result.score).toBe(1); @@ -122,7 +122,7 @@ describe('createWardenEvalJudge', () => { usage: emptyUsage(), }); - const judge = createWardenEvalJudge({ apiKey: 'test-key', model: 'anthropic/claude-sonnet-4-6' }); + const judge = createWardenEvalJudge({ apiKey: 'test-key', model: 'openai/gpt-6-luna' }); const result = await judge.assess(makeJudgeContext(meta, [makeFinding()])); expect(result.score).toBe(0); @@ -149,7 +149,7 @@ describe('createWardenEvalJudge', () => { error: 'No JSON found in judge response', }); - const judge = createWardenEvalJudge({ apiKey: 'test-key', model: 'anthropic/claude-sonnet-4-6' }); + const judge = createWardenEvalJudge({ apiKey: 'test-key', model: 'openai/gpt-6-luna' }); const result = await judge.assess(makeJudgeContext(meta, [makeFinding()])); expect(result.score).toBe(0); diff --git a/packages/evals/src/index.test.ts b/packages/evals/src/index.test.ts index 91de072c8..75751cd48 100644 --- a/packages/evals/src/index.test.ts +++ b/packages/evals/src/index.test.ts @@ -180,7 +180,7 @@ describe('standalone scenario files', () => { category: 'security-review', skill: '../warden/src/builtin-skills/security-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', baseDir: evalsDir, }); @@ -189,7 +189,7 @@ describe('standalone scenario files', () => { expect(meta.skillName).toBe('security-review'); expect(meta.skillPath).toContain('src/builtin-skills/security-review/SKILL.md'); expect(meta.runtime).toBe('pi'); - expect(meta.model).toBe('anthropic/claude-sonnet-4-6'); + expect(meta.model).toBe('openai/gpt-6-luna'); expect(meta.filePaths[0]).toContain('evals/fixtures/sentry-replay-delete-read-scope/'); }); @@ -198,7 +198,7 @@ describe('standalone scenario files', () => { category: 'security-review', skill: '../warden/src/builtin-skills/security-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', baseDir: evalsDir, }); @@ -211,7 +211,7 @@ describe('standalone scenario files', () => { category: 'code-review', skill: '../warden/src/builtin-skills/code-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', baseDir: evalsDir, }); @@ -391,7 +391,7 @@ describe('EvalFileSchema', () => { const valid = { skill: '../warden/src/builtin-skills/security-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', evals: [{ name: 'sentry-miss', given: 'Sentry endpoint with a known authorization miss', diff --git a/packages/evals/src/integrity-review.eval.ts b/packages/evals/src/integrity-review.eval.ts index f0d77c1c7..a254abaa7 100644 --- a/packages/evals/src/integrity-review.eval.ts +++ b/packages/evals/src/integrity-review.eval.ts @@ -14,7 +14,7 @@ const evals = discoverEvalScenarios({ category: 'integrity-review', skill: '../warden/src/builtin-skills/integrity-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', }); // Multi-file fixtures run several hunks plus verification and merge passes, // which can exceed the 120s the single-file suites use. diff --git a/packages/evals/src/judge.test.ts b/packages/evals/src/judge.test.ts index c23e4e8f2..f435f55c4 100644 --- a/packages/evals/src/judge.test.ts +++ b/packages/evals/src/judge.test.ts @@ -30,7 +30,7 @@ const meta: EvalMeta = { given: 'code that dereferences a possibly undefined value', skillPath: '/skills/bug-detection.md', filePaths: ['/fixtures/handler.ts'], - model: 'openrouter/anthropic/claude-sonnet-4.6', + model: 'openrouter/openai/gpt-6-luna', runtime: 'pi', should_find: [{ finding: 'null access on user', required: true }], should_not_find: ['style issues'], @@ -49,12 +49,12 @@ describe('runJudge', () => { }; runAuxiliary.mockResolvedValue({ success: true, data: response, usage }); - const result = await runJudge(meta, [], { model: 'openrouter/anthropic/claude-sonnet-4.6' }); + const result = await runJudge(meta, [], { model: 'openrouter/openai/gpt-6-luna' }); expect(mockedGetRuntime).toHaveBeenCalledWith('pi'); expect(runAuxiliary).toHaveBeenCalledWith(expect.objectContaining({ task: 'eval_judge', - model: 'openrouter/anthropic/claude-sonnet-4.6', + model: 'openrouter/openai/gpt-6-luna', apiKey: undefined, maxRetries: 0, })); @@ -64,7 +64,7 @@ describe('runJudge', () => { it('passes an Anthropic key through when one is configured', async () => { runAuxiliary.mockResolvedValue({ success: false, error: 'boom', usage }); - await runJudge(meta, [], { model: 'anthropic/claude-sonnet-4-6', apiKey: 'sk-ant' }); + await runJudge(meta, [], { model: 'openai/gpt-6-luna', apiKey: 'sk-ant' }); expect(runAuxiliary).toHaveBeenCalledWith(expect.objectContaining({ apiKey: 'sk-ant' })); }); @@ -72,7 +72,7 @@ describe('runJudge', () => { it('marks every assertion failed when the judge call fails', async () => { runAuxiliary.mockResolvedValue({ success: false, error: 'No API key for provider: openrouter', usage }); - const result = await runJudge(meta, [], { model: 'openrouter/anthropic/claude-sonnet-4.6' }); + const result = await runJudge(meta, [], { model: 'openrouter/openai/gpt-6-luna' }); expect(result.error).toBe('Judge call failed: No API key for provider: openrouter'); expect(result.usage).toBe(usage); @@ -91,7 +91,7 @@ describe('runJudge', () => { usage, }); - const result = await runJudge(meta, [], { model: 'openrouter/anthropic/claude-sonnet-4.6' }); + const result = await runJudge(meta, [], { model: 'openrouter/openai/gpt-6-luna' }); expect(result.error).toBe('Judge returned 0 verdicts, expected 1'); }); diff --git a/packages/evals/src/judge.ts b/packages/evals/src/judge.ts index c17a3f823..e5e060b2f 100644 --- a/packages/evals/src/judge.ts +++ b/packages/evals/src/judge.ts @@ -87,7 +87,7 @@ Requirements: } export interface JudgeOptions { - /** Pi model selector for the judge, e.g. `openrouter/anthropic/claude-sonnet-4.6`. */ + /** Pi model selector for the judge, e.g. `openrouter/openai/gpt-6-luna`. */ model: string; /** Anthropic key for Warden's legacy `apiKey` option. Other providers read their env key. */ apiKey?: string; diff --git a/packages/evals/src/provider.test.ts b/packages/evals/src/provider.test.ts index 5f413b0a2..cfcebfac8 100644 --- a/packages/evals/src/provider.test.ts +++ b/packages/evals/src/provider.test.ts @@ -2,7 +2,7 @@ import { describe, expect, it } from 'vitest'; import { DEFAULT_JUDGE_MODEL, resolveEvalProvider } from './provider.js'; describe('resolveEvalProvider', () => { - it('is disabled without a model override or Anthropic key', () => { + it('is disabled without a model override or OpenAI key', () => { expect(resolveEvalProvider({})).toEqual({ apiKey: '', model: undefined, @@ -13,11 +13,10 @@ describe('resolveEvalProvider', () => { }); }); - it('keeps scenario models when only an Anthropic key is set', () => { - const config = resolveEvalProvider({ WARDEN_ANTHROPIC_API_KEY: 'sk-ant' }); + it('keeps scenario models when only an OpenAI key is set', () => { + const config = resolveEvalProvider({ WARDEN_OPENAI_API_KEY: 'sk-openai' }); expect(config).toMatchObject({ - apiKey: 'sk-ant', model: undefined, runtime: undefined, judgeModel: DEFAULT_JUDGE_MODEL, @@ -25,22 +24,29 @@ describe('resolveEvalProvider', () => { }); }); - it('accepts the unprefixed Anthropic key', () => { - expect(resolveEvalProvider({ ANTHROPIC_API_KEY: 'sk-ant' }).apiKey).toBe('sk-ant'); + it('accepts the unprefixed OpenAI key', () => { + expect(resolveEvalProvider({ OPENAI_API_KEY: 'sk-openai' }).enabled).toBe(true); + }); + + it('stays disabled with only an Anthropic key, since the default models are OpenAI', () => { + const config = resolveEvalProvider({ WARDEN_ANTHROPIC_API_KEY: 'sk-ant' }); + + expect(config.apiKey).toBe('sk-ant'); + expect(config.enabled).toBe(false); }); it('routes evals, auxiliary calls, and the judge through WARDEN_EVAL_MODEL on Pi', () => { const config = resolveEvalProvider({ - WARDEN_EVAL_MODEL: ' openrouter/anthropic/claude-sonnet-4.6 ', + WARDEN_EVAL_MODEL: ' openrouter/openai/gpt-6-luna ', WARDEN_OPENROUTER_API_KEY: 'sk-or', }); expect(config).toEqual({ apiKey: '', - model: 'openrouter/anthropic/claude-sonnet-4.6', + model: 'openrouter/openai/gpt-6-luna', runtime: 'pi', - auxiliaryModel: 'openrouter/anthropic/claude-sonnet-4.6', - judgeModel: 'openrouter/anthropic/claude-sonnet-4.6', + auxiliaryModel: 'openrouter/openai/gpt-6-luna', + judgeModel: 'openrouter/openai/gpt-6-luna', enabled: true, }); }); @@ -48,11 +54,11 @@ describe('resolveEvalProvider', () => { it('uses WARDEN_EVAL_JUDGE_MODEL for the judge when set', () => { const config = resolveEvalProvider({ WARDEN_EVAL_MODEL: 'openrouter/x-ai/grok-4.3', - WARDEN_EVAL_JUDGE_MODEL: 'openrouter/anthropic/claude-sonnet-4.6', + WARDEN_EVAL_JUDGE_MODEL: 'openrouter/openai/gpt-6-luna', }); expect(config.model).toBe('openrouter/x-ai/grok-4.3'); - expect(config.judgeModel).toBe('openrouter/anthropic/claude-sonnet-4.6'); + expect(config.judgeModel).toBe('openrouter/openai/gpt-6-luna'); }); it('treats empty overrides as unset', () => { @@ -64,7 +70,7 @@ describe('resolveEvalProvider', () => { }); it('rejects a model override without a provider prefix', () => { - expect(() => resolveEvalProvider({ WARDEN_EVAL_MODEL: 'claude-sonnet-4-6' })).toThrow( + expect(() => resolveEvalProvider({ WARDEN_EVAL_MODEL: 'gpt-6-luna' })).toThrow( 'WARDEN_EVAL_MODEL must be a provider/model selector' ); }); diff --git a/packages/evals/src/provider.ts b/packages/evals/src/provider.ts index 0c88d3d7a..e4368d0a8 100644 --- a/packages/evals/src/provider.ts +++ b/packages/evals/src/provider.ts @@ -1,13 +1,13 @@ import type { RuntimeName } from '@sentry/warden'; -/** Env var that points every live eval at one Pi model selector, e.g. `openrouter/anthropic/claude-sonnet-4.6`. */ +/** Env var that points every live eval at one Pi model selector, e.g. `openrouter/openai/gpt-6-luna`. */ const EVAL_MODEL_ENV = 'WARDEN_EVAL_MODEL'; /** Env var that overrides the judge model. Defaults to the eval model. */ const EVAL_JUDGE_MODEL_ENV = 'WARDEN_EVAL_JUDGE_MODEL'; /** Judge model used when no eval model is configured. */ -export const DEFAULT_JUDGE_MODEL = 'anthropic/claude-sonnet-4-6'; +export const DEFAULT_JUDGE_MODEL = 'openai/gpt-6-luna'; export interface EvalProviderConfig { /** Anthropic key for Warden's legacy `apiKey` option. Empty when unset. */ @@ -23,7 +23,7 @@ export interface EvalProviderConfig { auxiliaryModel?: string; /** Pi model selector for the LLM judge. */ judgeModel: string; - /** Whether live evals have a configured model or Anthropic key to run with. */ + /** Whether live evals have a configured model or an OpenAI key for the default models. */ enabled: boolean; } @@ -33,7 +33,7 @@ function readModelSelector(env: NodeJS.ProcessEnv, name: string): string | undef return undefined; } if (!value.includes('/')) { - throw new Error(`${name} must be a provider/model selector, for example openrouter/anthropic/claude-sonnet-4.6`); + throw new Error(`${name} must be a provider/model selector, for example openrouter/openai/gpt-6-luna`); } return value; } @@ -41,13 +41,14 @@ function readModelSelector(env: NodeJS.ProcessEnv, name: string): string | undef /** * Resolve which model and credentials live evals use. * - * Without `WARDEN_EVAL_MODEL`, scenarios keep their YAML models and evals run only - * when an Anthropic key is present. With it, every scenario, Warden's auxiliary - * calls, and the judge use that selector, and credentials come from the - * provider's `WARDEN__API_KEY`. + * Without `WARDEN_EVAL_MODEL`, scenarios keep their checked-in OpenAI models and + * evals run only when an OpenAI key is present. With it, every scenario, + * Warden's auxiliary calls, and the judge use that selector, and credentials + * come from the provider's `WARDEN__API_KEY`. */ export function resolveEvalProvider(env: NodeJS.ProcessEnv = process.env): EvalProviderConfig { const apiKey = env['WARDEN_ANTHROPIC_API_KEY'] || env['ANTHROPIC_API_KEY'] || ''; + const openaiKey = env['WARDEN_OPENAI_API_KEY'] || env['OPENAI_API_KEY'] || ''; const model = readModelSelector(env, EVAL_MODEL_ENV); const judgeModel = readModelSelector(env, EVAL_JUDGE_MODEL_ENV) ?? model ?? DEFAULT_JUDGE_MODEL; @@ -57,6 +58,6 @@ export function resolveEvalProvider(env: NodeJS.ProcessEnv = process.env): EvalP runtime: model ? 'pi' : undefined, auxiliaryModel: model, judgeModel, - enabled: Boolean(model || apiKey), + enabled: Boolean(model || openaiKey), }; } diff --git a/packages/evals/src/runner.test.ts b/packages/evals/src/runner.test.ts index fcac9922a..742c7a2ce 100644 --- a/packages/evals/src/runner.test.ts +++ b/packages/evals/src/runner.test.ts @@ -36,7 +36,7 @@ describe('setupEvalRepo', () => { 'organization_preprod_size_analysis.py' ), ], - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', runtime: 'pi', should_find: [{ finding: 'baseArtifactId bypass', required: true }], should_not_find: [], @@ -97,7 +97,7 @@ describe('setupEvalRepo', () => { skillPath: join(repoRoot, 'packages', 'warden', 'src', 'builtin-skills', 'security-review', 'SKILL.md'), filePaths: [fixturePath], supportingFilePaths: [licensePath], - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', runtime: 'pi', should_find: [{ finding: 'source path context', required: true }], should_not_find: [], @@ -146,7 +146,7 @@ describe('runEvalSkill', () => { filePaths: [ join(evalsDir, 'fixtures', 'sentry-preprod-size-analysis-base-artifact-access', 'organization_preprod_size_analysis.py'), ], - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', runtime: 'pi', should_find: [], should_not_find: [], @@ -154,15 +154,15 @@ describe('runEvalSkill', () => { await runEvalSkill(meta, { apiKey: '', - model: 'openrouter/anthropic/claude-sonnet-4.6', + model: 'openrouter/openai/gpt-6-luna', runtime: 'pi', - auxiliaryModel: 'openrouter/anthropic/claude-sonnet-4.6', + auxiliaryModel: 'openrouter/openai/gpt-6-luna', }); expect(runLocalSkill).toHaveBeenCalledWith(expect.objectContaining({ - model: 'openrouter/anthropic/claude-sonnet-4.6', - auxiliaryModel: 'openrouter/anthropic/claude-sonnet-4.6', - synthesisModel: 'openrouter/anthropic/claude-sonnet-4.6', + model: 'openrouter/openai/gpt-6-luna', + auxiliaryModel: 'openrouter/openai/gpt-6-luna', + synthesisModel: 'openrouter/openai/gpt-6-luna', })); }); }); diff --git a/packages/evals/src/security-review.eval.ts b/packages/evals/src/security-review.eval.ts index 2b0fc26b9..dad7a27f1 100644 --- a/packages/evals/src/security-review.eval.ts +++ b/packages/evals/src/security-review.eval.ts @@ -14,7 +14,7 @@ const evals = discoverEvalScenarios({ category: 'security-review', skill: '../warden/src/builtin-skills/security-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', }); describeEval( diff --git a/packages/evals/src/types.ts b/packages/evals/src/types.ts index 5fc1a2f11..2329be696 100644 --- a/packages/evals/src/types.ts +++ b/packages/evals/src/types.ts @@ -2,10 +2,10 @@ import { z } from 'zod'; import { RuntimeNameSchema, SeveritySchema, type Finding, type RuntimeName } from '@sentry/warden'; /** Default model for eval skill execution. */ -export const DEFAULT_EVAL_MODEL = 'claude-sonnet-4-6'; +export const DEFAULT_EVAL_MODEL = 'openai/gpt-6-luna'; /** Default runtime for eval skill execution. */ -export const DEFAULT_EVAL_RUNTIME: RuntimeName = 'claude'; +export const DEFAULT_EVAL_RUNTIME: RuntimeName = 'pi'; /** * A "should find" assertion in BDD style. diff --git a/packages/evals/src/verify.eval.ts b/packages/evals/src/verify.eval.ts index 8fcac62ca..ba3568f25 100644 --- a/packages/evals/src/verify.eval.ts +++ b/packages/evals/src/verify.eval.ts @@ -13,7 +13,7 @@ const evals = discoverVerificationEvalScenarios({ category: 'verification', skill: '../warden/src/builtin-skills/security-review/SKILL.md', runtime: 'pi', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', }); describeEval( diff --git a/packages/evals/src/verify.test.ts b/packages/evals/src/verify.test.ts index 021262bc5..07e6c1f9c 100644 --- a/packages/evals/src/verify.test.ts +++ b/packages/evals/src/verify.test.ts @@ -78,7 +78,7 @@ describe('resolveVerificationEvalMeta', () => { supportingFilePaths: [licensePath], candidate, expectedVerdict: 'reject', - model: 'anthropic/claude-sonnet-4-6', + model: 'openai/gpt-6-luna', runtime: 'pi', }, { apiKey: 'test-api-key', diff --git a/packages/evals/src/verify.ts b/packages/evals/src/verify.ts index 3baa48bd1..c196d13ff 100644 --- a/packages/evals/src/verify.ts +++ b/packages/evals/src/verify.ts @@ -26,7 +26,7 @@ import type { EvalMeta } from './types.js'; import { usageToSummary } from './usage.js'; const DEFAULT_VERIFICATION_RUNTIME: RuntimeName = 'pi'; -const DEFAULT_VERIFICATION_MODEL = 'anthropic/claude-sonnet-4-6'; +const DEFAULT_VERIFICATION_MODEL = 'openai/gpt-6-luna'; const VerificationVerdictSchema = z.enum(['keep', 'reject']); diff --git a/packages/warden/package.json b/packages/warden/package.json index b96471bce..4d727f6ab 100644 --- a/packages/warden/package.json +++ b/packages/warden/package.json @@ -48,8 +48,8 @@ "dependencies": { "@anthropic-ai/claude-agent-sdk": "^0.3.150", "@anthropic-ai/sdk": "^0.98.0", - "@earendil-works/pi-ai": "^0.86.1", - "@earendil-works/pi-coding-agent": "^0.86.1", + "@earendil-works/pi-ai": "^0.87.1", + "@earendil-works/pi-coding-agent": "^0.87.1", "@inquirer/select": "^5.1.5", "@modelcontextprotocol/sdk": "^1.31.0", "@octokit/rest": "^22.0.1", diff --git a/packages/warden/src/cli/commands/build.ts b/packages/warden/src/cli/commands/build.ts index 48a0f38bd..b0cc3606a 100644 --- a/packages/warden/src/cli/commands/build.ts +++ b/packages/warden/src/cli/commands/build.ts @@ -173,7 +173,7 @@ type GeneratedSkillCommandMode = 'build' | 'improve'; function reportInvalidPiModelSelector(reporter: Reporter, invalid: InvalidPiModelSelector): void { reporter.error(invalidPiModelSelectorMessage(invalid)); - reporter.tip('Set a Pi model selector such as anthropic/claude-sonnet-4-6.'); + reporter.tip('Set a Pi model selector such as openai/gpt-6-luna.'); } async function resolvePrompt( diff --git a/packages/warden/src/cli/main.ts b/packages/warden/src/cli/main.ts index f3f734fc8..8b37d5c10 100644 --- a/packages/warden/src/cli/main.ts +++ b/packages/warden/src/cli/main.ts @@ -787,7 +787,7 @@ export function findInvalidPiModelSelector( function reportInvalidPiModelSelector(reporter: Reporter, invalid: InvalidPiModelSelector): void { reporter.error(invalidPiModelSelectorMessage(invalid)); - reporter.tip('Set a Pi model selector such as anthropic/claude-sonnet-4-6.'); + reporter.tip('Set a Pi model selector such as openai/gpt-6-luna.'); } function emitInvalidPiModelSelectorRunLog( diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 09437490c..7effb8ac0 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -221,11 +221,11 @@ importers: specifier: ^0.98.0 version: 0.98.0(zod@4.6.7) '@earendil-works/pi-ai': - specifier: ^0.86.1 - version: 0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) + specifier: ^0.87.1 + version: 0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) '@earendil-works/pi-coding-agent': - specifier: ^0.86.1 - version: 0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) + specifier: ^0.87.1 + version: 0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) '@inquirer/select': specifier: ^5.1.5 version: 5.1.5(@types/node@26.6.6) @@ -564,10 +564,6 @@ packages: resolution: {integrity: sha512-IDl/lrPb90aH+pZFHGNDmgH9nAUQj5PlZH1sJ3w7RikctyjHSnY3oNjZhrLoaBoQn/rNK0zsP6OHEqEhj2tdLA==} engines: {node: '>=20.0.0'} - '@aws-sdk/core@3.977.9': - resolution: {integrity: sha512-reqPFEQrZxDZpeGj4PFMepBeR5LGYHRqq/L0motTzgFkCRBA4rFdaVXDSLYyGHhxVz7sT2PDnPN9CluGSfgyJA==} - engines: {node: '>=20.0.0'} - '@aws-sdk/core@3.978.3': resolution: {integrity: sha512-nslpzUCTI9b2IQMWSd6mSAXldBexPc8rr0d3dXUutXYFLFaTdsHa2GD7sJdsn3PhyjK0O5K8ypd6zi+RXXPVlg==} engines: {node: '>=20.0.0'} @@ -616,18 +612,10 @@ packages: resolution: {integrity: sha512-vsPPM+nMbKJlUCFU+eoGZbdxdxDIAX9LbpjSXaR5Ufpmqgp8TdYQnoExhLu4T3umW/JIIPny1ydbhWidZZYokQ==} engines: {node: '>= 14.0.0'} - '@aws-sdk/nested-clients@3.997.44': - resolution: {integrity: sha512-NhEgryjlBF9w38ZXqGymQV28IhkYa1mKhlbYnqIis57AYwWGVYfUPgg/qC2rLRqOUfblxx++irvju10kVTa8Vw==} - engines: {node: '>=20.0.0'} - '@aws-sdk/nested-clients@3.997.48': resolution: {integrity: sha512-B01jdXJtAW/XOiUzGdI2mz67WyEHbGEc9X6Euzw3bjLAa+txTqdZDER4X2FsIEcXzV2ABqudVZ5thali8tCCzQ==} engines: {node: '>=20.0.0'} - '@aws-sdk/signature-v4-multi-region@3.996.46': - resolution: {integrity: sha512-L+2xZTye/2T96f3lwCws0Zw6GG2JHZW9e8FpVgGBeeExSKyeoZ6CWRpBml/7DNiK/O26jrgPM9F+Ay8VkgzUWQ==} - engines: {node: '>=20.0.0'} - '@aws-sdk/signature-v4-multi-region@3.996.48': resolution: {integrity: sha512-cFDXfEbXaGwbnpvR/DyqfxfjxpjXVRVthQLgkwvcfDS5u3+8G9WSj1X1Ag/pTRg/QOeOno1Tq3ycEdrKsCUcOA==} engines: {node: '>=20.0.0'} @@ -640,18 +628,10 @@ packages: resolution: {integrity: sha512-wDU36ofhabZYu+d2KSriyDbwzxNoaOp+4dG0p3qkabk7HeALR5nIWyQbjoyJZLn3iqWkv/xNdyUfbfevDVDzzg==} engines: {node: '>=20.0.0'} - '@aws-sdk/types@3.974.5': - resolution: {integrity: sha512-LkwLL2BLbC6wNNm4JaH9mbEqBMdOZCct6VAYqhdN4U1xrWM+fUJQEfbHwQgDypapOWTRtlk25akb5afM0P8CIQ==} - engines: {node: '>=20.0.0'} - '@aws-sdk/types@3.974.6': resolution: {integrity: sha512-v/clNZzZnDxGyvpHMOGpJKVXFAExJzUNAAjaWGdcx8QAcXLGwTaOkw33p5SHAi0YAioK32xB3hWwOekRVfmfKg==} engines: {node: '>=20.0.0'} - '@aws-sdk/xml-builder@3.972.40': - resolution: {integrity: sha512-wlFmCIGUlwF4zx/kncw+bmxTQh1HeSJq4mYV/V5cZUSJadDP3kXvGW8Rn21cimj/7y9ju+47oYWXi97vF7czaA==} - engines: {node: '>=20.0.0'} - '@aws-sdk/xml-builder@3.972.41': resolution: {integrity: sha512-ctjVSyCMegrWfXlx6VqzSBFI6UqmQ5ZlnfMhdLIiWmhoH8UAQxSCP5N3OpG7X3k4LnS7ou74C4mt20+bfTW2aQ==} engines: {node: '>=20.0.0'} @@ -897,30 +877,30 @@ packages: '@drizzle-team/brocli@0.10.2': resolution: {integrity: sha512-z33Il7l5dKjUgGULTqBsQBQwckHh5AbIuxhdsIxDDiZAzBOrZO6q9ogcWC65kU382AfynTfgNumVcNIjuIua6w==} - '@earendil-works/chord@0.86.1': - resolution: {integrity: sha512-GzUr5n4tFBHUYxN9CjcRHK8QWo9tbxNrZu6iWPQ+PFiFrLASvSZOKeAVAgh3gHv/t0X5OvUpFlrMQ/nEFfCYpg==} + '@earendil-works/chord@0.87.1': + resolution: {integrity: sha512-bg7IkJGFcEaMqqYgOGUiq5Ky9RghpRfrlZ8I/v/1b4bBZ02A7t3E+6uhPRbadwWb/kWsnVFbZsqOKRN4a3LLCg==} engines: {node: '>=22.19.0'} - '@earendil-works/pi-agent-core@0.86.1': - resolution: {integrity: sha512-8TbBzhYsDeu5V1Zl2NsyrBqJAzX1EiEL3Np3ZjGpy0pSDdGRVOpcyW1qruLqfWmEqGcnxmvgnTMLS/wJNZO2XQ==} + '@earendil-works/pi-agent-core@0.87.1': + resolution: {integrity: sha512-Zev3B0HK7YS5A4EZQ2XnEqiJuirx6QBiltJ+LpmjV5a/+2IU0cfKtIfnkNkORK707XOvKBY2WRtk7cAwHpbh2Q==} engines: {node: '>=22.19.0'} - '@earendil-works/pi-ai@0.86.1': - resolution: {integrity: sha512-1XHhI6D/fyQdsBieHC/E/4zGKVOoGe4yDyX67VXvzoYkFsX/qE7NpZE7E1RC8e6Bz8B9oG/P+MQFXikv2/BGEg==} + '@earendil-works/pi-ai@0.87.1': + resolution: {integrity: sha512-X/3PfQBnnoeVdO9Cv8zHghUMglzlgNZYGNzoPnbRoGnHl3Rw3TlA2UKSUB7BRHUOxMryHXYa8dnjWZlbRheDZA==} engines: {node: '>=22.19.0'} hasBin: true - '@earendil-works/pi-coding-agent@0.86.1': - resolution: {integrity: sha512-vZBuNfJnruxZyemZ3O05V0S/Ylze08ahFTIQ1Mik++gVdOevPl89gt/Uv0U97BPAJaj9cj6Vf9rcIgKtUrd0BA==} + '@earendil-works/pi-coding-agent@0.87.1': + resolution: {integrity: sha512-m8ArJUtVcQMSe1lLE/Ei7vX/JV7O39sWmWBsXV2NOU70F0qCp8GubA24pT3LnwTmM6LL2xV80/h6sQg85n69ew==} engines: {node: '>=22.19.0'} hasBin: true - '@earendil-works/pi-telemetry@0.86.1': - resolution: {integrity: sha512-SOcEqOS3oVGgKeahs2jHB906d8hFjuLP+RBee8xKYMRgw5KAeWHNg+YABfL0ALlp3Bt6tW4b632MLghc3vnTog==} + '@earendil-works/pi-telemetry@0.87.1': + resolution: {integrity: sha512-MC6TRQH5lgMXpcN+Vku2WMI2T8BsiUPzMQHGo81uqFZD3/9O79WWJAysEDGuzduP6R4tvtgwMLwmqIxynM10JQ==} engines: {node: '>=22.19.0'} - '@earendil-works/pi-tui@0.86.1': - resolution: {integrity: sha512-FU/zU/zG4RWokcZt+BVXXcieWi5ggvYnWP2kkB5XXjMaHRoy5BDhcZJ9JAnLTN9MwrCRoXgPQxOI0bFqwYeZkQ==} + '@earendil-works/pi-tui@0.87.1': + resolution: {integrity: sha512-YEH2vRyOeiO7hhN6j6AE6YwKSq2Kz2f3XR8bj1TbR+aGE/JsnY1hLPMI2pvaZfRM1n9Y00tejxFQ4zbzvF7nkQ==} engines: {node: '>=22.19.0'} '@edge-runtime/format@2.2.1': @@ -2931,22 +2911,17 @@ packages: '@sinclair/typebox@0.25.24': resolution: {integrity: sha512-XJfwUVUKDHF5ugKwIcxEgc9k8b7HbznCp6eUfWgu710hMPNIO4aw4/zB5RogDQz8nd6gyCDpU9O/m6qYEWY6yQ==} - '@smithy/core@3.33.3': - resolution: {integrity: sha512-CsOeKq/9kA3y6VJHt+/+VTCtBaxJ4OTFpgrjIUhPpDIKxBci1k2bJaQASF2h/ELWrulGp+t97DZ0mevfAD8idg==} - engines: {node: '>=18.0.0'} - '@smithy/core@3.36.0': resolution: {integrity: sha512-3hJiwG1F5t1SoXqp/yOCmYXziyx7ZVqF63S5W6YU201e/qwVaHPex+E/3vvyY9a3ORq/b+BydeNZpP2saQ9X2g==} engines: {node: '>=18.0.0'} + deprecated: |- + Deprecated due to a bug in custom logger data redaction. Upgrade to the latest version. If you used a custom logger with this + version, review your logs and rotate any credentials or other secrets. See https://github.com/aws/aws-sdk-js-v3/issues/8393. '@smithy/credential-provider-imds@4.5.2': resolution: {integrity: sha512-A9uSdn72ozbRUSit0eib0TW7nXuNPlaeM0zcGkJ+nE6tFcSDbnmtwoxbTCFBukVQcszDAyvsd7+rTduPTXpygg==} engines: {node: '>=18.0.0'} - '@smithy/fetch-http-handler@5.7.2': - resolution: {integrity: sha512-nZyWTmSpJEXl6VtWVMBJve/7x12DZu6sIX1z1a+ZMaHlQQRs9Zpu6NbTe/gmxYXVRpkjxyDYpZ5gx2IM6f/Wkw==} - engines: {node: '>=18.0.0'} - '@smithy/fetch-http-handler@5.8.0': resolution: {integrity: sha512-ycSJu3tFAQ4v04CBB0agqFMVsSQ1iG3yw+SpgxRqKfaURpQD4CZ8Wn0zPMmSnOuTpTh65Vz+EA0rMrw089wvkA==} engines: {node: '>=18.0.0'} @@ -2955,18 +2930,10 @@ packages: resolution: {integrity: sha512-ThMkboGeONWXAelq9FvGsuJC4rOi+qyC4/zhUF58xYpxUg5sQKx2VXZYJmtNjr4dSuBJ1HeJXETQILCz3wOHvw==} engines: {node: '>=18.0.0'} - '@smithy/signature-v4@5.7.3': - resolution: {integrity: sha512-7ImGm+FkHRLcBaRttIAMZ6bzJZWb2cJGoYjq46F2UjycujWzrL9GEN9h4w7eQyXJYnltrUhxbbieBAIRrdqpow==} - engines: {node: '>=18.0.0'} - '@smithy/signature-v4@5.7.4': resolution: {integrity: sha512-tHy0K0VtqNd5Y7Y41h0a0Lhh0L1GzC08dTWg0F7vRJWFtTENg7IZikf3wQkanYIRdb7ngoIPMTmqgUi401fEeQ==} engines: {node: '>=18.0.0'} - '@smithy/types@4.17.2': - resolution: {integrity: sha512-FOKpVZob9MPTn2znRzGrnsMHv7BOsKVw3XiP/cOyYLDVZ9qKp4nifIiSCuUU/fIj5Vu0UOAxCFr+qRAtG0NUkA==} - engines: {node: '>=18.0.0'} - '@smithy/types@4.19.0': resolution: {integrity: sha512-r7jh49VJxGerfAcTQA6gXcKc+98zOp/tqRwzYjgOE+iSQsP6cEU1hq2QzbuipmP68QtYdY9wKEhiCQZIzHgZ4Q==} engines: {node: '>=18.0.0'} @@ -4856,10 +4823,6 @@ packages: longest-streak@3.1.0: resolution: {integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==} - lru-cache@11.5.2: - resolution: {integrity: sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g==} - engines: {node: 20 || >=22} - lru-cache@11.5.3: resolution: {integrity: sha512-U4N8FgzmWxc8k1VH8Kr6lQg18U7Fjvby6wXHVRX/ZZ7IwWbRMgrRbP0Wrb5q5NVinryp4SQampHKdvtecItxUg==} engines: {node: 20 || >=22} @@ -6870,28 +6833,17 @@ snapshots: '@aws-sdk/client-bedrock-runtime@3.1127.0': dependencies: - '@aws-sdk/core': 3.977.9 + '@aws-sdk/core': 3.978.3 '@aws-sdk/credential-provider-node': 3.972.86 '@aws-sdk/eventstream-handler-node': 3.972.34 '@aws-sdk/middleware-eventstream': 3.972.29 '@aws-sdk/middleware-websocket': 3.972.52 '@aws-sdk/token-providers': 3.1127.0 - '@aws-sdk/types': 3.974.5 - '@smithy/core': 3.33.3 - '@smithy/fetch-http-handler': 5.7.2 + '@aws-sdk/types': 3.974.6 + '@smithy/core': 3.36.0 + '@smithy/fetch-http-handler': 5.8.0 '@smithy/node-http-handler': 4.12.1 - '@smithy/types': 4.17.2 - tslib: 2.8.1 - - '@aws-sdk/core@3.977.9': - dependencies: - '@aws-sdk/types': 3.974.5 - '@aws-sdk/xml-builder': 3.972.40 - '@aws/lambda-invoke-store': 0.3.0 - '@smithy/core': 3.33.3 - '@smithy/signature-v4': 5.7.3 - '@smithy/types': 4.17.2 - bowser: 2.14.1 + '@smithy/types': 4.19.0 tslib: 2.8.1 '@aws-sdk/core@3.978.3': @@ -6991,37 +6943,26 @@ snapshots: '@aws-sdk/eventstream-handler-node@3.972.34': dependencies: - '@aws-sdk/types': 3.974.5 - '@smithy/core': 3.33.3 - '@smithy/types': 4.17.2 + '@aws-sdk/types': 3.974.6 + '@smithy/core': 3.36.0 + '@smithy/types': 4.19.0 tslib: 2.8.1 '@aws-sdk/middleware-eventstream@3.972.29': dependencies: - '@aws-sdk/types': 3.974.5 - '@smithy/core': 3.33.3 - '@smithy/types': 4.17.2 + '@aws-sdk/types': 3.974.6 + '@smithy/core': 3.36.0 + '@smithy/types': 4.19.0 tslib: 2.8.1 '@aws-sdk/middleware-websocket@3.972.52': dependencies: - '@aws-sdk/core': 3.977.9 - '@aws-sdk/types': 3.974.5 - '@smithy/core': 3.33.3 - '@smithy/fetch-http-handler': 5.7.2 - '@smithy/signature-v4': 5.7.3 - '@smithy/types': 4.17.2 - tslib: 2.8.1 - - '@aws-sdk/nested-clients@3.997.44': - dependencies: - '@aws-sdk/core': 3.977.9 - '@aws-sdk/signature-v4-multi-region': 3.996.46 - '@aws-sdk/types': 3.974.5 - '@smithy/core': 3.33.3 - '@smithy/fetch-http-handler': 5.7.2 - '@smithy/node-http-handler': 4.12.1 - '@smithy/types': 4.17.2 + '@aws-sdk/core': 3.978.3 + '@aws-sdk/types': 3.974.6 + '@smithy/core': 3.36.0 + '@smithy/fetch-http-handler': 5.8.0 + '@smithy/signature-v4': 5.7.4 + '@smithy/types': 4.19.0 tslib: 2.8.1 '@aws-sdk/nested-clients@3.997.48': @@ -7035,13 +6976,6 @@ snapshots: '@smithy/types': 4.19.0 tslib: 2.8.1 - '@aws-sdk/signature-v4-multi-region@3.996.46': - dependencies: - '@aws-sdk/types': 3.974.5 - '@smithy/signature-v4': 5.7.3 - '@smithy/types': 4.17.2 - tslib: 2.8.1 - '@aws-sdk/signature-v4-multi-region@3.996.48': dependencies: '@aws-sdk/types': 3.974.6 @@ -7051,11 +6985,11 @@ snapshots: '@aws-sdk/token-providers@3.1127.0': dependencies: - '@aws-sdk/core': 3.977.9 - '@aws-sdk/nested-clients': 3.997.44 - '@aws-sdk/types': 3.974.5 - '@smithy/core': 3.33.3 - '@smithy/types': 4.17.2 + '@aws-sdk/core': 3.978.3 + '@aws-sdk/nested-clients': 3.997.48 + '@aws-sdk/types': 3.974.6 + '@smithy/core': 3.36.0 + '@smithy/types': 4.19.0 tslib: 2.8.1 '@aws-sdk/token-providers@3.1150.0': @@ -7067,21 +7001,11 @@ snapshots: '@smithy/types': 4.19.0 tslib: 2.8.1 - '@aws-sdk/types@3.974.5': - dependencies: - '@smithy/types': 4.17.2 - tslib: 2.8.1 - '@aws-sdk/types@3.974.6': dependencies: '@smithy/types': 4.19.0 tslib: 2.8.1 - '@aws-sdk/xml-builder@3.972.40': - dependencies: - '@smithy/types': 4.17.2 - tslib: 2.8.1 - '@aws-sdk/xml-builder@3.972.41': dependencies: '@smithy/types': 4.19.0 @@ -7268,15 +7192,15 @@ snapshots: '@drizzle-team/brocli@0.10.2': {} - '@earendil-works/chord@0.86.1': + '@earendil-works/chord@0.87.1': dependencies: esbuild: 0.28.2 - '@earendil-works/pi-agent-core@0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7)': + '@earendil-works/pi-agent-core@0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7)': dependencies: - '@earendil-works/chord': 0.86.1 - '@earendil-works/pi-ai': 0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) - '@earendil-works/pi-telemetry': 0.86.1 + '@earendil-works/chord': 0.87.1 + '@earendil-works/pi-ai': 0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) + '@earendil-works/pi-telemetry': 0.87.1 diff: 8.0.4 ignore: 7.0.8 typebox: 1.3.27 @@ -7290,11 +7214,11 @@ snapshots: - ws - zod - '@earendil-works/pi-ai@0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7)': + '@earendil-works/pi-ai@0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7)': dependencies: '@anthropic-ai/sdk': 0.124.0(zod@4.6.7) '@aws-sdk/client-bedrock-runtime': 3.1127.0 - '@earendil-works/pi-telemetry': 0.86.1 + '@earendil-works/pi-telemetry': 0.87.1 '@google/genai': 2.21.0(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7)) '@smithy/node-http-handler': 4.12.1 http-proxy-agent: 9.1.0 @@ -7311,12 +7235,12 @@ snapshots: - ws - zod - '@earendil-works/pi-coding-agent@0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7)': + '@earendil-works/pi-coding-agent@0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7)': dependencies: - '@earendil-works/chord': 0.86.1 - '@earendil-works/pi-agent-core': 0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) - '@earendil-works/pi-ai': 0.86.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) - '@earendil-works/pi-tui': 0.86.1 + '@earendil-works/chord': 0.87.1 + '@earendil-works/pi-agent-core': 0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) + '@earendil-works/pi-ai': 0.87.1(@modelcontextprotocol/sdk@1.32.1(zod@4.6.7))(ws@8.22.0)(zod@4.6.7) + '@earendil-works/pi-tui': 0.87.1 '@silvia-odwyer/photon-node': 0.3.4 chalk: 6.0.0 cross-spawn: 7.0.6 @@ -7341,9 +7265,9 @@ snapshots: - ws - zod - '@earendil-works/pi-telemetry@0.86.1': {} + '@earendil-works/pi-telemetry@0.87.1': {} - '@earendil-works/pi-tui@0.86.1': + '@earendil-works/pi-tui@0.87.1': dependencies: get-east-asian-width: 1.6.0 marked: 18.0.11 @@ -8765,11 +8689,6 @@ snapshots: '@sinclair/typebox@0.25.24': {} - '@smithy/core@3.33.3': - dependencies: - '@smithy/types': 4.19.0 - tslib: 2.8.1 - '@smithy/core@3.36.0': dependencies: '@smithy/types': 4.19.0 @@ -8781,12 +8700,6 @@ snapshots: '@smithy/types': 4.19.0 tslib: 2.8.1 - '@smithy/fetch-http-handler@5.7.2': - dependencies: - '@smithy/core': 3.33.3 - '@smithy/types': 4.17.2 - tslib: 2.8.1 - '@smithy/fetch-http-handler@5.8.0': dependencies: '@smithy/core': 3.36.0 @@ -8795,26 +8708,16 @@ snapshots: '@smithy/node-http-handler@4.12.1': dependencies: - '@smithy/core': 3.33.3 + '@smithy/core': 3.36.0 '@smithy/types': 4.19.0 tslib: 2.8.1 - '@smithy/signature-v4@5.7.3': - dependencies: - '@smithy/core': 3.33.3 - '@smithy/types': 4.17.2 - tslib: 2.8.1 - '@smithy/signature-v4@5.7.4': dependencies: '@smithy/core': 3.36.0 '@smithy/types': 4.19.0 tslib: 2.8.1 - '@smithy/types@4.17.2': - dependencies: - tslib: 2.8.1 - '@smithy/types@4.19.0': dependencies: tslib: 2.8.1 @@ -10705,7 +10608,7 @@ snapshots: hosted-git-info@9.0.3: dependencies: - lru-cache: 11.5.2 + lru-cache: 11.5.3 html-escaper@2.0.2: {} @@ -11037,8 +10940,6 @@ snapshots: longest-streak@3.1.0: {} - lru-cache@11.5.2: {} - lru-cache@11.5.3: {} lru-cache@6.0.0: