@namzu/sdk 36.0.0 → 38.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +244 -0
- package/README.md +68 -41
- package/dist/bridge/a2a/mapper.d.ts.map +1 -1
- package/dist/bridge/a2a/mapper.js +4 -0
- package/dist/bridge/a2a/mapper.js.map +1 -1
- package/dist/bridge/sse/mapper.d.ts.map +1 -1
- package/dist/bridge/sse/mapper.js +16 -1
- package/dist/bridge/sse/mapper.js.map +1 -1
- package/dist/compaction/extractor.d.ts +1 -1
- package/dist/compaction/extractor.d.ts.map +1 -1
- package/dist/compaction/extractor.js +15 -7
- package/dist/compaction/extractor.js.map +1 -1
- package/dist/compaction/manager.d.ts +2 -0
- package/dist/compaction/manager.d.ts.map +1 -1
- package/dist/compaction/manager.js +12 -1
- package/dist/compaction/manager.js.map +1 -1
- package/dist/compaction/verifier.d.ts.map +1 -1
- package/dist/compaction/verifier.js +82 -15
- package/dist/compaction/verifier.js.map +1 -1
- package/dist/config/runtime.d.ts +16 -6
- package/dist/config/runtime.d.ts.map +1 -1
- package/dist/config/runtime.js +2 -0
- package/dist/config/runtime.js.map +1 -1
- package/dist/contracts/api.d.ts +1 -1
- package/dist/contracts/api.d.ts.map +1 -1
- package/dist/contracts/schemas.d.ts +10 -10
- package/dist/eval/harness-verification.d.ts +63 -0
- package/dist/eval/harness-verification.d.ts.map +1 -0
- package/dist/eval/harness-verification.js +165 -0
- package/dist/eval/harness-verification.js.map +1 -0
- package/dist/eval/index.d.ts +2 -0
- package/dist/eval/index.d.ts.map +1 -1
- package/dist/eval/index.js +1 -0
- package/dist/eval/index.js.map +1 -1
- package/dist/execution/code-runtime/json-value.d.ts +10 -0
- package/dist/execution/code-runtime/json-value.d.ts.map +1 -0
- package/dist/execution/code-runtime/json-value.js +89 -0
- package/dist/execution/code-runtime/json-value.js.map +1 -0
- package/dist/execution/code-runtime/worker-program.d.ts +8 -0
- package/dist/execution/code-runtime/worker-program.d.ts.map +1 -0
- package/dist/execution/code-runtime/worker-program.js +240 -0
- package/dist/execution/code-runtime/worker-program.js.map +1 -0
- package/dist/execution/code-runtime/worker.d.ts +22 -0
- package/dist/execution/code-runtime/worker.d.ts.map +1 -1
- package/dist/execution/code-runtime/worker.js +148 -111
- package/dist/execution/code-runtime/worker.js.map +1 -1
- package/dist/manager/agent/lifecycle.d.ts +12 -0
- package/dist/manager/agent/lifecycle.d.ts.map +1 -1
- package/dist/manager/agent/lifecycle.js +316 -46
- package/dist/manager/agent/lifecycle.js.map +1 -1
- package/dist/manager/run/persistence.d.ts +2 -0
- package/dist/manager/run/persistence.d.ts.map +1 -1
- package/dist/manager/run/persistence.js +6 -0
- package/dist/manager/run/persistence.js.map +1 -1
- package/dist/prompt/coding-agent-doctrine.d.ts +2 -2
- package/dist/prompt/coding-agent-doctrine.d.ts.map +1 -1
- package/dist/prompt/coding-agent-doctrine.js +11 -5
- package/dist/prompt/coding-agent-doctrine.js.map +1 -1
- package/dist/provider/capabilities.d.ts +5 -1
- package/dist/provider/capabilities.d.ts.map +1 -1
- package/dist/provider/capabilities.js +24 -0
- package/dist/provider/capabilities.js.map +1 -1
- package/dist/provider/fallback.d.ts.map +1 -1
- package/dist/provider/fallback.js +6 -2
- package/dist/provider/fallback.js.map +1 -1
- package/dist/public-runtime.d.ts +4 -1
- package/dist/public-runtime.d.ts.map +1 -1
- package/dist/public-runtime.js +3 -1
- package/dist/public-runtime.js.map +1 -1
- package/dist/public-tools.d.ts +2 -1
- package/dist/public-tools.d.ts.map +1 -1
- package/dist/public-tools.js +2 -1
- package/dist/public-tools.js.map +1 -1
- package/dist/public-types.d.ts +2 -0
- package/dist/public-types.d.ts.map +1 -1
- package/dist/registry/tool/execute.d.ts +3 -0
- package/dist/registry/tool/execute.d.ts.map +1 -1
- package/dist/registry/tool/execute.js +11 -80
- package/dist/registry/tool/execute.js.map +1 -1
- package/dist/run/command-gate.d.ts.map +1 -1
- package/dist/run/command-gate.js +65 -12
- package/dist/run/command-gate.js.map +1 -1
- package/dist/run/index.d.ts +2 -0
- package/dist/run/index.d.ts.map +1 -1
- package/dist/run/index.js +1 -0
- package/dist/run/index.js.map +1 -1
- package/dist/run/memory-promoter.d.ts +3 -35
- package/dist/run/memory-promoter.d.ts.map +1 -1
- package/dist/run/memory-promoter.js +32 -40
- package/dist/run/memory-promoter.js.map +1 -1
- package/dist/run/memory-recall.d.ts +25 -0
- package/dist/run/memory-recall.d.ts.map +1 -0
- package/dist/run/memory-recall.js +228 -0
- package/dist/run/memory-recall.js.map +1 -0
- package/dist/run/reporter.d.ts.map +1 -1
- package/dist/run/reporter.js +2 -0
- package/dist/run/reporter.js.map +1 -1
- package/dist/run/token-budget.d.ts +12 -4
- package/dist/run/token-budget.d.ts.map +1 -1
- package/dist/run/token-budget.js +49 -14
- package/dist/run/token-budget.js.map +1 -1
- package/dist/run/workspace-fingerprint.d.ts +10 -3
- package/dist/run/workspace-fingerprint.d.ts.map +1 -1
- package/dist/run/workspace-fingerprint.js +17 -8
- package/dist/run/workspace-fingerprint.js.map +1 -1
- package/dist/runtime/query/checkpoint.d.ts +14 -0
- package/dist/runtime/query/checkpoint.d.ts.map +1 -1
- package/dist/runtime/query/checkpoint.js +82 -1
- package/dist/runtime/query/checkpoint.js.map +1 -1
- package/dist/runtime/query/executor.d.ts +8 -3
- package/dist/runtime/query/executor.d.ts.map +1 -1
- package/dist/runtime/query/executor.js +94 -30
- package/dist/runtime/query/executor.js.map +1 -1
- package/dist/runtime/query/index.d.ts +7 -8
- package/dist/runtime/query/index.d.ts.map +1 -1
- package/dist/runtime/query/index.js +55 -7
- package/dist/runtime/query/index.js.map +1 -1
- package/dist/runtime/query/iteration/index.d.ts +12 -0
- package/dist/runtime/query/iteration/index.d.ts.map +1 -1
- package/dist/runtime/query/iteration/index.js +348 -38
- package/dist/runtime/query/iteration/index.js.map +1 -1
- package/dist/runtime/query/iteration/native-output.d.ts +10 -0
- package/dist/runtime/query/iteration/native-output.d.ts.map +1 -0
- package/dist/runtime/query/iteration/native-output.js +32 -0
- package/dist/runtime/query/iteration/native-output.js.map +1 -0
- package/dist/runtime/query/iteration/phases/advisory.d.ts.map +1 -1
- package/dist/runtime/query/iteration/phases/advisory.js +18 -13
- package/dist/runtime/query/iteration/phases/advisory.js.map +1 -1
- package/dist/runtime/query/iteration/phases/compaction.d.ts +2 -0
- package/dist/runtime/query/iteration/phases/compaction.d.ts.map +1 -1
- package/dist/runtime/query/iteration/phases/compaction.js +32 -11
- package/dist/runtime/query/iteration/phases/compaction.js.map +1 -1
- package/dist/runtime/query/iteration/phases/context.d.ts +9 -0
- package/dist/runtime/query/iteration/phases/context.d.ts.map +1 -1
- package/dist/runtime/query/iteration/phases/context.js.map +1 -1
- package/dist/runtime/query/iteration/phases/tool-review.d.ts.map +1 -1
- package/dist/runtime/query/iteration/phases/tool-review.js +1 -1
- package/dist/runtime/query/iteration/phases/tool-review.js.map +1 -1
- package/dist/runtime/query/iteration/phases/working-memory.d.ts +1 -1
- package/dist/runtime/query/iteration/phases/working-memory.d.ts.map +1 -1
- package/dist/runtime/query/iteration/phases/working-memory.js +23 -6
- package/dist/runtime/query/iteration/phases/working-memory.js.map +1 -1
- package/dist/runtime/query/iteration/stream-turn.d.ts.map +1 -1
- package/dist/runtime/query/iteration/stream-turn.js +12 -0
- package/dist/runtime/query/iteration/stream-turn.js.map +1 -1
- package/dist/runtime/query/observation-context.d.ts +10 -0
- package/dist/runtime/query/observation-context.d.ts.map +1 -0
- package/dist/runtime/query/observation-context.js +84 -0
- package/dist/runtime/query/observation-context.js.map +1 -0
- package/dist/runtime/query/request-context.d.ts +30 -0
- package/dist/runtime/query/request-context.d.ts.map +1 -0
- package/dist/runtime/query/request-context.js +76 -0
- package/dist/runtime/query/request-context.js.map +1 -0
- package/dist/runtime/query/request-rich-content.d.ts.map +1 -1
- package/dist/runtime/query/request-rich-content.js +6 -3
- package/dist/runtime/query/request-rich-content.js.map +1 -1
- package/dist/runtime/query/review-policy.d.ts +3 -0
- package/dist/runtime/query/review-policy.d.ts.map +1 -1
- package/dist/runtime/query/review-policy.js +4 -1
- package/dist/runtime/query/review-policy.js.map +1 -1
- package/dist/runtime/query/steering.d.ts +6 -2
- package/dist/runtime/query/steering.d.ts.map +1 -1
- package/dist/runtime/query/steering.js +17 -2
- package/dist/runtime/query/steering.js.map +1 -1
- package/dist/runtime/query/tool-call-budget.d.ts +19 -0
- package/dist/runtime/query/tool-call-budget.d.ts.map +1 -0
- package/dist/runtime/query/tool-call-budget.js +110 -0
- package/dist/runtime/query/tool-call-budget.js.map +1 -0
- package/dist/runtime/query/tooling.d.ts +3 -0
- package/dist/runtime/query/tooling.d.ts.map +1 -1
- package/dist/runtime/query/tooling.js +5 -0
- package/dist/runtime/query/tooling.js.map +1 -1
- package/dist/sandbox/file-walk-program.d.ts.map +1 -1
- package/dist/sandbox/file-walk-program.js +8 -0
- package/dist/sandbox/file-walk-program.js.map +1 -1
- package/dist/sandbox/file-walk.d.ts.map +1 -1
- package/dist/sandbox/file-walk.js +9 -0
- package/dist/sandbox/file-walk.js.map +1 -1
- package/dist/scheduler/completion-inbox.d.ts.map +1 -1
- package/dist/scheduler/completion-inbox.js +3 -0
- package/dist/scheduler/completion-inbox.js.map +1 -1
- package/dist/scheduler/local.d.ts.map +1 -1
- package/dist/scheduler/local.js +1 -0
- package/dist/scheduler/local.js.map +1 -1
- package/dist/session/handoff/capacity.d.ts +2 -2
- package/dist/session/handoff/capacity.d.ts.map +1 -1
- package/dist/session/handoff/capacity.js +3 -2
- package/dist/session/handoff/capacity.js.map +1 -1
- package/dist/store/memory/disk.d.ts +6 -2
- package/dist/store/memory/disk.d.ts.map +1 -1
- package/dist/store/memory/disk.js +42 -25
- package/dist/store/memory/disk.js.map +1 -1
- package/dist/store/memory/index.d.ts +4 -0
- package/dist/store/memory/index.d.ts.map +1 -1
- package/dist/store/memory/index.js +55 -19
- package/dist/store/memory/index.js.map +1 -1
- package/dist/store/memory/memory.d.ts +3 -2
- package/dist/store/memory/memory.d.ts.map +1 -1
- package/dist/store/memory/memory.js +11 -2
- package/dist/store/memory/memory.js.map +1 -1
- package/dist/store/memory/operation-lock.d.ts +11 -0
- package/dist/store/memory/operation-lock.d.ts.map +1 -0
- package/dist/store/memory/operation-lock.js +94 -0
- package/dist/store/memory/operation-lock.js.map +1 -0
- package/dist/store/run/token-budget-disk.js +3 -0
- package/dist/store/run/token-budget-disk.js.map +1 -1
- package/dist/tools/builtins/computer-use.d.ts.map +1 -1
- package/dist/tools/builtins/computer-use.js +60 -10
- package/dist/tools/builtins/computer-use.js.map +1 -1
- package/dist/tools/builtins/edit.d.ts.map +1 -1
- package/dist/tools/builtins/edit.js +12 -26
- package/dist/tools/builtins/edit.js.map +1 -1
- package/dist/tools/builtins/file-write-result.d.ts +4 -0
- package/dist/tools/builtins/file-write-result.d.ts.map +1 -0
- package/dist/tools/builtins/file-write-result.js +72 -0
- package/dist/tools/builtins/file-write-result.js.map +1 -0
- package/dist/tools/builtins/glob.d.ts.map +1 -1
- package/dist/tools/builtins/glob.js +8 -1
- package/dist/tools/builtins/glob.js.map +1 -1
- package/dist/tools/builtins/grep.d.ts.map +1 -1
- package/dist/tools/builtins/grep.js +10 -0
- package/dist/tools/builtins/grep.js.map +1 -1
- package/dist/tools/builtins/job.d.ts.map +1 -1
- package/dist/tools/builtins/job.js +6 -0
- package/dist/tools/builtins/job.js.map +1 -1
- package/dist/tools/builtins/read-file.d.ts.map +1 -1
- package/dist/tools/builtins/read-file.js +10 -0
- package/dist/tools/builtins/read-file.js.map +1 -1
- package/dist/tools/builtins/run-code.d.ts +6 -0
- package/dist/tools/builtins/run-code.d.ts.map +1 -1
- package/dist/tools/builtins/run-code.js +15 -4
- package/dist/tools/builtins/run-code.js.map +1 -1
- package/dist/tools/builtins/search-tools.d.ts.map +1 -1
- package/dist/tools/builtins/search-tools.js +14 -2
- package/dist/tools/builtins/search-tools.js.map +1 -1
- package/dist/tools/builtins/write-file.d.ts.map +1 -1
- package/dist/tools/builtins/write-file.js +30 -44
- package/dist/tools/builtins/write-file.js.map +1 -1
- package/dist/tools/defineTool.d.ts +2 -0
- package/dist/tools/defineTool.d.ts.map +1 -1
- package/dist/tools/defineTool.js +3 -0
- package/dist/tools/defineTool.js.map +1 -1
- package/dist/tools/file-read-tracker.d.ts +4 -0
- package/dist/tools/file-read-tracker.d.ts.map +1 -0
- package/dist/tools/file-read-tracker.js +16 -0
- package/dist/tools/file-read-tracker.js.map +1 -0
- package/dist/tools/memory/delete.d.ts +4 -0
- package/dist/tools/memory/delete.d.ts.map +1 -0
- package/dist/tools/memory/delete.js +26 -0
- package/dist/tools/memory/delete.js.map +1 -0
- package/dist/tools/memory/index.d.ts +2 -0
- package/dist/tools/memory/index.d.ts.map +1 -1
- package/dist/tools/memory/index.js +6 -0
- package/dist/tools/memory/index.js.map +1 -1
- package/dist/tools/memory/save.d.ts.map +1 -1
- package/dist/tools/memory/save.js +3 -2
- package/dist/tools/memory/save.js.map +1 -1
- package/dist/tools/memory/search.d.ts.map +1 -1
- package/dist/tools/memory/search.js +12 -5
- package/dist/tools/memory/search.js.map +1 -1
- package/dist/tools/memory/update.d.ts +4 -0
- package/dist/tools/memory/update.d.ts.map +1 -0
- package/dist/tools/memory/update.js +47 -0
- package/dist/tools/memory/update.js.map +1 -0
- package/dist/tools/task/list.js +2 -2
- package/dist/tools/task/list.js.map +1 -1
- package/dist/types/agent/scheduler.d.ts +5 -0
- package/dist/types/agent/scheduler.d.ts.map +1 -1
- package/dist/types/agent/task.d.ts +10 -0
- package/dist/types/agent/task.d.ts.map +1 -1
- package/dist/types/computer-use/index.d.ts +6 -0
- package/dist/types/computer-use/index.d.ts.map +1 -1
- package/dist/types/computer-use/index.js.map +1 -1
- package/dist/types/errors/catalog.js +1 -1
- package/dist/types/errors/catalog.js.map +1 -1
- package/dist/types/hitl/index.d.ts +11 -1
- package/dist/types/hitl/index.d.ts.map +1 -1
- package/dist/types/hitl/index.js.map +1 -1
- package/dist/types/memory/index.d.ts +14 -1
- package/dist/types/memory/index.d.ts.map +1 -1
- package/dist/types/plugin/index.d.ts +7 -0
- package/dist/types/plugin/index.d.ts.map +1 -1
- package/dist/types/plugin/index.js.map +1 -1
- package/dist/types/project/entity.d.ts +1 -0
- package/dist/types/project/entity.d.ts.map +1 -1
- package/dist/types/provider/chat.d.ts +4 -0
- package/dist/types/provider/chat.d.ts.map +1 -1
- package/dist/types/provider/config.d.ts +4 -0
- package/dist/types/provider/config.d.ts.map +1 -1
- package/dist/types/provider/model.d.ts +4 -0
- package/dist/types/provider/model.d.ts.map +1 -1
- package/dist/types/provider/stream.d.ts +6 -0
- package/dist/types/provider/stream.d.ts.map +1 -1
- package/dist/types/run/answer-review.d.ts +2 -0
- package/dist/types/run/answer-review.d.ts.map +1 -1
- package/dist/types/run/config.d.ts +2 -0
- package/dist/types/run/config.d.ts.map +1 -1
- package/dist/types/run/events.d.ts +19 -0
- package/dist/types/run/events.d.ts.map +1 -1
- package/dist/types/run/events.js.map +1 -1
- package/dist/types/run/prepare-step.d.ts +19 -1
- package/dist/types/run/prepare-step.d.ts.map +1 -1
- package/dist/types/sandbox/index.d.ts +1 -0
- package/dist/types/sandbox/index.d.ts.map +1 -1
- package/dist/types/sandbox/index.js.map +1 -1
- package/dist/types/structured-output/index.d.ts +8 -2
- package/dist/types/structured-output/index.d.ts.map +1 -1
- package/dist/types/tool/index.d.ts +15 -0
- package/dist/types/tool/index.d.ts.map +1 -1
- package/dist/types/tool/index.js.map +1 -1
- package/dist/types/tool/presentation.d.ts +4 -0
- package/dist/types/tool/presentation.d.ts.map +1 -1
- package/dist/utils/json-snapshot.d.ts +3 -0
- package/dist/utils/json-snapshot.d.ts.map +1 -0
- package/dist/utils/json-snapshot.js +79 -0
- package/dist/utils/json-snapshot.js.map +1 -0
- package/package.json +4 -2
- package/src/bridge/a2a/mapper.ts +4 -0
- package/src/bridge/sse/mapper.ts +16 -1
- package/src/compaction/extractor.ts +21 -8
- package/src/compaction/manager.ts +11 -1
- package/src/compaction/verifier.ts +80 -18
- package/src/config/runtime.ts +2 -0
- package/src/contracts/api.ts +1 -0
- package/src/eval/harness-verification.ts +270 -0
- package/src/eval/index.ts +10 -0
- package/src/execution/code-runtime/json-value.ts +82 -0
- package/src/execution/code-runtime/worker-program.ts +239 -0
- package/src/execution/code-runtime/worker.ts +164 -111
- package/src/manager/agent/lifecycle.ts +352 -54
- package/src/manager/run/persistence.ts +7 -0
- package/src/prompt/coding-agent-doctrine.ts +11 -5
- package/src/provider/capabilities.ts +41 -1
- package/src/provider/fallback.ts +9 -2
- package/src/public-runtime.ts +6 -0
- package/src/public-tools.ts +7 -1
- package/src/public-types.ts +7 -0
- package/src/registry/tool/execute.ts +17 -79
- package/src/run/command-gate.ts +61 -13
- package/src/run/index.ts +2 -0
- package/src/run/memory-promoter.ts +32 -40
- package/src/run/memory-recall.ts +254 -0
- package/src/run/reporter.ts +2 -0
- package/src/run/token-budget.ts +55 -14
- package/src/run/workspace-fingerprint.ts +17 -8
- package/src/runtime/query/checkpoint.ts +96 -2
- package/src/runtime/query/executor.ts +100 -29
- package/src/runtime/query/index.ts +76 -16
- package/src/runtime/query/iteration/index.ts +405 -46
- package/src/runtime/query/iteration/native-output.ts +35 -0
- package/src/runtime/query/iteration/phases/advisory.ts +21 -11
- package/src/runtime/query/iteration/phases/compaction.ts +36 -14
- package/src/runtime/query/iteration/phases/context.ts +9 -0
- package/src/runtime/query/iteration/phases/tool-review.ts +5 -1
- package/src/runtime/query/iteration/phases/working-memory.ts +23 -5
- package/src/runtime/query/iteration/stream-turn.ts +15 -0
- package/src/runtime/query/observation-context.ts +86 -0
- package/src/runtime/query/request-context.ts +103 -0
- package/src/runtime/query/request-rich-content.ts +8 -3
- package/src/runtime/query/review-policy.ts +7 -1
- package/src/runtime/query/steering.ts +19 -2
- package/src/runtime/query/tool-call-budget.ts +115 -0
- package/src/runtime/query/tooling.ts +8 -0
- package/src/sandbox/file-walk-program.ts +8 -0
- package/src/sandbox/file-walk.ts +9 -0
- package/src/scheduler/completion-inbox.ts +3 -0
- package/src/scheduler/local.ts +1 -0
- package/src/session/handoff/capacity.ts +7 -3
- package/src/store/memory/disk.ts +52 -30
- package/src/store/memory/index.ts +75 -27
- package/src/store/memory/memory.ts +18 -6
- package/src/store/memory/operation-lock.ts +99 -0
- package/src/store/run/token-budget-disk.ts +3 -0
- package/src/tools/builtins/computer-use.ts +61 -7
- package/src/tools/builtins/edit.ts +12 -27
- package/src/tools/builtins/file-write-result.ts +84 -0
- package/src/tools/builtins/glob.ts +7 -1
- package/src/tools/builtins/grep.ts +10 -0
- package/src/tools/builtins/job.ts +8 -0
- package/src/tools/builtins/read-file.ts +10 -0
- package/src/tools/builtins/run-code.ts +24 -5
- package/src/tools/builtins/search-tools.ts +18 -3
- package/src/tools/builtins/write-file.ts +39 -44
- package/src/tools/defineTool.ts +5 -0
- package/src/tools/file-read-tracker.ts +16 -0
- package/src/tools/memory/delete.ts +29 -0
- package/src/tools/memory/index.ts +6 -0
- package/src/tools/memory/save.ts +4 -2
- package/src/tools/memory/search.ts +12 -5
- package/src/tools/memory/update.ts +50 -0
- package/src/tools/task/list.ts +2 -2
- package/src/types/agent/scheduler.ts +6 -0
- package/src/types/agent/task.ts +13 -0
- package/src/types/computer-use/index.ts +6 -0
- package/src/types/errors/catalog.ts +1 -1
- package/src/types/hitl/index.ts +11 -1
- package/src/types/memory/index.ts +16 -1
- package/src/types/plugin/index.ts +10 -0
- package/src/types/project/entity.ts +1 -0
- package/src/types/provider/chat.ts +2 -0
- package/src/types/provider/config.ts +4 -0
- package/src/types/provider/model.ts +4 -0
- package/src/types/provider/stream.ts +7 -0
- package/src/types/run/answer-review.ts +2 -0
- package/src/types/run/config.ts +2 -0
- package/src/types/run/events.ts +20 -0
- package/src/types/run/prepare-step.ts +19 -1
- package/src/types/sandbox/index.ts +1 -0
- package/src/types/structured-output/index.ts +15 -2
- package/src/types/tool/index.ts +16 -0
- package/src/types/tool/presentation.ts +4 -0
- package/src/utils/json-snapshot.ts +76 -0
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
/** Clone JSON data without invoking getters or silently dropping values. */
|
|
2
|
+
export function cloneJsonValue(value, freeze, path = '$') {
|
|
3
|
+
const active = new WeakSet();
|
|
4
|
+
const copies = new WeakMap();
|
|
5
|
+
const clone = (candidate, at) => {
|
|
6
|
+
if (candidate === null || typeof candidate === 'string' || typeof candidate === 'boolean') {
|
|
7
|
+
return candidate;
|
|
8
|
+
}
|
|
9
|
+
if (typeof candidate === 'number') {
|
|
10
|
+
if (!Number.isFinite(candidate) || Object.is(candidate, -0)) {
|
|
11
|
+
throw new TypeError(`${at} must be a finite JSON number`);
|
|
12
|
+
}
|
|
13
|
+
return candidate;
|
|
14
|
+
}
|
|
15
|
+
if (typeof candidate !== 'object') {
|
|
16
|
+
throw new TypeError(`${at} must be a JSON value, not ${typeof candidate}`);
|
|
17
|
+
}
|
|
18
|
+
if (active.has(candidate))
|
|
19
|
+
throw new TypeError(`${at} contains a cycle`);
|
|
20
|
+
const existing = copies.get(candidate);
|
|
21
|
+
if (existing)
|
|
22
|
+
return existing;
|
|
23
|
+
active.add(candidate);
|
|
24
|
+
try {
|
|
25
|
+
if (Array.isArray(candidate)) {
|
|
26
|
+
const extra = Reflect.ownKeys(candidate).filter((key) => key !== 'length' && (typeof key !== 'string' || !/^(0|[1-9]\d*)$/.test(key)));
|
|
27
|
+
if (extra.length > 0)
|
|
28
|
+
throw new TypeError(`${at} has non-JSON array properties`);
|
|
29
|
+
const result = new Array(candidate.length);
|
|
30
|
+
copies.set(candidate, result);
|
|
31
|
+
for (let index = 0; index < candidate.length; index++) {
|
|
32
|
+
const descriptor = Object.getOwnPropertyDescriptor(candidate, String(index));
|
|
33
|
+
if (!descriptor)
|
|
34
|
+
throw new TypeError(`${at}[${index}] is a sparse array hole`);
|
|
35
|
+
if (!descriptor.enumerable || !('value' in descriptor)) {
|
|
36
|
+
throw new TypeError(`${at}[${index}] must be an enumerable data property`);
|
|
37
|
+
}
|
|
38
|
+
result[index] = clone(descriptor.value, `${at}[${index}]`);
|
|
39
|
+
}
|
|
40
|
+
if (freeze)
|
|
41
|
+
Object.freeze(result);
|
|
42
|
+
return result;
|
|
43
|
+
}
|
|
44
|
+
const prototype = Object.getPrototypeOf(candidate);
|
|
45
|
+
if (prototype !== Object.prototype && prototype !== null) {
|
|
46
|
+
throw new TypeError(`${at} must be a plain JSON object`);
|
|
47
|
+
}
|
|
48
|
+
// JSON does not preserve prototypes. Canonicalize both admitted plain
|
|
49
|
+
// shapes to an ordinary object so a disk checkpoint round-trip compares
|
|
50
|
+
// equal to a fresh preparation of the same semantic value. Properties
|
|
51
|
+
// are still defined explicitly, so a literal "__proto__" key remains
|
|
52
|
+
// data rather than changing this object's prototype.
|
|
53
|
+
const result = {};
|
|
54
|
+
copies.set(candidate, result);
|
|
55
|
+
for (const key of Reflect.ownKeys(candidate)) {
|
|
56
|
+
if (typeof key !== 'string')
|
|
57
|
+
throw new TypeError(`${at} has a symbol property`);
|
|
58
|
+
const descriptor = Object.getOwnPropertyDescriptor(candidate, key);
|
|
59
|
+
if (!descriptor?.enumerable || !('value' in descriptor)) {
|
|
60
|
+
throw new TypeError(`${at}.${key} must be an enumerable data property`);
|
|
61
|
+
}
|
|
62
|
+
Object.defineProperty(result, key, {
|
|
63
|
+
value: clone(descriptor.value, `${at}.${key}`),
|
|
64
|
+
enumerable: true,
|
|
65
|
+
writable: !freeze,
|
|
66
|
+
configurable: !freeze,
|
|
67
|
+
});
|
|
68
|
+
}
|
|
69
|
+
if (freeze)
|
|
70
|
+
Object.freeze(result);
|
|
71
|
+
return result;
|
|
72
|
+
}
|
|
73
|
+
finally {
|
|
74
|
+
active.delete(candidate);
|
|
75
|
+
}
|
|
76
|
+
};
|
|
77
|
+
return clone(value, path);
|
|
78
|
+
}
|
|
79
|
+
//# sourceMappingURL=json-snapshot.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"json-snapshot.js","sourceRoot":"","sources":["../../src/utils/json-snapshot.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@namzu/sdk",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "38.0.0",
|
|
4
4
|
"description": "Open-source AI agent SDK with a built-in runtime. Nothing between you and your agents.",
|
|
5
5
|
"license": "FSL-1.1-MIT",
|
|
6
6
|
"engines": {
|
|
@@ -73,8 +73,10 @@
|
|
|
73
73
|
"zod-to-json-schema": "^3.23.0"
|
|
74
74
|
},
|
|
75
75
|
"dependencies": {
|
|
76
|
+
"@jitl/quickjs-wasmfile-release-sync": "0.32.0",
|
|
76
77
|
"brace-expansion": "^2.1.4",
|
|
77
|
-
"minimatch": "^9.0.9"
|
|
78
|
+
"minimatch": "^9.0.9",
|
|
79
|
+
"quickjs-emscripten-core": "0.32.0"
|
|
78
80
|
},
|
|
79
81
|
"scripts": {
|
|
80
82
|
"build": "tsc --build",
|
package/src/bridge/a2a/mapper.ts
CHANGED
|
@@ -46,6 +46,10 @@ type A2ATransform<K extends RunEvent['type']> =
|
|
|
46
46
|
const MAPPING: {
|
|
47
47
|
[K in RunEvent['type']]: A2ATransform<K>
|
|
48
48
|
} = {
|
|
49
|
+
// Internal cumulative admission ledger, not a public UI event.
|
|
50
|
+
tool_calls_admitted: null,
|
|
51
|
+
// Hosted activity is retained in the run log; A2A exposes the resulting answer.
|
|
52
|
+
hosted_tool: null,
|
|
49
53
|
run_started: (e, ctx) => statusEvent(e.runId, 'running', false, ctx),
|
|
50
54
|
|
|
51
55
|
run_completed: (e, ctx) => {
|
package/src/bridge/sse/mapper.ts
CHANGED
|
@@ -34,6 +34,16 @@ type EventTransform<K extends RunEvent['type']> = {
|
|
|
34
34
|
const MAPPING: {
|
|
35
35
|
[K in RunEvent['type']]: EventTransform<K>
|
|
36
36
|
} = {
|
|
37
|
+
// Internal cumulative admission ledger, not a public UI event.
|
|
38
|
+
tool_calls_admitted: null,
|
|
39
|
+
hosted_tool: {
|
|
40
|
+
wire: 'hosted.tool',
|
|
41
|
+
transform: (e, runId) => ({
|
|
42
|
+
run_id: runId,
|
|
43
|
+
iteration: e.iteration,
|
|
44
|
+
tool: e.tool,
|
|
45
|
+
}),
|
|
46
|
+
},
|
|
37
47
|
run_started: {
|
|
38
48
|
wire: 'run.started',
|
|
39
49
|
transform: (e, runId) => ({
|
|
@@ -52,7 +62,12 @@ const MAPPING: {
|
|
|
52
62
|
// needs in order to see supervision loosen.
|
|
53
63
|
approval_policy_changed: {
|
|
54
64
|
wire: 'approval_policy.changed',
|
|
55
|
-
transform: (e, runId) => ({
|
|
65
|
+
transform: (e, runId) => ({
|
|
66
|
+
run_id: runId,
|
|
67
|
+
from: e.from,
|
|
68
|
+
to: e.to,
|
|
69
|
+
reason: e.reason,
|
|
70
|
+
}),
|
|
56
71
|
},
|
|
57
72
|
|
|
58
73
|
iteration_completed: {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import type { CompactionConfig } from '../config/runtime.js'
|
|
2
2
|
import { EDIT_TOOLS, READ_TOOLS, SEARCH_TOOLS, SHELL_TOOLS } from '../constants/compaction/index.js'
|
|
3
|
-
import type
|
|
3
|
+
import { type WorkingStateManager, truncateStateText } from './manager.js'
|
|
4
4
|
|
|
5
5
|
function tryParseJson(raw: string): Record<string, unknown> | null {
|
|
6
6
|
try {
|
|
@@ -25,12 +25,17 @@ function splitSentences(text: string): string[] {
|
|
|
25
25
|
}
|
|
26
26
|
|
|
27
27
|
function isSubstantive(sentence: string): boolean {
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
28
|
+
// Discard standalone acknowledgements, not sentences beginning with one:
|
|
29
|
+
// "No production writes" and even "Node 24" used to match the `no` prefix.
|
|
30
|
+
return !/^(ok|okay|sure|alright|got it|understood|i see|great|perfect|excellent|good|nice|cool|right|yes|no|thanks)[.!?]*$/i.test(
|
|
31
|
+
sentence,
|
|
32
|
+
)
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
function isExplicitAssistantDecision(sentence: string): boolean {
|
|
36
|
+
return /^(?:(?:the|my|our) decision is\b|decision\s*:|(?:i|we)(?: have|'ve)? (?:decided|chose|chosen)\b)/i.test(
|
|
37
|
+
sentence,
|
|
38
|
+
)
|
|
34
39
|
}
|
|
35
40
|
|
|
36
41
|
function truncateResult(result: string, maxLen: number): string {
|
|
@@ -199,6 +204,14 @@ export function extractFromAssistantMessage(
|
|
|
199
204
|
const selected = substantive.slice(0, config.maxSentencesPerTurn)
|
|
200
205
|
|
|
201
206
|
for (const sentence of selected) {
|
|
202
|
-
|
|
207
|
+
if (isExplicitAssistantDecision(sentence)) {
|
|
208
|
+
// A recorded assertion, not verified truth or an instruction from the
|
|
209
|
+
// user. Keep that provenance when a host later promotes the decision.
|
|
210
|
+
manager.addDecision(
|
|
211
|
+
truncateStateText(`Assistant stated: ${sentence}`, config.maxCharsPerNote),
|
|
212
|
+
)
|
|
213
|
+
} else {
|
|
214
|
+
manager.addAssistantNote(sentence)
|
|
215
|
+
}
|
|
203
216
|
}
|
|
204
217
|
}
|
|
@@ -13,6 +13,16 @@ export const MAX_PINS = 40
|
|
|
13
13
|
/** Characters one pin may carry; a pin is a fact, not a document. */
|
|
14
14
|
export const MAX_PIN_CHARS = 600
|
|
15
15
|
|
|
16
|
+
/** @internal Keep the omission visible within the existing character budget. */
|
|
17
|
+
export function truncateStateText(text: string, max: number): string {
|
|
18
|
+
if (max === undefined || text.length <= max) return text
|
|
19
|
+
const marker = max >= '… [truncated]'.length ? '… [truncated]' : '…'
|
|
20
|
+
let head = text.slice(0, Math.max(0, max - marker.length))
|
|
21
|
+
const last = head.charCodeAt(head.length - 1)
|
|
22
|
+
if (last >= 0xd800 && last <= 0xdbff) head = head.slice(0, -1)
|
|
23
|
+
return `${head}${marker}`
|
|
24
|
+
}
|
|
25
|
+
|
|
16
26
|
function createEmptyState(): WorkingState {
|
|
17
27
|
return {
|
|
18
28
|
task: '',
|
|
@@ -130,7 +140,7 @@ export class WorkingStateManager {
|
|
|
130
140
|
}
|
|
131
141
|
|
|
132
142
|
addUserRequirement(requirement: string): void {
|
|
133
|
-
const truncated = requirement
|
|
143
|
+
const truncated = truncateStateText(requirement, this.config.maxCharsPerRequirement)
|
|
134
144
|
this.pushWithEviction(
|
|
135
145
|
'userRequirements',
|
|
136
146
|
this.state.userRequirements,
|
|
@@ -2,7 +2,7 @@ import type { CompactionConfig } from '../config/runtime.js'
|
|
|
2
2
|
import { collectChatCompletion } from '../provider/collect-chat-completion.js'
|
|
3
3
|
import { resolveStreamIdleTimeoutMs, withStreamIdleTimeout } from '../provider/idle-timeout.js'
|
|
4
4
|
import type { TokenUsage } from '../types/common/index.js'
|
|
5
|
-
import type { Message } from '../types/message/index.js'
|
|
5
|
+
import type { Message, MessageAttachment, ToolResultBlock } from '../types/message/index.js'
|
|
6
6
|
import type { LLMProvider } from '../types/provider/interface.js'
|
|
7
7
|
import type { WorkingStateManager } from './manager.js'
|
|
8
8
|
import { serializeState } from './serializer.js'
|
|
@@ -20,28 +20,90 @@ If the structured state is complete, respond with exactly: COMPLETE
|
|
|
20
20
|
|
|
21
21
|
If something important is missing, respond with a brief bullet list of the missing items (no preamble, just the bullets). Each bullet should be a single concise sentence.`
|
|
22
22
|
|
|
23
|
-
function
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
23
|
+
function* attachmentExcerpt(
|
|
24
|
+
attachment: MessageAttachment | Exclude<ToolResultBlock, { type: 'text' }>,
|
|
25
|
+
): Generator<string> {
|
|
26
|
+
const kind =
|
|
27
|
+
attachment.type === 'stored'
|
|
28
|
+
? attachment.kind
|
|
29
|
+
: attachment.type === 'document'
|
|
30
|
+
? 'document'
|
|
31
|
+
: 'image'
|
|
32
|
+
yield `[${kind}`
|
|
33
|
+
if ('name' in attachment && attachment.name) {
|
|
34
|
+
yield ' "'
|
|
35
|
+
yield attachment.name
|
|
36
|
+
yield '"'
|
|
37
|
+
}
|
|
38
|
+
yield ': '
|
|
39
|
+
yield attachment.mediaType
|
|
40
|
+
yield ' — not included in this text excerpt]'
|
|
41
|
+
}
|
|
31
42
|
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
43
|
+
/** Visible evidence only: never stringify a whole message or its attachment bytes. */
|
|
44
|
+
function* conversationExcerpt(messages: readonly Message[]): Generator<string> {
|
|
45
|
+
let first = true
|
|
46
|
+
for (const message of messages) {
|
|
47
|
+
const hasDetails =
|
|
48
|
+
message.role === 'tool' ||
|
|
49
|
+
(message.role === 'assistant' && message.toolCalls?.length) ||
|
|
50
|
+
(message.role === 'user' && message.attachments?.length)
|
|
51
|
+
if (!message.content && !hasDetails) continue
|
|
52
|
+
if (!first) yield '\n\n'
|
|
53
|
+
first = false
|
|
54
|
+
yield `[${message.role}]: `
|
|
55
|
+
if (message.role === 'tool') {
|
|
56
|
+
yield '[tool result '
|
|
57
|
+
yield message.toolCallId
|
|
58
|
+
yield `; isError=${message.isError === true}]\n`
|
|
59
|
+
}
|
|
60
|
+
if (typeof message.content === 'string') yield message.content
|
|
61
|
+
else if (message.content) {
|
|
62
|
+
for (const [index, block] of message.content.entries()) {
|
|
63
|
+
if (index > 0) yield '\n'
|
|
64
|
+
if (block.type === 'text') yield block.text
|
|
65
|
+
else yield* attachmentExcerpt(block)
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
if (message.role === 'assistant') {
|
|
69
|
+
for (const call of message.toolCalls ?? []) {
|
|
70
|
+
yield '\n[tool call '
|
|
71
|
+
yield call.id
|
|
72
|
+
yield '] '
|
|
73
|
+
yield call.function.name
|
|
74
|
+
yield '('
|
|
75
|
+
yield call.function.arguments
|
|
76
|
+
yield ')'
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
if (message.role === 'user') {
|
|
80
|
+
for (const attachment of message.attachments ?? []) {
|
|
81
|
+
yield '\n'
|
|
82
|
+
yield* attachmentExcerpt(attachment)
|
|
36
83
|
}
|
|
37
|
-
break
|
|
38
84
|
}
|
|
39
|
-
|
|
40
|
-
lines.push(`${prefix}${content}`)
|
|
41
|
-
charCount += prefix.length + content.length
|
|
42
85
|
}
|
|
86
|
+
}
|
|
43
87
|
|
|
44
|
-
|
|
88
|
+
function truncateMessages(messages: readonly Message[], budget: number): string {
|
|
89
|
+
if (budget <= 0) return ''
|
|
90
|
+
const parts: string[] = []
|
|
91
|
+
let remaining = budget
|
|
92
|
+
for (const part of conversationExcerpt(messages)) {
|
|
93
|
+
if (part.length > remaining) {
|
|
94
|
+
parts.push(part.slice(0, remaining))
|
|
95
|
+
// Role labels, separators and the omission marker all consume the
|
|
96
|
+
// same budget. Consume fragments lazily so huge arguments and rich
|
|
97
|
+
// results cannot bypass the cap or require a full serialized copy.
|
|
98
|
+
let prefix = parts.join('').slice(0, budget - 1)
|
|
99
|
+
const last = prefix.charCodeAt(prefix.length - 1)
|
|
100
|
+
if (last >= 0xd800 && last <= 0xdbff) prefix = prefix.slice(0, -1)
|
|
101
|
+
return `${prefix}…`
|
|
102
|
+
}
|
|
103
|
+
parts.push(part)
|
|
104
|
+
remaining -= part.length
|
|
105
|
+
}
|
|
106
|
+
return parts.join('')
|
|
45
107
|
}
|
|
46
108
|
|
|
47
109
|
/**
|
package/src/config/runtime.ts
CHANGED
|
@@ -17,6 +17,8 @@ export const TaskRouterConfigSchema = z
|
|
|
17
17
|
.optional()
|
|
18
18
|
|
|
19
19
|
export const CompactionConfigSchema = z.object({
|
|
20
|
+
/** Request-only exact duplicate observation masking. Enabled unless false; disabled strategy opts out too. */
|
|
21
|
+
deduplicateObservations: z.boolean().optional(),
|
|
20
22
|
/**
|
|
21
23
|
* `salience` is the default: every message scored without a model, the
|
|
22
24
|
* context held from half the window. `structured` is the previous
|
package/src/contracts/api.ts
CHANGED
|
@@ -197,6 +197,7 @@ export type StreamEventType =
|
|
|
197
197
|
* know the answer it is reading came from a provider it did not ask for —
|
|
198
198
|
* at a different price, and possibly a different quality.
|
|
199
199
|
*/
|
|
200
|
+
| 'hosted.tool'
|
|
200
201
|
| 'provider.fallback'
|
|
201
202
|
| 'tool.executing'
|
|
202
203
|
/** Ephemeral progress from a long-running tool. Not in the transcript. */
|
|
@@ -0,0 +1,270 @@
|
|
|
1
|
+
import type { CaseResult } from './types.js'
|
|
2
|
+
|
|
3
|
+
/** A host-owned outcome, with enough identity to check pairing and cite its trace. */
|
|
4
|
+
export interface HarnessTrial {
|
|
5
|
+
taskId: string
|
|
6
|
+
trial: number
|
|
7
|
+
/** Environment/seed/model/limits fingerprint. Equal within a pair, fresh in confirmation. */
|
|
8
|
+
conditions: string
|
|
9
|
+
trajectoryId: string
|
|
10
|
+
result: CaseResult
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export interface HarnessAttribution {
|
|
14
|
+
taskId: string
|
|
15
|
+
effect: 'improvement' | 'regression' | 'unresolved'
|
|
16
|
+
reason: string
|
|
17
|
+
baselineTrajectories: readonly string[]
|
|
18
|
+
candidateTrajectories: readonly string[]
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export interface HarnessVerificationBatch {
|
|
22
|
+
baselineRevision: string
|
|
23
|
+
candidateRevision: string
|
|
24
|
+
baseline: readonly HarnessTrial[]
|
|
25
|
+
candidate: readonly HarnessTrial[]
|
|
26
|
+
/** Supplied by an independent trace reviewer, never inferred from scores alone. */
|
|
27
|
+
attributions: readonly HarnessAttribution[]
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export type HarnessBehaviorStatus =
|
|
31
|
+
| 'recovered'
|
|
32
|
+
| 'stable-success'
|
|
33
|
+
| 'regressed'
|
|
34
|
+
| 'still-failing'
|
|
35
|
+
| 'mixed'
|
|
36
|
+
| 'inconclusive'
|
|
37
|
+
|
|
38
|
+
export interface HarnessTaskComparison {
|
|
39
|
+
taskId: string
|
|
40
|
+
status: HarnessBehaviorStatus
|
|
41
|
+
baselinePasses: number
|
|
42
|
+
candidatePasses: number
|
|
43
|
+
trials: number
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
export interface HarnessComparison {
|
|
47
|
+
tasks: readonly HarnessTaskComparison[]
|
|
48
|
+
/** Paired trial pass-rate difference, not held-out pass@1 or causal evidence. */
|
|
49
|
+
passRateDelta: number | null
|
|
50
|
+
positiveEvidence: readonly string[]
|
|
51
|
+
regressions: readonly string[]
|
|
52
|
+
unresolved: readonly string[]
|
|
53
|
+
/** Actual recorded consumption from BOTH sides, including unsuccessful runs. */
|
|
54
|
+
usage: { rollouts: number; tokens: number; costUsd: number; durationMs: number }
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
function nonempty(value: string): boolean {
|
|
58
|
+
return typeof value === 'string' && value.trim().length > 0
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
function key(trial: HarnessTrial): string {
|
|
62
|
+
return JSON.stringify([trial.taskId, trial.trial])
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
function indexTrials(trials: readonly HarnessTrial[]): Map<string, HarnessTrial> {
|
|
66
|
+
const result = new Map<string, HarnessTrial>()
|
|
67
|
+
const traces = new Set<string>()
|
|
68
|
+
for (const trial of trials) {
|
|
69
|
+
if (
|
|
70
|
+
!nonempty(trial.taskId) ||
|
|
71
|
+
!nonempty(trial.conditions) ||
|
|
72
|
+
!nonempty(trial.trajectoryId) ||
|
|
73
|
+
!Number.isSafeInteger(trial.trial) ||
|
|
74
|
+
trial.trial < 0
|
|
75
|
+
)
|
|
76
|
+
throw new Error(
|
|
77
|
+
'A harness trial needs a task, nonnegative trial index, conditions and trajectory ID.',
|
|
78
|
+
)
|
|
79
|
+
if (result.has(key(trial)) || traces.has(trial.trajectoryId))
|
|
80
|
+
throw new Error('Duplicate harness trial or trajectory ID.')
|
|
81
|
+
result.set(key(trial), trial)
|
|
82
|
+
traces.add(trial.trajectoryId)
|
|
83
|
+
}
|
|
84
|
+
return result
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
function measured(trial: HarnessTrial): boolean {
|
|
88
|
+
const { result } = trial
|
|
89
|
+
const scores = Object.values(result.scores)
|
|
90
|
+
return (
|
|
91
|
+
!result.run.error &&
|
|
92
|
+
(result.status === 'passed' || result.status === 'failed') &&
|
|
93
|
+
scores.length > 0 &&
|
|
94
|
+
scores.every((s) => !s.unavailable && Number.isFinite(s.score) && s.score >= 0 && s.score <= 1)
|
|
95
|
+
)
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
/** HarnessLens Table 6 comparison plus explicit, trace-linked attribution. No model calls. */
|
|
99
|
+
export function compareHarnessTrials(batch: HarnessVerificationBatch): HarnessComparison {
|
|
100
|
+
if (
|
|
101
|
+
!nonempty(batch.baselineRevision) ||
|
|
102
|
+
!nonempty(batch.candidateRevision) ||
|
|
103
|
+
batch.baselineRevision === batch.candidateRevision
|
|
104
|
+
)
|
|
105
|
+
throw new Error('Distinct baseline and candidate revisions are required.')
|
|
106
|
+
const baseline = indexTrials(batch.baseline)
|
|
107
|
+
const candidate = indexTrials(batch.candidate)
|
|
108
|
+
if (!baseline.size || baseline.size !== candidate.size)
|
|
109
|
+
throw new Error('Complete paired trials are required.')
|
|
110
|
+
const baselineTraces = new Set(batch.baseline.map((t) => t.trajectoryId))
|
|
111
|
+
if (batch.candidate.some((t) => baselineTraces.has(t.trajectoryId)))
|
|
112
|
+
throw new Error('Baseline and candidate must have distinct trajectories.')
|
|
113
|
+
const groups = new Map<string, HarnessTrial[]>()
|
|
114
|
+
for (const [id, before] of baseline) {
|
|
115
|
+
const after = candidate.get(id)
|
|
116
|
+
if (!after || before.conditions !== after.conditions)
|
|
117
|
+
throw new Error('Harness trial conditions do not match.')
|
|
118
|
+
const group = groups.get(before.taskId) ?? []
|
|
119
|
+
group.push(before)
|
|
120
|
+
groups.set(before.taskId, group)
|
|
121
|
+
}
|
|
122
|
+
const tasks: HarnessTaskComparison[] = []
|
|
123
|
+
for (const [taskId, before] of groups) {
|
|
124
|
+
if (new Set(before.map((t) => t.conditions)).size !== before.length)
|
|
125
|
+
throw new Error('Repeated trials need distinct controlled conditions.')
|
|
126
|
+
const after = before.map((t) => candidate.get(key(t)) as HarnessTrial)
|
|
127
|
+
const b = before.filter((t) => t.result.status === 'passed').length
|
|
128
|
+
const c = after.filter((t) => t.result.status === 'passed').length
|
|
129
|
+
const status: HarnessBehaviorStatus = ![...before, ...after].every(measured)
|
|
130
|
+
? 'inconclusive'
|
|
131
|
+
: b === 0 && c > 0
|
|
132
|
+
? 'recovered'
|
|
133
|
+
: b > 0 && c === after.length
|
|
134
|
+
? 'stable-success'
|
|
135
|
+
: b > 0 && c === 0
|
|
136
|
+
? 'regressed'
|
|
137
|
+
: b === 0 && c === 0
|
|
138
|
+
? 'still-failing'
|
|
139
|
+
: 'mixed'
|
|
140
|
+
tasks.push({ taskId, status, baselinePasses: b, candidatePasses: c, trials: before.length })
|
|
141
|
+
}
|
|
142
|
+
const positive = new Set<string>()
|
|
143
|
+
const regressions = new Set<string>()
|
|
144
|
+
const unresolved = new Set(
|
|
145
|
+
tasks.filter((t) => t.status === 'inconclusive' || t.status === 'mixed').map((t) => t.taskId),
|
|
146
|
+
)
|
|
147
|
+
// Conservative Namzu policy: even an unattributed observed regression blocks promotion.
|
|
148
|
+
for (const task of tasks) if (task.status === 'regressed') regressions.add(task.taskId)
|
|
149
|
+
for (const evidence of batch.attributions) {
|
|
150
|
+
const task = tasks.find((t) => t.taskId === evidence.taskId)
|
|
151
|
+
const cites = (ids: readonly string[], trials: readonly HarnessTrial[]) =>
|
|
152
|
+
ids.length > 0 &&
|
|
153
|
+
ids.every((id) => trials.some((t) => t.taskId === evidence.taskId && t.trajectoryId === id))
|
|
154
|
+
if (
|
|
155
|
+
!task ||
|
|
156
|
+
!nonempty(evidence.reason) ||
|
|
157
|
+
!cites(evidence.baselineTrajectories, batch.baseline) ||
|
|
158
|
+
!cites(evidence.candidateTrajectories, batch.candidate) ||
|
|
159
|
+
!['improvement', 'regression', 'unresolved'].includes(evidence.effect)
|
|
160
|
+
)
|
|
161
|
+
throw new Error('Attribution must explain and cite both sides of an existing task.')
|
|
162
|
+
if (evidence.effect === 'regression') regressions.add(task.taskId)
|
|
163
|
+
else if (evidence.effect === 'unresolved') unresolved.add(task.taskId)
|
|
164
|
+
else if (
|
|
165
|
+
task.status === 'recovered' ||
|
|
166
|
+
(task.status === 'stable-success' && task.candidatePasses > task.baselinePasses)
|
|
167
|
+
)
|
|
168
|
+
positive.add(task.taskId)
|
|
169
|
+
}
|
|
170
|
+
const usage = { rollouts: baseline.size * 2, tokens: 0, costUsd: 0, durationMs: 0 }
|
|
171
|
+
for (const trial of [...batch.baseline, ...batch.candidate]) {
|
|
172
|
+
const values = [
|
|
173
|
+
trial.result.run.totalTokens,
|
|
174
|
+
trial.result.run.totalCostUsd,
|
|
175
|
+
trial.result.run.durationMs,
|
|
176
|
+
]
|
|
177
|
+
if (values.some((n) => !Number.isFinite(n) || n < 0))
|
|
178
|
+
throw new Error('Invalid recorded harness usage.')
|
|
179
|
+
usage.tokens += trial.result.run.totalTokens
|
|
180
|
+
usage.costUsd += trial.result.run.totalCostUsd
|
|
181
|
+
usage.durationMs += trial.result.run.durationMs
|
|
182
|
+
}
|
|
183
|
+
return {
|
|
184
|
+
tasks,
|
|
185
|
+
positiveEvidence: [...positive],
|
|
186
|
+
regressions: [...regressions],
|
|
187
|
+
unresolved: [...unresolved],
|
|
188
|
+
usage,
|
|
189
|
+
passRateDelta: tasks.some((t) => t.status === 'inconclusive')
|
|
190
|
+
? null
|
|
191
|
+
: tasks.reduce((sum, t) => sum + t.candidatePasses - t.baselinePasses, 0) / baseline.size,
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
export interface HarnessReview {
|
|
196
|
+
decision: 'accept' | 'reject' | 'inconclusive'
|
|
197
|
+
reason: string
|
|
198
|
+
verification: HarnessComparison
|
|
199
|
+
confirmation?: HarnessComparison
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
/**
|
|
203
|
+
* Evaluate recorded evidence; never applies a patch. Requires at least five tasks,
|
|
204
|
+
* exactly two trials per task, and a same-size confirmation with at most two reused tasks.
|
|
205
|
+
* Hosts own isolated execution, task selection, scoring and independent trace review.
|
|
206
|
+
*/
|
|
207
|
+
export function reviewHarnessCandidate(
|
|
208
|
+
verification: HarnessVerificationBatch,
|
|
209
|
+
confirmation?: HarnessVerificationBatch,
|
|
210
|
+
): HarnessReview {
|
|
211
|
+
const first = compareHarnessTrials(verification)
|
|
212
|
+
const second = confirmation ? compareHarnessTrials(confirmation) : undefined
|
|
213
|
+
const result = (decision: HarnessReview['decision'], reason: string): HarnessReview => ({
|
|
214
|
+
decision,
|
|
215
|
+
reason,
|
|
216
|
+
verification: first,
|
|
217
|
+
...(second ? { confirmation: second } : {}),
|
|
218
|
+
})
|
|
219
|
+
const sufficient = (report: HarnessComparison) =>
|
|
220
|
+
report.tasks.length >= 5 && report.tasks.every((t) => t.trials === 2)
|
|
221
|
+
if (!sufficient(first))
|
|
222
|
+
return result(
|
|
223
|
+
'inconclusive',
|
|
224
|
+
'Verification requires at least five distinct tasks and two paired trials per task.',
|
|
225
|
+
)
|
|
226
|
+
if (first.regressions.length || second?.regressions.length)
|
|
227
|
+
return result('reject', 'Observed or attributed regression blocks promotion.')
|
|
228
|
+
if (first.unresolved.length || second?.unresolved.length)
|
|
229
|
+
return result('inconclusive', 'Incomplete or ambiguous behavioral evidence.')
|
|
230
|
+
if (!first.positiveEvidence.length)
|
|
231
|
+
return result(
|
|
232
|
+
'reject',
|
|
233
|
+
'A metric increase or preservation alone is not attributable improvement.',
|
|
234
|
+
)
|
|
235
|
+
if (!confirmation || !second)
|
|
236
|
+
return result('inconclusive', 'A complete fresh confirmation round is required.')
|
|
237
|
+
if (
|
|
238
|
+
verification.baselineRevision !== confirmation.baselineRevision ||
|
|
239
|
+
verification.candidateRevision !== confirmation.candidateRevision
|
|
240
|
+
)
|
|
241
|
+
return result('inconclusive', 'Revisions changed between verification and confirmation.')
|
|
242
|
+
const firstTasks = new Set(first.tasks.map((t) => t.taskId))
|
|
243
|
+
if (
|
|
244
|
+
!sufficient(second) ||
|
|
245
|
+
second.tasks.length !== first.tasks.length ||
|
|
246
|
+
second.tasks.filter((t) => firstTasks.has(t.taskId)).length > 2
|
|
247
|
+
)
|
|
248
|
+
return result(
|
|
249
|
+
'inconclusive',
|
|
250
|
+
'Confirmation must use the same batch size with at most two reused tasks.',
|
|
251
|
+
)
|
|
252
|
+
const conditions = new Set(verification.baseline.map((t) => t.conditions))
|
|
253
|
+
const traces = new Set(
|
|
254
|
+
[...verification.baseline, ...verification.candidate].map((t) => t.trajectoryId),
|
|
255
|
+
)
|
|
256
|
+
if (
|
|
257
|
+
confirmation.baseline.some((t) => conditions.has(t.conditions)) ||
|
|
258
|
+
[...confirmation.baseline, ...confirmation.candidate].some((t) => traces.has(t.trajectoryId))
|
|
259
|
+
)
|
|
260
|
+
return result('inconclusive', 'Confirmation requires fresh conditions and trajectories.')
|
|
261
|
+
if (!second.positiveEvidence.length || second.passRateDelta === null || second.passRateDelta <= 0)
|
|
262
|
+
return result(
|
|
263
|
+
'reject',
|
|
264
|
+
'Confirmation needs attributable improvement and a positive primary-metric difference.',
|
|
265
|
+
)
|
|
266
|
+
return result(
|
|
267
|
+
'accept',
|
|
268
|
+
'Both rounds support improvement without observed regression; confirmation improves the paired pass rate.',
|
|
269
|
+
)
|
|
270
|
+
}
|
package/src/eval/index.ts
CHANGED
|
@@ -1,4 +1,14 @@
|
|
|
1
1
|
export { evalRunFromQuery, evalRunFromRun } from './from-run.js'
|
|
2
|
+
export { compareHarnessTrials, reviewHarnessCandidate } from './harness-verification.js'
|
|
3
|
+
export type {
|
|
4
|
+
HarnessTrial,
|
|
5
|
+
HarnessAttribution,
|
|
6
|
+
HarnessVerificationBatch,
|
|
7
|
+
HarnessBehaviorStatus,
|
|
8
|
+
HarnessTaskComparison,
|
|
9
|
+
HarnessComparison,
|
|
10
|
+
HarnessReview,
|
|
11
|
+
} from './harness-verification.js'
|
|
2
12
|
export { formatReport, runExperiment } from './experiment.js'
|
|
3
13
|
export type { ExperimentConfig } from './experiment.js'
|
|
4
14
|
export { judgeScorer } from './judge.js'
|