agent-bober 0.12.0 → 0.17.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/.claude-plugin/marketplace.json +20 -0
- package/.claude-plugin/plugin.json +2 -2
- package/CHANGELOG.md +243 -0
- package/README.md +238 -5
- package/agents/bober-architect.md +72 -0
- package/agents/bober-code-reviewer.md +238 -0
- package/agents/bober-curator.md +49 -0
- package/agents/bober-deployer.md +267 -0
- package/agents/bober-diagnoser.md +289 -0
- package/agents/bober-documenter.md +129 -0
- package/agents/bober-evaluator.md +135 -1
- package/agents/bober-generator.md +80 -3
- package/agents/bober-planner.md +47 -1
- package/agents/bober-postmortemer.md +185 -0
- package/agents/bober-researcher.md +38 -0
- package/dist/cli/commands/approve.d.ts +17 -0
- package/dist/cli/commands/approve.d.ts.map +1 -0
- package/dist/cli/commands/approve.js +64 -0
- package/dist/cli/commands/approve.js.map +1 -0
- package/dist/cli/commands/audit-show.d.ts +14 -0
- package/dist/cli/commands/audit-show.d.ts.map +1 -0
- package/dist/cli/commands/audit-show.js +85 -0
- package/dist/cli/commands/audit-show.js.map +1 -0
- package/dist/cli/commands/config.d.ts +10 -0
- package/dist/cli/commands/config.d.ts.map +1 -0
- package/dist/cli/commands/config.js +73 -0
- package/dist/cli/commands/config.js.map +1 -0
- package/dist/cli/commands/graph.d.ts +8 -0
- package/dist/cli/commands/graph.d.ts.map +1 -0
- package/dist/cli/commands/graph.js +219 -0
- package/dist/cli/commands/graph.js.map +1 -0
- package/dist/cli/commands/impact.d.ts +19 -0
- package/dist/cli/commands/impact.d.ts.map +1 -0
- package/dist/cli/commands/impact.js +191 -0
- package/dist/cli/commands/impact.js.map +1 -0
- package/dist/cli/commands/incident.d.ts +19 -0
- package/dist/cli/commands/incident.d.ts.map +1 -0
- package/dist/cli/commands/incident.js +324 -0
- package/dist/cli/commands/incident.js.map +1 -0
- package/dist/cli/commands/init.js +40 -1
- package/dist/cli/commands/init.js.map +1 -1
- package/dist/cli/commands/list-approvals.d.ts +16 -0
- package/dist/cli/commands/list-approvals.d.ts.map +1 -0
- package/dist/cli/commands/list-approvals.js +57 -0
- package/dist/cli/commands/list-approvals.js.map +1 -0
- package/dist/cli/commands/memory.d.ts +14 -0
- package/dist/cli/commands/memory.d.ts.map +1 -0
- package/dist/cli/commands/memory.js +132 -0
- package/dist/cli/commands/memory.js.map +1 -0
- package/dist/cli/commands/onboard.d.ts +3 -0
- package/dist/cli/commands/onboard.d.ts.map +1 -0
- package/dist/cli/commands/onboard.js +190 -0
- package/dist/cli/commands/onboard.js.map +1 -0
- package/dist/cli/commands/playbook.d.ts +17 -0
- package/dist/cli/commands/playbook.d.ts.map +1 -0
- package/dist/cli/commands/playbook.js +123 -0
- package/dist/cli/commands/playbook.js.map +1 -0
- package/dist/cli/commands/postmortem.d.ts +12 -0
- package/dist/cli/commands/postmortem.d.ts.map +1 -0
- package/dist/cli/commands/postmortem.js +67 -0
- package/dist/cli/commands/postmortem.js.map +1 -0
- package/dist/cli/commands/reject.d.ts +17 -0
- package/dist/cli/commands/reject.d.ts.map +1 -0
- package/dist/cli/commands/reject.js +52 -0
- package/dist/cli/commands/reject.js.map +1 -0
- package/dist/cli/commands/rollback.d.ts +21 -0
- package/dist/cli/commands/rollback.d.ts.map +1 -0
- package/dist/cli/commands/rollback.js +90 -0
- package/dist/cli/commands/rollback.js.map +1 -0
- package/dist/cli/commands/run.d.ts +9 -0
- package/dist/cli/commands/run.d.ts.map +1 -1
- package/dist/cli/commands/run.js +29 -0
- package/dist/cli/commands/run.js.map +1 -1
- package/dist/cli/commands/telemetry.d.ts +16 -0
- package/dist/cli/commands/telemetry.d.ts.map +1 -0
- package/dist/cli/commands/telemetry.js +152 -0
- package/dist/cli/commands/telemetry.js.map +1 -0
- package/dist/cli/commands/worktree.d.ts +12 -0
- package/dist/cli/commands/worktree.d.ts.map +1 -0
- package/dist/cli/commands/worktree.js +57 -0
- package/dist/cli/commands/worktree.js.map +1 -0
- package/dist/cli/index.js +56 -0
- package/dist/cli/index.js.map +1 -1
- package/dist/config/defaults.d.ts.map +1 -1
- package/dist/config/defaults.js +41 -3
- package/dist/config/defaults.js.map +1 -1
- package/dist/config/index.d.ts +1 -1
- package/dist/config/index.d.ts.map +1 -1
- package/dist/config/index.js +4 -0
- package/dist/config/index.js.map +1 -1
- package/dist/config/loader.d.ts.map +1 -1
- package/dist/config/loader.js +25 -1
- package/dist/config/loader.js.map +1 -1
- package/dist/config/role-providers.d.ts +29 -0
- package/dist/config/role-providers.d.ts.map +1 -0
- package/dist/config/role-providers.js +115 -0
- package/dist/config/role-providers.js.map +1 -0
- package/dist/config/schema.d.ts +1350 -61
- package/dist/config/schema.d.ts.map +1 -1
- package/dist/config/schema.js +189 -0
- package/dist/config/schema.js.map +1 -1
- package/dist/contracts/eval-result.d.ts +112 -56
- package/dist/contracts/eval-result.d.ts.map +1 -1
- package/dist/contracts/eval-result.js +3 -0
- package/dist/contracts/eval-result.js.map +1 -1
- package/dist/contracts/sprint-contract.d.ts +30 -30
- package/dist/fleet/aggregator.d.ts +5 -0
- package/dist/fleet/aggregator.d.ts.map +1 -0
- package/dist/fleet/aggregator.js +39 -0
- package/dist/fleet/aggregator.js.map +1 -0
- package/dist/fleet/child-config.d.ts +12 -0
- package/dist/fleet/child-config.d.ts.map +1 -0
- package/dist/fleet/child-config.js +38 -0
- package/dist/fleet/child-config.js.map +1 -0
- package/dist/fleet/coordinator.d.ts +25 -0
- package/dist/fleet/coordinator.d.ts.map +1 -0
- package/dist/fleet/coordinator.js +40 -0
- package/dist/fleet/coordinator.js.map +1 -0
- package/dist/fleet/index.d.ts +40 -0
- package/dist/fleet/index.d.ts.map +1 -0
- package/dist/fleet/index.js +117 -0
- package/dist/fleet/index.js.map +1 -0
- package/dist/fleet/manifest.d.ts +51 -0
- package/dist/fleet/manifest.d.ts.map +1 -0
- package/dist/fleet/manifest.js +32 -0
- package/dist/fleet/manifest.js.map +1 -0
- package/dist/fleet/reporter.d.ts +32 -0
- package/dist/fleet/reporter.d.ts.map +1 -0
- package/dist/fleet/reporter.js +71 -0
- package/dist/fleet/reporter.js.map +1 -0
- package/dist/fleet/runner.d.ts +48 -0
- package/dist/fleet/runner.d.ts.map +1 -0
- package/dist/fleet/runner.js +104 -0
- package/dist/fleet/runner.js.map +1 -0
- package/dist/fleet/scaffolder.d.ts +12 -0
- package/dist/fleet/scaffolder.d.ts.map +1 -0
- package/dist/fleet/scaffolder.js +82 -0
- package/dist/fleet/scaffolder.js.map +1 -0
- package/dist/fleet/types.d.ts +21 -0
- package/dist/fleet/types.d.ts.map +1 -0
- package/dist/fleet/types.js +2 -0
- package/dist/fleet/types.js.map +1 -0
- package/dist/graph/artifact-store.d.ts +14 -0
- package/dist/graph/artifact-store.d.ts.map +1 -0
- package/dist/graph/artifact-store.js +100 -0
- package/dist/graph/artifact-store.js.map +1 -0
- package/dist/graph/cli.d.ts +53 -0
- package/dist/graph/cli.d.ts.map +1 -0
- package/dist/graph/cli.js +181 -0
- package/dist/graph/cli.js.map +1 -0
- package/dist/graph/client.d.ts +64 -0
- package/dist/graph/client.d.ts.map +1 -0
- package/dist/graph/client.js +216 -0
- package/dist/graph/client.js.map +1 -0
- package/dist/graph/fallback.d.ts +13 -0
- package/dist/graph/fallback.d.ts.map +1 -0
- package/dist/graph/fallback.js +57 -0
- package/dist/graph/fallback.js.map +1 -0
- package/dist/graph/hook-handler.d.ts +50 -0
- package/dist/graph/hook-handler.d.ts.map +1 -0
- package/dist/graph/hook-handler.js +217 -0
- package/dist/graph/hook-handler.js.map +1 -0
- package/dist/graph/incidents.d.ts +59 -0
- package/dist/graph/incidents.d.ts.map +1 -0
- package/dist/graph/incidents.js +22 -0
- package/dist/graph/incidents.js.map +1 -0
- package/dist/graph/mcp-client.d.ts +51 -0
- package/dist/graph/mcp-client.d.ts.map +1 -0
- package/dist/graph/mcp-client.js +285 -0
- package/dist/graph/mcp-client.js.map +1 -0
- package/dist/graph/onboarding-composer.d.ts +30 -0
- package/dist/graph/onboarding-composer.d.ts.map +1 -0
- package/dist/graph/onboarding-composer.js +275 -0
- package/dist/graph/onboarding-composer.js.map +1 -0
- package/dist/graph/pipeline-lifecycle.d.ts +95 -0
- package/dist/graph/pipeline-lifecycle.d.ts.map +1 -0
- package/dist/graph/pipeline-lifecycle.js +341 -0
- package/dist/graph/pipeline-lifecycle.js.map +1 -0
- package/dist/graph/preflight-budgets.d.ts +52 -0
- package/dist/graph/preflight-budgets.d.ts.map +1 -0
- package/dist/graph/preflight-budgets.js +78 -0
- package/dist/graph/preflight-budgets.js.map +1 -0
- package/dist/graph/preflight-injector.d.ts +130 -0
- package/dist/graph/preflight-injector.d.ts.map +1 -0
- package/dist/graph/preflight-injector.js +618 -0
- package/dist/graph/preflight-injector.js.map +1 -0
- package/dist/graph/prereq.d.ts +12 -0
- package/dist/graph/prereq.d.ts.map +1 -0
- package/dist/graph/prereq.js +61 -0
- package/dist/graph/prereq.js.map +1 -0
- package/dist/graph/prompts.d.ts +42 -0
- package/dist/graph/prompts.d.ts.map +1 -0
- package/dist/graph/prompts.js +80 -0
- package/dist/graph/prompts.js.map +1 -0
- package/dist/graph/sandbox.d.ts +19 -0
- package/dist/graph/sandbox.d.ts.map +1 -0
- package/dist/graph/sandbox.js +25 -0
- package/dist/graph/sandbox.js.map +1 -0
- package/dist/graph/token-usage.d.ts +21 -0
- package/dist/graph/token-usage.d.ts.map +1 -0
- package/dist/graph/token-usage.js +22 -0
- package/dist/graph/token-usage.js.map +1 -0
- package/dist/graph/types.d.ts +129 -0
- package/dist/graph/types.d.ts.map +1 -0
- package/dist/graph/types.js +12 -0
- package/dist/graph/types.js.map +1 -0
- package/dist/incident/orchestrator.d.ts +168 -0
- package/dist/incident/orchestrator.d.ts.map +1 -0
- package/dist/incident/orchestrator.js +279 -0
- package/dist/incident/orchestrator.js.map +1 -0
- package/dist/incident/playbook-search.d.ts +67 -0
- package/dist/incident/playbook-search.d.ts.map +1 -0
- package/dist/incident/playbook-search.js +288 -0
- package/dist/incident/playbook-search.js.map +1 -0
- package/dist/incident/postmortem.d.ts +44 -0
- package/dist/incident/postmortem.d.ts.map +1 -0
- package/dist/incident/postmortem.js +486 -0
- package/dist/incident/postmortem.js.map +1 -0
- package/dist/incident/resolution-verify.d.ts +186 -0
- package/dist/incident/resolution-verify.d.ts.map +1 -0
- package/dist/incident/resolution-verify.js +210 -0
- package/dist/incident/resolution-verify.js.map +1 -0
- package/dist/incident/rollback.d.ts +137 -0
- package/dist/incident/rollback.d.ts.map +1 -0
- package/dist/incident/rollback.js +328 -0
- package/dist/incident/rollback.js.map +1 -0
- package/dist/incident/timeline.d.ts +147 -0
- package/dist/incident/timeline.d.ts.map +1 -0
- package/dist/incident/timeline.js +452 -0
- package/dist/incident/timeline.js.map +1 -0
- package/dist/incident/types.d.ts +335 -0
- package/dist/incident/types.d.ts.map +1 -0
- package/dist/incident/types.js +158 -0
- package/dist/incident/types.js.map +1 -0
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/mcp/event-stream.d.ts +46 -0
- package/dist/mcp/event-stream.d.ts.map +1 -0
- package/dist/mcp/event-stream.js +421 -0
- package/dist/mcp/event-stream.js.map +1 -0
- package/dist/mcp/external-client.d.ts +38 -0
- package/dist/mcp/external-client.d.ts.map +1 -0
- package/dist/mcp/external-client.js +121 -0
- package/dist/mcp/external-client.js.map +1 -0
- package/dist/mcp/run-manager.d.ts +74 -9
- package/dist/mcp/run-manager.d.ts.map +1 -1
- package/dist/mcp/run-manager.js +127 -31
- package/dist/mcp/run-manager.js.map +1 -1
- package/dist/mcp/server.d.ts.map +1 -1
- package/dist/mcp/server.js +56 -0
- package/dist/mcp/server.js.map +1 -1
- package/dist/mcp/tools/abort-run.d.ts +2 -0
- package/dist/mcp/tools/abort-run.d.ts.map +1 -0
- package/dist/mcp/tools/abort-run.js +62 -0
- package/dist/mcp/tools/abort-run.js.map +1 -0
- package/dist/mcp/tools/anchor.js +1 -1
- package/dist/mcp/tools/anchor.js.map +1 -1
- package/dist/mcp/tools/approve-checkpoint.d.ts +2 -0
- package/dist/mcp/tools/approve-checkpoint.d.ts.map +1 -0
- package/dist/mcp/tools/approve-checkpoint.js +70 -0
- package/dist/mcp/tools/approve-checkpoint.js.map +1 -0
- package/dist/mcp/tools/brownfield.js +1 -1
- package/dist/mcp/tools/brownfield.js.map +1 -1
- package/dist/mcp/tools/get-project-state.d.ts +2 -0
- package/dist/mcp/tools/get-project-state.d.ts.map +1 -0
- package/dist/mcp/tools/get-project-state.js +107 -0
- package/dist/mcp/tools/get-project-state.js.map +1 -0
- package/dist/mcp/tools/get-run-status.d.ts +2 -0
- package/dist/mcp/tools/get-run-status.d.ts.map +1 -0
- package/dist/mcp/tools/get-run-status.js +40 -0
- package/dist/mcp/tools/get-run-status.js.map +1 -0
- package/dist/mcp/tools/graph-schemas.d.ts +100 -0
- package/dist/mcp/tools/graph-schemas.d.ts.map +1 -0
- package/dist/mcp/tools/graph-schemas.js +39 -0
- package/dist/mcp/tools/graph-schemas.js.map +1 -0
- package/dist/mcp/tools/graph.d.ts +19 -0
- package/dist/mcp/tools/graph.d.ts.map +1 -0
- package/dist/mcp/tools/graph.js +263 -0
- package/dist/mcp/tools/graph.js.map +1 -0
- package/dist/mcp/tools/incident.d.ts +2 -0
- package/dist/mcp/tools/incident.d.ts.map +1 -0
- package/dist/mcp/tools/incident.js +246 -0
- package/dist/mcp/tools/incident.js.map +1 -0
- package/dist/mcp/tools/index.d.ts +38 -18
- package/dist/mcp/tools/index.d.ts.map +1 -1
- package/dist/mcp/tools/index.js +74 -18
- package/dist/mcp/tools/index.js.map +1 -1
- package/dist/mcp/tools/init.d.ts.map +1 -1
- package/dist/mcp/tools/init.js +2 -0
- package/dist/mcp/tools/init.js.map +1 -1
- package/dist/mcp/tools/list-active-runs.d.ts +2 -0
- package/dist/mcp/tools/list-active-runs.d.ts.map +1 -0
- package/dist/mcp/tools/list-active-runs.js +35 -0
- package/dist/mcp/tools/list-active-runs.js.map +1 -0
- package/dist/mcp/tools/list-pending-approvals.d.ts +2 -0
- package/dist/mcp/tools/list-pending-approvals.d.ts.map +1 -0
- package/dist/mcp/tools/list-pending-approvals.js +40 -0
- package/dist/mcp/tools/list-pending-approvals.js.map +1 -0
- package/dist/mcp/tools/list-projects.d.ts +2 -0
- package/dist/mcp/tools/list-projects.d.ts.map +1 -0
- package/dist/mcp/tools/list-projects.js +101 -0
- package/dist/mcp/tools/list-projects.js.map +1 -0
- package/dist/mcp/tools/list-specs.d.ts +2 -0
- package/dist/mcp/tools/list-specs.d.ts.map +1 -0
- package/dist/mcp/tools/list-specs.js +48 -0
- package/dist/mcp/tools/list-specs.js.map +1 -0
- package/dist/mcp/tools/playbook.d.ts +2 -0
- package/dist/mcp/tools/playbook.d.ts.map +1 -0
- package/dist/mcp/tools/playbook.js +104 -0
- package/dist/mcp/tools/playbook.js.map +1 -0
- package/dist/mcp/tools/postmortem.d.ts +2 -0
- package/dist/mcp/tools/postmortem.d.ts.map +1 -0
- package/dist/mcp/tools/postmortem.js +75 -0
- package/dist/mcp/tools/postmortem.js.map +1 -0
- package/dist/mcp/tools/react.js +1 -1
- package/dist/mcp/tools/react.js.map +1 -1
- package/dist/mcp/tools/reject-checkpoint.d.ts +2 -0
- package/dist/mcp/tools/reject-checkpoint.d.ts.map +1 -0
- package/dist/mcp/tools/reject-checkpoint.js +79 -0
- package/dist/mcp/tools/reject-checkpoint.js.map +1 -0
- package/dist/mcp/tools/rollback.d.ts +2 -0
- package/dist/mcp/tools/rollback.d.ts.map +1 -0
- package/dist/mcp/tools/rollback.js +78 -0
- package/dist/mcp/tools/rollback.js.map +1 -0
- package/dist/mcp/tools/run-in-worktree.d.ts +2 -0
- package/dist/mcp/tools/run-in-worktree.d.ts.map +1 -0
- package/dist/mcp/tools/run-in-worktree.js +90 -0
- package/dist/mcp/tools/run-in-worktree.js.map +1 -0
- package/dist/mcp/tools/run.js +1 -1
- package/dist/mcp/tools/run.js.map +1 -1
- package/dist/mcp/tools/solidity.js +1 -1
- package/dist/mcp/tools/solidity.js.map +1 -1
- package/dist/mcp/tools/status.d.ts.map +1 -1
- package/dist/mcp/tools/status.js +11 -0
- package/dist/mcp/tools/status.js.map +1 -1
- package/dist/mcp/tools/subscribe-events.d.ts +2 -0
- package/dist/mcp/tools/subscribe-events.d.ts.map +1 -0
- package/dist/mcp/tools/subscribe-events.js +48 -0
- package/dist/mcp/tools/subscribe-events.js.map +1 -0
- package/dist/mcp/tools/unsubscribe-events.d.ts +2 -0
- package/dist/mcp/tools/unsubscribe-events.d.ts.map +1 -0
- package/dist/mcp/tools/unsubscribe-events.js +45 -0
- package/dist/mcp/tools/unsubscribe-events.js.map +1 -0
- package/dist/orchestrator/agent-loader.d.ts +16 -0
- package/dist/orchestrator/agent-loader.d.ts.map +1 -1
- package/dist/orchestrator/agent-loader.js +30 -0
- package/dist/orchestrator/agent-loader.js.map +1 -1
- package/dist/orchestrator/agentic-loop.d.ts +51 -0
- package/dist/orchestrator/agentic-loop.d.ts.map +1 -1
- package/dist/orchestrator/agentic-loop.js +123 -4
- package/dist/orchestrator/agentic-loop.js.map +1 -1
- package/dist/orchestrator/arch-lenses.d.ts +7 -0
- package/dist/orchestrator/arch-lenses.d.ts.map +1 -0
- package/dist/orchestrator/arch-lenses.js +22 -0
- package/dist/orchestrator/arch-lenses.js.map +1 -0
- package/dist/orchestrator/architect-agent.d.ts +16 -0
- package/dist/orchestrator/architect-agent.d.ts.map +1 -1
- package/dist/orchestrator/architect-agent.js +546 -9
- package/dist/orchestrator/architect-agent.js.map +1 -1
- package/dist/orchestrator/checkpoints/audit.d.ts +128 -0
- package/dist/orchestrator/checkpoints/audit.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/audit.js +272 -0
- package/dist/orchestrator/checkpoints/audit.js.map +1 -0
- package/dist/orchestrator/checkpoints/feedback-router.d.ts +213 -0
- package/dist/orchestrator/checkpoints/feedback-router.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/feedback-router.js +438 -0
- package/dist/orchestrator/checkpoints/feedback-router.js.map +1 -0
- package/dist/orchestrator/checkpoints/index.d.ts +11 -0
- package/dist/orchestrator/checkpoints/index.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/index.js +12 -0
- package/dist/orchestrator/checkpoints/index.js.map +1 -0
- package/dist/orchestrator/checkpoints/mechanisms/cli.d.ts +35 -0
- package/dist/orchestrator/checkpoints/mechanisms/cli.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/mechanisms/cli.js +153 -0
- package/dist/orchestrator/checkpoints/mechanisms/cli.js.map +1 -0
- package/dist/orchestrator/checkpoints/mechanisms/disk.d.ts +34 -0
- package/dist/orchestrator/checkpoints/mechanisms/disk.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/mechanisms/disk.js +139 -0
- package/dist/orchestrator/checkpoints/mechanisms/disk.js.map +1 -0
- package/dist/orchestrator/checkpoints/mechanisms/pr.d.ts +141 -0
- package/dist/orchestrator/checkpoints/mechanisms/pr.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/mechanisms/pr.js +445 -0
- package/dist/orchestrator/checkpoints/mechanisms/pr.js.map +1 -0
- package/dist/orchestrator/checkpoints/noop.d.ts +12 -0
- package/dist/orchestrator/checkpoints/noop.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/noop.js +13 -0
- package/dist/orchestrator/checkpoints/noop.js.map +1 -0
- package/dist/orchestrator/checkpoints/registry.d.ts +48 -0
- package/dist/orchestrator/checkpoints/registry.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/registry.js +89 -0
- package/dist/orchestrator/checkpoints/registry.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/_util.d.ts +50 -0
- package/dist/orchestrator/checkpoints/renderers/_util.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/_util.js +137 -0
- package/dist/orchestrator/checkpoints/renderers/_util.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/code-review.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/code-review.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/code-review.js +66 -0
- package/dist/orchestrator/checkpoints/renderers/code-review.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/curator-briefing.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/curator-briefing.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/curator-briefing.js +40 -0
- package/dist/orchestrator/checkpoints/renderers/curator-briefing.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/eval-result.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/eval-result.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/eval-result.js +54 -0
- package/dist/orchestrator/checkpoints/renderers/eval-result.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/generator-diff.d.ts +49 -0
- package/dist/orchestrator/checkpoints/renderers/generator-diff.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/generator-diff.js +154 -0
- package/dist/orchestrator/checkpoints/renderers/generator-diff.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/pipeline-summary.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/pipeline-summary.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/pipeline-summary.js +59 -0
- package/dist/orchestrator/checkpoints/renderers/pipeline-summary.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/plan.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/plan.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/plan.js +34 -0
- package/dist/orchestrator/checkpoints/renderers/plan.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/registry.d.ts +43 -0
- package/dist/orchestrator/checkpoints/renderers/registry.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/registry.js +83 -0
- package/dist/orchestrator/checkpoints/renderers/registry.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/research.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/research.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/research.js +39 -0
- package/dist/orchestrator/checkpoints/renderers/research.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-contract.d.ts +20 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-contract.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-contract.js +57 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-contract.js.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-summary.d.ts +15 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-summary.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-summary.js +38 -0
- package/dist/orchestrator/checkpoints/renderers/sprint-summary.js.map +1 -0
- package/dist/orchestrator/checkpoints/sites.d.ts +22 -0
- package/dist/orchestrator/checkpoints/sites.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/sites.js +57 -0
- package/dist/orchestrator/checkpoints/sites.js.map +1 -0
- package/dist/orchestrator/checkpoints/types.d.ts +51 -0
- package/dist/orchestrator/checkpoints/types.d.ts.map +1 -0
- package/dist/orchestrator/checkpoints/types.js +9 -0
- package/dist/orchestrator/checkpoints/types.js.map +1 -0
- package/dist/orchestrator/code-reviewer-agent.d.ts +50 -0
- package/dist/orchestrator/code-reviewer-agent.d.ts.map +1 -0
- package/dist/orchestrator/code-reviewer-agent.js +283 -0
- package/dist/orchestrator/code-reviewer-agent.js.map +1 -0
- package/dist/orchestrator/curator-agent.d.ts.map +1 -1
- package/dist/orchestrator/curator-agent.js +60 -9
- package/dist/orchestrator/curator-agent.js.map +1 -1
- package/dist/orchestrator/deploy/classify.d.ts +31 -0
- package/dist/orchestrator/deploy/classify.d.ts.map +1 -0
- package/dist/orchestrator/deploy/classify.js +109 -0
- package/dist/orchestrator/deploy/classify.js.map +1 -0
- package/dist/orchestrator/deploy/execute.d.ts +45 -0
- package/dist/orchestrator/deploy/execute.d.ts.map +1 -0
- package/dist/orchestrator/deploy/execute.js +146 -0
- package/dist/orchestrator/deploy/execute.js.map +1 -0
- package/dist/orchestrator/deploy/executor.d.ts +22 -0
- package/dist/orchestrator/deploy/executor.d.ts.map +1 -0
- package/dist/orchestrator/deploy/executor.js +31 -0
- package/dist/orchestrator/deploy/executor.js.map +1 -0
- package/dist/orchestrator/deploy/index.d.ts +21 -0
- package/dist/orchestrator/deploy/index.d.ts.map +1 -0
- package/dist/orchestrator/deploy/index.js +21 -0
- package/dist/orchestrator/deploy/index.js.map +1 -0
- package/dist/orchestrator/deploy/resolve.d.ts +51 -0
- package/dist/orchestrator/deploy/resolve.d.ts.map +1 -0
- package/dist/orchestrator/deploy/resolve.js +53 -0
- package/dist/orchestrator/deploy/resolve.js.map +1 -0
- package/dist/orchestrator/deploy/spawn.d.ts +60 -0
- package/dist/orchestrator/deploy/spawn.d.ts.map +1 -0
- package/dist/orchestrator/deploy/spawn.js +62 -0
- package/dist/orchestrator/deploy/spawn.js.map +1 -0
- package/dist/orchestrator/deploy/types.d.ts +98 -0
- package/dist/orchestrator/deploy/types.d.ts.map +1 -0
- package/dist/orchestrator/deploy/types.js +39 -0
- package/dist/orchestrator/deploy/types.js.map +1 -0
- package/dist/orchestrator/documenter-agent.d.ts +57 -0
- package/dist/orchestrator/documenter-agent.d.ts.map +1 -0
- package/dist/orchestrator/documenter-agent.js +195 -0
- package/dist/orchestrator/documenter-agent.js.map +1 -0
- package/dist/orchestrator/environment.d.ts +45 -0
- package/dist/orchestrator/environment.d.ts.map +1 -0
- package/dist/orchestrator/environment.js +151 -0
- package/dist/orchestrator/environment.js.map +1 -0
- package/dist/orchestrator/eval-lenses.d.ts +7 -0
- package/dist/orchestrator/eval-lenses.d.ts.map +1 -0
- package/dist/orchestrator/eval-lenses.js +19 -0
- package/dist/orchestrator/eval-lenses.js.map +1 -0
- package/dist/orchestrator/eval-persist.d.ts +25 -0
- package/dist/orchestrator/eval-persist.d.ts.map +1 -0
- package/dist/orchestrator/eval-persist.js +74 -0
- package/dist/orchestrator/eval-persist.js.map +1 -0
- package/dist/orchestrator/evaluator-agent.d.ts +23 -0
- package/dist/orchestrator/evaluator-agent.d.ts.map +1 -1
- package/dist/orchestrator/evaluator-agent.js +80 -10
- package/dist/orchestrator/evaluator-agent.js.map +1 -1
- package/dist/orchestrator/generator-agent.d.ts.map +1 -1
- package/dist/orchestrator/generator-agent.js +53 -8
- package/dist/orchestrator/generator-agent.js.map +1 -1
- package/dist/orchestrator/memory/distill.d.ts +60 -0
- package/dist/orchestrator/memory/distill.d.ts.map +1 -0
- package/dist/orchestrator/memory/distill.js +177 -0
- package/dist/orchestrator/memory/distill.js.map +1 -0
- package/dist/orchestrator/memory/eval-source.d.ts +20 -0
- package/dist/orchestrator/memory/eval-source.d.ts.map +1 -0
- package/dist/orchestrator/memory/eval-source.js +88 -0
- package/dist/orchestrator/memory/eval-source.js.map +1 -0
- package/dist/orchestrator/memory/retrieve.d.ts +45 -0
- package/dist/orchestrator/memory/retrieve.d.ts.map +1 -0
- package/dist/orchestrator/memory/retrieve.js +102 -0
- package/dist/orchestrator/memory/retrieve.js.map +1 -0
- package/dist/orchestrator/model-resolver.d.ts.map +1 -1
- package/dist/orchestrator/model-resolver.js +15 -1
- package/dist/orchestrator/model-resolver.js.map +1 -1
- package/dist/orchestrator/observability/index.d.ts +12 -0
- package/dist/orchestrator/observability/index.d.ts.map +1 -0
- package/dist/orchestrator/observability/index.js +12 -0
- package/dist/orchestrator/observability/index.js.map +1 -0
- package/dist/orchestrator/observability/merge.d.ts +73 -0
- package/dist/orchestrator/observability/merge.d.ts.map +1 -0
- package/dist/orchestrator/observability/merge.js +110 -0
- package/dist/orchestrator/observability/merge.js.map +1 -0
- package/dist/orchestrator/pipeline.d.ts +31 -0
- package/dist/orchestrator/pipeline.d.ts.map +1 -1
- package/dist/orchestrator/pipeline.js +267 -5
- package/dist/orchestrator/pipeline.js.map +1 -1
- package/dist/orchestrator/planner-agent.d.ts +22 -1
- package/dist/orchestrator/planner-agent.d.ts.map +1 -1
- package/dist/orchestrator/planner-agent.js +165 -8
- package/dist/orchestrator/planner-agent.js.map +1 -1
- package/dist/orchestrator/research-agent.d.ts.map +1 -1
- package/dist/orchestrator/research-agent.js +48 -11
- package/dist/orchestrator/research-agent.js.map +1 -1
- package/dist/orchestrator/tools/handlers.d.ts +16 -0
- package/dist/orchestrator/tools/handlers.d.ts.map +1 -1
- package/dist/orchestrator/tools/handlers.js +30 -5
- package/dist/orchestrator/tools/handlers.js.map +1 -1
- package/dist/orchestrator/tools/index.d.ts +84 -1
- package/dist/orchestrator/tools/index.d.ts.map +1 -1
- package/dist/orchestrator/tools/index.js +164 -1
- package/dist/orchestrator/tools/index.js.map +1 -1
- package/dist/orchestrator/tools/schemas.js +5 -5
- package/dist/orchestrator/tools/schemas.js.map +1 -1
- package/dist/orchestrator/workflow/args-builder.d.ts +35 -0
- package/dist/orchestrator/workflow/args-builder.d.ts.map +1 -0
- package/dist/orchestrator/workflow/args-builder.js +142 -0
- package/dist/orchestrator/workflow/args-builder.js.map +1 -0
- package/dist/orchestrator/workflow/budget.d.ts +57 -0
- package/dist/orchestrator/workflow/budget.d.ts.map +1 -0
- package/dist/orchestrator/workflow/budget.js +80 -0
- package/dist/orchestrator/workflow/budget.js.map +1 -0
- package/dist/orchestrator/workflow/conformance.d.ts +27 -0
- package/dist/orchestrator/workflow/conformance.d.ts.map +1 -0
- package/dist/orchestrator/workflow/conformance.js +111 -0
- package/dist/orchestrator/workflow/conformance.js.map +1 -0
- package/dist/orchestrator/workflow/eligibility.d.ts +8 -0
- package/dist/orchestrator/workflow/eligibility.d.ts.map +1 -0
- package/dist/orchestrator/workflow/eligibility.js +10 -0
- package/dist/orchestrator/workflow/eligibility.js.map +1 -0
- package/dist/orchestrator/workflow/engine.d.ts +10 -0
- package/dist/orchestrator/workflow/engine.d.ts.map +1 -0
- package/dist/orchestrator/workflow/engine.js +2 -0
- package/dist/orchestrator/workflow/engine.js.map +1 -0
- package/dist/orchestrator/workflow/errors.d.ts +13 -0
- package/dist/orchestrator/workflow/errors.d.ts.map +1 -0
- package/dist/orchestrator/workflow/errors.js +26 -0
- package/dist/orchestrator/workflow/errors.js.map +1 -0
- package/dist/orchestrator/workflow/flusher.d.ts +19 -0
- package/dist/orchestrator/workflow/flusher.d.ts.map +1 -0
- package/dist/orchestrator/workflow/flusher.js +81 -0
- package/dist/orchestrator/workflow/flusher.js.map +1 -0
- package/dist/orchestrator/workflow/interpreter.d.ts +48 -0
- package/dist/orchestrator/workflow/interpreter.d.ts.map +1 -0
- package/dist/orchestrator/workflow/interpreter.js +92 -0
- package/dist/orchestrator/workflow/interpreter.js.map +1 -0
- package/dist/orchestrator/workflow/pure-sprint.d.ts +65 -0
- package/dist/orchestrator/workflow/pure-sprint.d.ts.map +1 -0
- package/dist/orchestrator/workflow/pure-sprint.js +82 -0
- package/dist/orchestrator/workflow/pure-sprint.js.map +1 -0
- package/dist/orchestrator/workflow/reconciler.d.ts +15 -0
- package/dist/orchestrator/workflow/reconciler.d.ts.map +1 -0
- package/dist/orchestrator/workflow/reconciler.js +65 -0
- package/dist/orchestrator/workflow/reconciler.js.map +1 -0
- package/dist/orchestrator/workflow/resume-cursor.d.ts +10 -0
- package/dist/orchestrator/workflow/resume-cursor.d.ts.map +1 -0
- package/dist/orchestrator/workflow/resume-cursor.js +25 -0
- package/dist/orchestrator/workflow/resume-cursor.js.map +1 -0
- package/dist/orchestrator/workflow/retry.d.ts +50 -0
- package/dist/orchestrator/workflow/retry.d.ts.map +1 -0
- package/dist/orchestrator/workflow/retry.js +100 -0
- package/dist/orchestrator/workflow/retry.js.map +1 -0
- package/dist/orchestrator/workflow/scheduler.d.ts +87 -0
- package/dist/orchestrator/workflow/scheduler.d.ts.map +1 -0
- package/dist/orchestrator/workflow/scheduler.js +158 -0
- package/dist/orchestrator/workflow/scheduler.js.map +1 -0
- package/dist/orchestrator/workflow/selector.d.ts +26 -0
- package/dist/orchestrator/workflow/selector.d.ts.map +1 -0
- package/dist/orchestrator/workflow/selector.js +54 -0
- package/dist/orchestrator/workflow/selector.js.map +1 -0
- package/dist/orchestrator/workflow/synthesizer.d.ts +52 -0
- package/dist/orchestrator/workflow/synthesizer.d.ts.map +1 -0
- package/dist/orchestrator/workflow/synthesizer.js +75 -0
- package/dist/orchestrator/workflow/synthesizer.js.map +1 -0
- package/dist/orchestrator/workflow/ts-engine.d.ts +13 -0
- package/dist/orchestrator/workflow/ts-engine.d.ts.map +1 -0
- package/dist/orchestrator/workflow/ts-engine.js +14 -0
- package/dist/orchestrator/workflow/ts-engine.js.map +1 -0
- package/dist/orchestrator/workflow/types.d.ts +55 -0
- package/dist/orchestrator/workflow/types.d.ts.map +1 -0
- package/dist/orchestrator/workflow/types.js +3 -0
- package/dist/orchestrator/workflow/types.js.map +1 -0
- package/dist/orchestrator/workflow/workflow-engine.d.ts +31 -0
- package/dist/orchestrator/workflow/workflow-engine.d.ts.map +1 -0
- package/dist/orchestrator/workflow/workflow-engine.js +70 -0
- package/dist/orchestrator/workflow/workflow-engine.js.map +1 -0
- package/dist/orchestrator/worktree.d.ts +18 -0
- package/dist/orchestrator/worktree.d.ts.map +1 -0
- package/dist/orchestrator/worktree.js +129 -0
- package/dist/orchestrator/worktree.js.map +1 -0
- package/dist/providers/anthropic.d.ts +8 -1
- package/dist/providers/anthropic.d.ts.map +1 -1
- package/dist/providers/anthropic.js +135 -11
- package/dist/providers/anthropic.js.map +1 -1
- package/dist/providers/claude-code.d.ts +44 -0
- package/dist/providers/claude-code.d.ts.map +1 -0
- package/dist/providers/claude-code.js +143 -0
- package/dist/providers/claude-code.js.map +1 -0
- package/dist/providers/factory.d.ts +16 -2
- package/dist/providers/factory.d.ts.map +1 -1
- package/dist/providers/factory.js +101 -14
- package/dist/providers/factory.js.map +1 -1
- package/dist/providers/google.d.ts.map +1 -1
- package/dist/providers/google.js +32 -3
- package/dist/providers/google.js.map +1 -1
- package/dist/providers/index.d.ts +4 -2
- package/dist/providers/index.d.ts.map +1 -1
- package/dist/providers/index.js +3 -1
- package/dist/providers/index.js.map +1 -1
- package/dist/providers/openai.d.ts.map +1 -1
- package/dist/providers/openai.js +28 -3
- package/dist/providers/openai.js.map +1 -1
- package/dist/providers/preflight.d.ts +22 -0
- package/dist/providers/preflight.d.ts.map +1 -0
- package/dist/providers/preflight.js +54 -0
- package/dist/providers/preflight.js.map +1 -0
- package/dist/providers/structured.d.ts +130 -0
- package/dist/providers/structured.d.ts.map +1 -0
- package/dist/providers/structured.js +205 -0
- package/dist/providers/structured.js.map +1 -0
- package/dist/providers/types.d.ts +53 -2
- package/dist/providers/types.d.ts.map +1 -1
- package/dist/state/approval-state.d.ts +74 -0
- package/dist/state/approval-state.d.ts.map +1 -0
- package/dist/state/approval-state.js +127 -0
- package/dist/state/approval-state.js.map +1 -0
- package/dist/state/history-rotation.d.ts +17 -0
- package/dist/state/history-rotation.d.ts.map +1 -0
- package/dist/state/history-rotation.js +84 -0
- package/dist/state/history-rotation.js.map +1 -0
- package/dist/state/history.d.ts +16 -4
- package/dist/state/history.d.ts.map +1 -1
- package/dist/state/history.js +62 -20
- package/dist/state/history.js.map +1 -1
- package/dist/state/index.d.ts +4 -1
- package/dist/state/index.d.ts.map +1 -1
- package/dist/state/index.js +5 -2
- package/dist/state/index.js.map +1 -1
- package/dist/state/memory.d.ts +60 -0
- package/dist/state/memory.d.ts.map +1 -0
- package/dist/state/memory.js +242 -0
- package/dist/state/memory.js.map +1 -0
- package/dist/state/review-state.d.ts +15 -0
- package/dist/state/review-state.d.ts.map +1 -0
- package/dist/state/review-state.js +51 -0
- package/dist/state/review-state.js.map +1 -0
- package/dist/state/run-state.d.ts +39 -0
- package/dist/state/run-state.d.ts.map +1 -0
- package/dist/state/run-state.js +101 -0
- package/dist/state/run-state.js.map +1 -0
- package/dist/telemetry/emit.d.ts +41 -0
- package/dist/telemetry/emit.d.ts.map +1 -0
- package/dist/telemetry/emit.js +65 -0
- package/dist/telemetry/emit.js.map +1 -0
- package/dist/utils/git.d.ts +27 -0
- package/dist/utils/git.d.ts.map +1 -1
- package/dist/utils/git.js +50 -0
- package/dist/utils/git.js.map +1 -1
- package/hooks/hooks.json +27 -1
- package/hooks/session-start +42 -0
- package/package.json +13 -6
- package/scripts/check-prereqs.sh +12 -0
- package/scripts/e2e-graph-smoke.sh +167 -0
- package/scripts/graph-hook.mjs +151 -0
- package/scripts/run-kpi-gate.mjs +245 -0
- package/scripts/spike-claude-code-provider.mjs +66 -0
- package/scripts/spike-deepseek.mjs +63 -0
- package/scripts/sync-skills.mjs +4 -1
- package/scripts/sync-targets.json +12 -0
- package/scripts/update-all.mjs +255 -0
- package/skills/bober.architect/SKILL.md +13 -0
- package/skills/bober.architect/references/arch-lens-panel.md +126 -0
- package/skills/bober.code-review/SKILL.md +186 -0
- package/skills/bober.debug/SKILL.md +300 -0
- package/skills/bober.deploy/SKILL.md +262 -0
- package/skills/bober.diagnose/SKILL.md +254 -0
- package/skills/bober.eval/SKILL.md +9 -0
- package/skills/bober.eval/references/lens-panel.md +115 -0
- package/skills/bober.graph/SKILL.md +85 -0
- package/skills/bober.impact/SKILL.md +101 -0
- package/skills/bober.incident/SKILL.md +245 -0
- package/skills/bober.onboard/SKILL.md +84 -0
- package/skills/bober.plan/SKILL.md +16 -0
- package/skills/bober.postmortem/SKILL.md +231 -0
- package/skills/bober.run/SKILL.md +23 -4
- package/skills/bober.run/references/lens-panel.md +115 -0
- package/skills/bober.runbook/SKILL.md +335 -0
- package/skills/bober.sprint/SKILL.md +44 -2
- package/skills/bober.sprint/references/lens-panel.md +115 -0
- package/skills/bober.using-bober/SKILL.md +133 -0
- package/skills/bober.verify/SKILL.md +143 -0
- package/skills/shared/arch-lens-panel.md +126 -0
- package/skills/shared/lens-panel.md +115 -0
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# e2e-graph-smoke.sh — end-to-end smoke test for the tokensave graph integration.
|
|
3
|
+
#
|
|
4
|
+
# Prerequisites:
|
|
5
|
+
# - tokensave >= 6.0.0-beta.1 installed and on PATH
|
|
6
|
+
# - npm + node >= 18
|
|
7
|
+
#
|
|
8
|
+
# This script is gated in CI by checking for the tokensave binary.
|
|
9
|
+
# If tokensave is not available, the script exits 0 (skip, not fail).
|
|
10
|
+
#
|
|
11
|
+
# Usage:
|
|
12
|
+
# bash scripts/e2e-graph-smoke.sh
|
|
13
|
+
#
|
|
14
|
+
# The script:
|
|
15
|
+
# 1. Verifies tokensave is available
|
|
16
|
+
# 2. Builds the project
|
|
17
|
+
# 3. Creates a temp directory with a minimal project
|
|
18
|
+
# 4. Runs agent-bober init (brownfield) to get bober.config.json with graph.enabled=true
|
|
19
|
+
# 5. Runs agent-bober graph init
|
|
20
|
+
# 6. Runs agent-bober graph status — asserts ready=true in JSON output
|
|
21
|
+
# 7. Runs agent-bober onboard — asserts 5 files written
|
|
22
|
+
# 8. Runs agent-bober impact sandboxPath — asserts .bober/graph/impact/sandboxpath.md exists
|
|
23
|
+
# 9. Cleans up
|
|
24
|
+
|
|
25
|
+
set -euo pipefail
|
|
26
|
+
|
|
27
|
+
# ── Colors ────────────────────────────────────────────────────────────────────
|
|
28
|
+
RED='\033[0;31m'
|
|
29
|
+
GREEN='\033[0;32m'
|
|
30
|
+
CYAN='\033[0;36m'
|
|
31
|
+
YELLOW='\033[1;33m'
|
|
32
|
+
NC='\033[0m' # No Color
|
|
33
|
+
|
|
34
|
+
info() { echo -e "${CYAN}[smoke]${NC} $*"; }
|
|
35
|
+
ok() { echo -e "${GREEN}[OK]${NC} $*"; }
|
|
36
|
+
warn() { echo -e "${YELLOW}[SKIP]${NC} $*"; }
|
|
37
|
+
fail() { echo -e "${RED}[FAIL]${NC} $*" >&2; exit 1; }
|
|
38
|
+
|
|
39
|
+
# ── Gate: tokensave must be available ─────────────────────────────────────────
|
|
40
|
+
if ! command -v tokensave &>/dev/null; then
|
|
41
|
+
warn "tokensave binary not found — skipping e2e smoke test (install with: brew install aovestdipaperino/tap/tokensave)"
|
|
42
|
+
exit 0
|
|
43
|
+
fi
|
|
44
|
+
|
|
45
|
+
TOKENSAVE_VERSION=$(tokensave --version 2>&1 | head -1 || echo "unknown")
|
|
46
|
+
info "tokensave found: ${TOKENSAVE_VERSION}"
|
|
47
|
+
|
|
48
|
+
# ── Step 1: Build the project ─────────────────────────────────────────────────
|
|
49
|
+
REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
|
|
50
|
+
info "Building agent-bober from ${REPO_ROOT}..."
|
|
51
|
+
cd "${REPO_ROOT}"
|
|
52
|
+
npm run build 2>&1 | tail -5
|
|
53
|
+
ok "Build complete"
|
|
54
|
+
|
|
55
|
+
# ── Step 2: Create a temp test project ────────────────────────────────────────
|
|
56
|
+
TMP_DIR="$(mktemp -d)"
|
|
57
|
+
trap 'rm -rf "${TMP_DIR}"' EXIT
|
|
58
|
+
info "Temp project: ${TMP_DIR}"
|
|
59
|
+
|
|
60
|
+
# Initialise a minimal git repo so agent-bober can detect project root
|
|
61
|
+
cd "${TMP_DIR}"
|
|
62
|
+
git init -q
|
|
63
|
+
git commit --allow-empty -m "init" -q
|
|
64
|
+
|
|
65
|
+
# Write a minimal bober.config.json with graph.enabled=true
|
|
66
|
+
cat > bober.config.json <<'EOF'
|
|
67
|
+
{
|
|
68
|
+
"project": { "name": "smoke-test", "mode": "brownfield" },
|
|
69
|
+
"planner": { "model": "sonnet" },
|
|
70
|
+
"generator": { "model": "sonnet" },
|
|
71
|
+
"evaluator": { "strategies": [] },
|
|
72
|
+
"graph": { "enabled": true, "languageTier": "core" }
|
|
73
|
+
}
|
|
74
|
+
EOF
|
|
75
|
+
|
|
76
|
+
# Add a minimal TypeScript source file
|
|
77
|
+
mkdir -p src
|
|
78
|
+
cat > src/index.ts <<'EOF'
|
|
79
|
+
export function sandboxPath(root: string, p: string): string {
|
|
80
|
+
return `${root}/${p}`;
|
|
81
|
+
}
|
|
82
|
+
EOF
|
|
83
|
+
|
|
84
|
+
# Write a package.json so tokensave knows it is a Node project
|
|
85
|
+
cat > package.json <<'EOF'
|
|
86
|
+
{ "name": "smoke-test", "version": "1.0.0" }
|
|
87
|
+
EOF
|
|
88
|
+
|
|
89
|
+
ok "Temp project created"
|
|
90
|
+
|
|
91
|
+
# ── Step 3: Link or use agent-bober ───────────────────────────────────────────
|
|
92
|
+
BOBER_BIN="${REPO_ROOT}/node_modules/.bin/agent-bober"
|
|
93
|
+
if [[ ! -f "${BOBER_BIN}" ]]; then
|
|
94
|
+
# If running from a global install
|
|
95
|
+
BOBER_BIN="agent-bober"
|
|
96
|
+
fi
|
|
97
|
+
|
|
98
|
+
# Use the built binary directly for hermetic execution
|
|
99
|
+
NODE_BIN="node ${REPO_ROOT}/dist/cli/index.js"
|
|
100
|
+
|
|
101
|
+
run_bober() {
|
|
102
|
+
${NODE_BIN} "$@"
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
# ── Step 4: graph init ────────────────────────────────────────────────────────
|
|
106
|
+
info "Running: agent-bober graph init"
|
|
107
|
+
run_bober graph init
|
|
108
|
+
ok "graph init succeeded"
|
|
109
|
+
|
|
110
|
+
# ── Step 5: graph status ──────────────────────────────────────────────────────
|
|
111
|
+
info "Running: agent-bober graph status --json"
|
|
112
|
+
STATUS_JSON="$(run_bober graph status --json)"
|
|
113
|
+
info "Status output: ${STATUS_JSON}"
|
|
114
|
+
|
|
115
|
+
# The graph may not be 'ready' if tokensave hasn't fully indexed in CI,
|
|
116
|
+
# but the command should succeed (exit 0) and produce valid JSON.
|
|
117
|
+
echo "${STATUS_JSON}" | node -e "
|
|
118
|
+
const d = JSON.parse(require('fs').readFileSync('/dev/stdin','utf8'));
|
|
119
|
+
if (typeof d.indexedFileCount !== 'number') { console.error('Missing indexedFileCount'); process.exit(1); }
|
|
120
|
+
if (typeof d.stale !== 'boolean') { console.error('Missing stale'); process.exit(1); }
|
|
121
|
+
console.log('JSON shape OK');
|
|
122
|
+
" || fail "graph status --json produced invalid JSON"
|
|
123
|
+
|
|
124
|
+
ok "graph status succeeded"
|
|
125
|
+
|
|
126
|
+
# ── Step 6: onboard ───────────────────────────────────────────────────────────
|
|
127
|
+
info "Running: agent-bober onboard"
|
|
128
|
+
# onboard requires a live graph engine; run it and check artifacts
|
|
129
|
+
run_bober onboard || warn "onboard exited non-zero (graph may not be fully ready)"
|
|
130
|
+
|
|
131
|
+
ONBOARD_DIR="${TMP_DIR}/.bober/onboarding"
|
|
132
|
+
if [[ -d "${ONBOARD_DIR}" ]]; then
|
|
133
|
+
ARTIFACT_COUNT="$(ls "${ONBOARD_DIR}"/*.md 2>/dev/null | wc -l | tr -d ' ')"
|
|
134
|
+
if [[ "${ARTIFACT_COUNT}" -eq 5 ]]; then
|
|
135
|
+
ok "onboard wrote 5 artifacts"
|
|
136
|
+
else
|
|
137
|
+
warn "onboard wrote ${ARTIFACT_COUNT}/5 artifacts (graph may be warming up)"
|
|
138
|
+
fi
|
|
139
|
+
else
|
|
140
|
+
warn "onboard directory not created (graph engine may not be ready)"
|
|
141
|
+
fi
|
|
142
|
+
|
|
143
|
+
# ── Step 7: impact ────────────────────────────────────────────────────────────
|
|
144
|
+
info "Running: agent-bober impact sandboxPath"
|
|
145
|
+
run_bober impact sandboxPath || warn "impact exited non-zero (graph may not be fully ready)"
|
|
146
|
+
|
|
147
|
+
IMPACT_FILE="${TMP_DIR}/.bober/graph/impact/sandboxpath.md"
|
|
148
|
+
if [[ -f "${IMPACT_FILE}" ]]; then
|
|
149
|
+
ok "impact report written: .bober/graph/impact/sandboxpath.md"
|
|
150
|
+
# Verify required sections
|
|
151
|
+
if grep -q "^# Impact: sandboxPath" "${IMPACT_FILE}" && \
|
|
152
|
+
grep -q "^## Affected symbols" "${IMPACT_FILE}" && \
|
|
153
|
+
grep -q "^## Tests covering this symbol" "${IMPACT_FILE}"; then
|
|
154
|
+
ok "impact report has all required sections"
|
|
155
|
+
else
|
|
156
|
+
fail "impact report is missing required sections"
|
|
157
|
+
fi
|
|
158
|
+
else
|
|
159
|
+
warn "impact file not created (graph engine may not be ready)"
|
|
160
|
+
fi
|
|
161
|
+
|
|
162
|
+
# ── Done ──────────────────────────────────────────────────────────────────────
|
|
163
|
+
echo ""
|
|
164
|
+
ok "e2e-graph-smoke.sh completed"
|
|
165
|
+
echo ""
|
|
166
|
+
echo " Temp project: ${TMP_DIR} (cleaned up)"
|
|
167
|
+
echo " Tokensave: ${TOKENSAVE_VERSION}"
|
|
@@ -0,0 +1,151 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* PostToolUse hook for Edit|Write tools.
|
|
4
|
+
*
|
|
5
|
+
* Claude Code invokes this script after every Edit/Write tool call,
|
|
6
|
+
* passing tool metadata via stdin (JSON) per the hook contract.
|
|
7
|
+
*
|
|
8
|
+
* Contract:
|
|
9
|
+
* - Read bober.config.json sync; exit 0 if graph.enabled=false or graph.autoSync=false.
|
|
10
|
+
* - Read JSON payload from stdin (Claude Code hook protocol).
|
|
11
|
+
* - Extract file paths (tool_input.file_path for Edit/Write).
|
|
12
|
+
* - Validate each path is inside the project root (sandboxPath logic mirrored
|
|
13
|
+
* from src/orchestrator/tools/handlers.ts:31-45).
|
|
14
|
+
* - Append one JSON line to .bober/graph/.hook-queue.jsonl: {ts, tool, paths}.
|
|
15
|
+
* - Exit 0 in <50ms. No tokensave invocation here.
|
|
16
|
+
*
|
|
17
|
+
* Cross-platform notes:
|
|
18
|
+
* - Shebang is present but Windows uses the hooks.json command directly:
|
|
19
|
+
* "command": "node scripts/graph-hook.mjs" (NOT a bare path).
|
|
20
|
+
* - All path operations use node:path, no shell quoting.
|
|
21
|
+
* - Uses fs SYNC calls only (readFileSync, appendFileSync) so the script
|
|
22
|
+
* can return as soon as the event loop drains. No promises.
|
|
23
|
+
*/
|
|
24
|
+
|
|
25
|
+
import { readFileSync, appendFileSync, mkdirSync, existsSync } from "node:fs";
|
|
26
|
+
import { resolve, relative, isAbsolute, dirname } from "node:path";
|
|
27
|
+
|
|
28
|
+
const PROJECT_ROOT = process.cwd();
|
|
29
|
+
|
|
30
|
+
// ── Helpers ────────────────────────────────────────────────────────
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Mirror of src/orchestrator/tools/handlers.ts:31-45 sandboxPath.
|
|
34
|
+
* Returns null instead of throwing when the path is outside the sandbox,
|
|
35
|
+
* so the hook script can silently drop + log an incident rather than crash.
|
|
36
|
+
*/
|
|
37
|
+
function sandboxPath(projectRoot, inputPath) {
|
|
38
|
+
if (typeof inputPath !== "string" || !inputPath) return null;
|
|
39
|
+
const abs = isAbsolute(inputPath) ? resolve(inputPath) : resolve(projectRoot, inputPath);
|
|
40
|
+
const rel = relative(projectRoot, abs);
|
|
41
|
+
if (rel.startsWith("..") || isAbsolute(rel)) return null;
|
|
42
|
+
return abs;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
function readConfigSync() {
|
|
46
|
+
for (const candidate of ["bober.config.json", ".bober/config.json"]) {
|
|
47
|
+
const p = resolve(PROJECT_ROOT, candidate);
|
|
48
|
+
if (existsSync(p)) {
|
|
49
|
+
try {
|
|
50
|
+
return JSON.parse(readFileSync(p, "utf-8"));
|
|
51
|
+
} catch {
|
|
52
|
+
return null;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
return null;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function readStdinSync() {
|
|
60
|
+
// Read up to 64KB from stdin synchronously via file descriptor 0.
|
|
61
|
+
try {
|
|
62
|
+
return readFileSync(0, "utf-8");
|
|
63
|
+
} catch {
|
|
64
|
+
return "";
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
function appendSandboxDropIncident(file) {
|
|
69
|
+
// Best-effort; mirrors IncidentLog.append for the "sandbox-drop" variant.
|
|
70
|
+
try {
|
|
71
|
+
const incidentsPath = resolve(PROJECT_ROOT, ".bober/graph/incidents.jsonl");
|
|
72
|
+
mkdirSync(dirname(incidentsPath), { recursive: true });
|
|
73
|
+
appendFileSync(
|
|
74
|
+
incidentsPath,
|
|
75
|
+
JSON.stringify({
|
|
76
|
+
ts: new Date().toISOString(),
|
|
77
|
+
event: "sandbox-drop",
|
|
78
|
+
file,
|
|
79
|
+
source: "graph-hook",
|
|
80
|
+
}) + "\n",
|
|
81
|
+
"utf-8",
|
|
82
|
+
);
|
|
83
|
+
} catch {
|
|
84
|
+
// ignore — never block the tool call
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
// ── Main ───────────────────────────────────────────────────────────
|
|
89
|
+
|
|
90
|
+
function main() {
|
|
91
|
+
const config = readConfigSync();
|
|
92
|
+
const graph = config?.graph;
|
|
93
|
+
|
|
94
|
+
// Early exit when graph is disabled or autoSync is off.
|
|
95
|
+
// The hook entry stays registered in hooks.json (per s8-c9) but does nothing.
|
|
96
|
+
if (!graph || graph.enabled === false) return 0;
|
|
97
|
+
if (graph.autoSync === false) return 0;
|
|
98
|
+
|
|
99
|
+
const raw = readStdinSync();
|
|
100
|
+
let payload = {};
|
|
101
|
+
try {
|
|
102
|
+
payload = raw.trim() ? JSON.parse(raw) : {};
|
|
103
|
+
} catch {
|
|
104
|
+
// Malformed payload — exit cleanly with a warning; never crash.
|
|
105
|
+
process.stderr.write("[graph-hook] Warning: malformed stdin payload\n");
|
|
106
|
+
return 0;
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
// Claude Code hook payload shape:
|
|
110
|
+
// { tool_name, tool_input: { file_path?, edits?[{file_path?}] }, ... }
|
|
111
|
+
const tool = payload.tool_name ?? "unknown";
|
|
112
|
+
const candidatePaths = [];
|
|
113
|
+
const ti = payload.tool_input ?? {};
|
|
114
|
+
if (typeof ti.file_path === "string") candidatePaths.push(ti.file_path);
|
|
115
|
+
if (Array.isArray(ti.edits)) {
|
|
116
|
+
for (const e of ti.edits) {
|
|
117
|
+
if (typeof e?.file_path === "string") candidatePaths.push(e.file_path);
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
// Sandbox-validate every path. Drop any path outside the project root
|
|
122
|
+
// with a silent incident log.
|
|
123
|
+
const validated = [];
|
|
124
|
+
for (const p of candidatePaths) {
|
|
125
|
+
const sb = sandboxPath(PROJECT_ROOT, p);
|
|
126
|
+
if (sb === null) appendSandboxDropIncident(p);
|
|
127
|
+
else validated.push(sb);
|
|
128
|
+
}
|
|
129
|
+
if (validated.length === 0) return 0;
|
|
130
|
+
|
|
131
|
+
// Append to IPC queue file. mkdir is defensive.
|
|
132
|
+
const queueFile = resolve(PROJECT_ROOT, ".bober/graph/.hook-queue.jsonl");
|
|
133
|
+
try {
|
|
134
|
+
mkdirSync(dirname(queueFile), { recursive: true });
|
|
135
|
+
appendFileSync(
|
|
136
|
+
queueFile,
|
|
137
|
+
JSON.stringify({
|
|
138
|
+
ts: new Date().toISOString(),
|
|
139
|
+
tool,
|
|
140
|
+
paths: validated,
|
|
141
|
+
}) + "\n",
|
|
142
|
+
"utf-8",
|
|
143
|
+
);
|
|
144
|
+
} catch {
|
|
145
|
+
// Best-effort; never block the tool call
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
return 0;
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
process.exit(main());
|
|
@@ -0,0 +1,245 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* KPI Gate (Sprint 7) — Go/No-Go for Sprints 8-10.
|
|
4
|
+
*
|
|
5
|
+
* Reads token-usage data (real or fixture), computes per-role percent
|
|
6
|
+
* reduction (baseline vs graph-enabled), writes a structured report to
|
|
7
|
+
* .bober/graph/kpi-gate-report.json, and exits:
|
|
8
|
+
* - 0 on pass (reduction.combined >= threshold)
|
|
9
|
+
* - 2 on fail
|
|
10
|
+
* - 1 on script error (cannot read fixtures, invalid env, etc.)
|
|
11
|
+
*
|
|
12
|
+
* Default threshold: 40. Override with env KPI_GATE_THRESHOLD.
|
|
13
|
+
*
|
|
14
|
+
* Modes:
|
|
15
|
+
* 1. Fixture mode (auto when --use-fixtures, KPI_FIXTURE_FILE, or any
|
|
16
|
+
* KPI_*_TOKENS_* env var is set):
|
|
17
|
+
* - Reads token data from KPI_FIXTURE_FILE (default:
|
|
18
|
+
* .bober/graph/token-usage.jsonl), OR
|
|
19
|
+
* - Reads directly from env: KPI_BASELINE_TOKENS_RESEARCHER_PHASE2,
|
|
20
|
+
* KPI_BASELINE_TOKENS_CURATOR, KPI_BASELINE_TOKENS_ARCHITECT,
|
|
21
|
+
* KPI_GATED_TOKENS_RESEARCHER_PHASE2, KPI_GATED_TOKENS_CURATOR,
|
|
22
|
+
* KPI_GATED_TOKENS_ARCHITECT (and the matching *_TURNS_* counts).
|
|
23
|
+
* 2. Real-pipeline mode (default when no fixture flags/env): TODO —
|
|
24
|
+
* run the benchmark contract twice via runPipeline(). Deferred to
|
|
25
|
+
* manual post-merge runs (per orchestrator autonomous-mode rule).
|
|
26
|
+
*/
|
|
27
|
+
|
|
28
|
+
import { readFile, writeFile, mkdir } from "node:fs/promises";
|
|
29
|
+
import { resolve, dirname } from "node:path";
|
|
30
|
+
import { fileURLToPath } from "node:url";
|
|
31
|
+
|
|
32
|
+
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
33
|
+
const ROOT = resolve(__dirname, "..");
|
|
34
|
+
|
|
35
|
+
const ROLES = ["researcher-phase2", "curator", "architect"];
|
|
36
|
+
const DEFAULT_THRESHOLD = 40;
|
|
37
|
+
const DIVERGENCE_PCT = 10; // s7-c9: turn-count vs token-count divergence flag
|
|
38
|
+
|
|
39
|
+
function envInt(name, fallback) {
|
|
40
|
+
const v = process.env[name];
|
|
41
|
+
if (v === undefined) return fallback;
|
|
42
|
+
const n = Number(v);
|
|
43
|
+
if (!Number.isFinite(n)) return fallback;
|
|
44
|
+
return n;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
function tokensEnvFor(prefix, role) {
|
|
48
|
+
// KPI_BASELINE_TOKENS_RESEARCHER_PHASE2, KPI_GATED_TOKENS_CURATOR, etc.
|
|
49
|
+
const upper = role.toUpperCase().replace(/-/g, "_");
|
|
50
|
+
return envInt(`${prefix}_${upper}`, undefined);
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
function turnsEnvFor(prefix, role) {
|
|
54
|
+
const upper = role.toUpperCase().replace(/-/g, "_");
|
|
55
|
+
return envInt(`${prefix}_TURNS_${upper}`, undefined);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
function shouldUseFixtures(argv) {
|
|
59
|
+
if (argv.includes("--use-fixtures")) return true;
|
|
60
|
+
if (process.env.KPI_FIXTURE_FILE) return true;
|
|
61
|
+
for (const role of ROLES) {
|
|
62
|
+
if (tokensEnvFor("KPI_BASELINE_TOKENS", role) !== undefined) return true;
|
|
63
|
+
if (tokensEnvFor("KPI_GATED_TOKENS", role) !== undefined) return true;
|
|
64
|
+
}
|
|
65
|
+
return false;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
async function loadFixtureRecords(filePath) {
|
|
69
|
+
// Read JSONL — one record per line, same shape as src/graph/token-usage.ts.
|
|
70
|
+
const raw = await readFile(filePath, "utf-8");
|
|
71
|
+
const records = [];
|
|
72
|
+
for (const line of raw.split("\n")) {
|
|
73
|
+
const t = line.trim();
|
|
74
|
+
if (!t) continue;
|
|
75
|
+
try {
|
|
76
|
+
records.push(JSON.parse(t));
|
|
77
|
+
} catch {
|
|
78
|
+
// Skip malformed lines (incidents.jsonl style — never throw).
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
return records;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
function aggregateRecords(records) {
|
|
85
|
+
// Returns: { baseline: {role: {tokens, turns}}, gated: {...} }
|
|
86
|
+
// tokens = inputTokens + outputTokens, turns = count of records per role.
|
|
87
|
+
const out = { baseline: {}, gated: {} };
|
|
88
|
+
for (const role of ROLES) {
|
|
89
|
+
out.baseline[role] = { tokens: 0, turns: 0 };
|
|
90
|
+
out.gated[role] = { tokens: 0, turns: 0 };
|
|
91
|
+
}
|
|
92
|
+
for (const r of records) {
|
|
93
|
+
if (!r || typeof r !== "object") continue;
|
|
94
|
+
if (!ROLES.includes(r.agent)) continue;
|
|
95
|
+
const bucket = r.graphEnabled === true ? out.gated : out.baseline;
|
|
96
|
+
const slot = bucket[r.agent];
|
|
97
|
+
slot.tokens += (r.inputTokens ?? 0) + (r.outputTokens ?? 0);
|
|
98
|
+
slot.turns += 1;
|
|
99
|
+
}
|
|
100
|
+
return out;
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
function overrideWithEnv(agg) {
|
|
104
|
+
// Env vars take precedence over JSONL fixture for explicit pass/fail cases.
|
|
105
|
+
for (const role of ROLES) {
|
|
106
|
+
const bTok = tokensEnvFor("KPI_BASELINE_TOKENS", role);
|
|
107
|
+
if (bTok !== undefined) agg.baseline[role].tokens = bTok;
|
|
108
|
+
const gTok = tokensEnvFor("KPI_GATED_TOKENS", role);
|
|
109
|
+
if (gTok !== undefined) agg.gated[role].tokens = gTok;
|
|
110
|
+
const bTurns = turnsEnvFor("KPI_BASELINE", role);
|
|
111
|
+
if (bTurns !== undefined) agg.baseline[role].turns = bTurns;
|
|
112
|
+
const gTurns = turnsEnvFor("KPI_GATED", role);
|
|
113
|
+
if (gTurns !== undefined) agg.gated[role].turns = gTurns;
|
|
114
|
+
}
|
|
115
|
+
return agg;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
function pct(baseline, gated) {
|
|
119
|
+
if (!Number.isFinite(baseline) || baseline <= 0) return 0;
|
|
120
|
+
return Number((((baseline - gated) / baseline) * 100).toFixed(2));
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
function computeReduction(agg) {
|
|
124
|
+
const reduction = {};
|
|
125
|
+
let totalBaseline = 0;
|
|
126
|
+
let weightedSum = 0;
|
|
127
|
+
for (const role of ROLES) {
|
|
128
|
+
const b = agg.baseline[role].tokens;
|
|
129
|
+
const g = agg.gated[role].tokens;
|
|
130
|
+
reduction[role] = pct(b, g);
|
|
131
|
+
totalBaseline += b;
|
|
132
|
+
weightedSum += (b - g);
|
|
133
|
+
}
|
|
134
|
+
reduction.combined = totalBaseline > 0
|
|
135
|
+
? Number(((weightedSum / totalBaseline) * 100).toFixed(2))
|
|
136
|
+
: 0;
|
|
137
|
+
return reduction;
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
function computeTurnDelta(agg) {
|
|
141
|
+
const delta = {};
|
|
142
|
+
for (const role of ROLES) {
|
|
143
|
+
delta[role] = pct(agg.baseline[role].turns, agg.gated[role].turns);
|
|
144
|
+
}
|
|
145
|
+
return delta;
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
function hasDivergence(reduction, turnDelta) {
|
|
149
|
+
// s7-c9: if turn-delta and token-delta differ by >10 pp for any gated role,
|
|
150
|
+
// flag for human review.
|
|
151
|
+
for (const role of ROLES) {
|
|
152
|
+
if (Math.abs(reduction[role] - turnDelta[role]) > DIVERGENCE_PCT) return true;
|
|
153
|
+
}
|
|
154
|
+
return false;
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
function buildRecommendations(report) {
|
|
158
|
+
const lines = [];
|
|
159
|
+
if (report.gatePass) return lines;
|
|
160
|
+
const arch = ".bober/architecture/arch-20260524-port-code-review-graph-architecture.md";
|
|
161
|
+
lines.push(`Combined reduction ${report.reduction.combined}% is below threshold ${report.threshold}%.`);
|
|
162
|
+
lines.push(`Review per-role deltas: researcher-phase2=${report.reduction["researcher-phase2"]}%, curator=${report.reduction.curator}%, architect=${report.reduction.architect}%.`);
|
|
163
|
+
lines.push(`Open questions on budget tuning: see ${arch} (preflight-budgets section).`);
|
|
164
|
+
lines.push(`Consider: (a) raising per-role token budgets, (b) tightening QUERY_BATCHES, (c) adding graph_review_context calls in agent prompts.`);
|
|
165
|
+
return lines;
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
async function main() {
|
|
169
|
+
const argv = process.argv.slice(2);
|
|
170
|
+
const threshold = envInt("KPI_GATE_THRESHOLD", DEFAULT_THRESHOLD);
|
|
171
|
+
|
|
172
|
+
let agg;
|
|
173
|
+
if (shouldUseFixtures(argv)) {
|
|
174
|
+
const fixturePath = process.env.KPI_FIXTURE_FILE
|
|
175
|
+
?? resolve(ROOT, ".bober/graph/token-usage.jsonl");
|
|
176
|
+
let records = [];
|
|
177
|
+
try {
|
|
178
|
+
records = await loadFixtureRecords(fixturePath);
|
|
179
|
+
} catch (err) {
|
|
180
|
+
// Missing fixture file is OK when env overrides will fill the values.
|
|
181
|
+
if (err && err.code !== "ENOENT") throw err;
|
|
182
|
+
}
|
|
183
|
+
agg = aggregateRecords(records);
|
|
184
|
+
agg = overrideWithEnv(agg);
|
|
185
|
+
} else {
|
|
186
|
+
console.error("Real-pipeline KPI mode not implemented in this script. Use --use-fixtures or env overrides.");
|
|
187
|
+
console.error("TODO: invoke runPipeline twice (graphEnabled=false, then graphEnabled=true) against tests/benchmarks/curator-benchmark-contract.json.");
|
|
188
|
+
process.exit(1);
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
const reduction = computeReduction(agg);
|
|
192
|
+
const turnDelta = computeTurnDelta(agg);
|
|
193
|
+
const divergenceFlag = hasDivergence(reduction, turnDelta);
|
|
194
|
+
const gatePass = reduction.combined >= threshold;
|
|
195
|
+
|
|
196
|
+
const report = {
|
|
197
|
+
baseline: {
|
|
198
|
+
"researcher-phase2": agg.baseline["researcher-phase2"].tokens,
|
|
199
|
+
curator: agg.baseline.curator.tokens,
|
|
200
|
+
architect: agg.baseline.architect.tokens,
|
|
201
|
+
},
|
|
202
|
+
gated: {
|
|
203
|
+
"researcher-phase2": agg.gated["researcher-phase2"].tokens,
|
|
204
|
+
curator: agg.gated.curator.tokens,
|
|
205
|
+
architect: agg.gated.architect.tokens,
|
|
206
|
+
},
|
|
207
|
+
reduction, // includes researcher-phase2, curator, architect, combined
|
|
208
|
+
turnCounts: {
|
|
209
|
+
baseline: {
|
|
210
|
+
"researcher-phase2": agg.baseline["researcher-phase2"].turns,
|
|
211
|
+
curator: agg.baseline.curator.turns,
|
|
212
|
+
architect: agg.baseline.architect.turns,
|
|
213
|
+
},
|
|
214
|
+
gated: {
|
|
215
|
+
"researcher-phase2": agg.gated["researcher-phase2"].turns,
|
|
216
|
+
curator: agg.gated.curator.turns,
|
|
217
|
+
architect: agg.gated.architect.turns,
|
|
218
|
+
},
|
|
219
|
+
},
|
|
220
|
+
turnCountDelta: turnDelta,
|
|
221
|
+
divergenceFlag,
|
|
222
|
+
gatePass,
|
|
223
|
+
threshold,
|
|
224
|
+
timestamp: new Date().toISOString(),
|
|
225
|
+
recommendations: undefined, // filled below
|
|
226
|
+
};
|
|
227
|
+
report.recommendations = buildRecommendations(report);
|
|
228
|
+
|
|
229
|
+
const outPath = resolve(ROOT, ".bober/graph/kpi-gate-report.json");
|
|
230
|
+
await mkdir(dirname(outPath), { recursive: true });
|
|
231
|
+
await writeFile(outPath, JSON.stringify(report, null, 2) + "\n", "utf-8");
|
|
232
|
+
|
|
233
|
+
console.log(`KPI gate: ${gatePass ? "PASS" : "FAIL"} (combined=${reduction.combined}%, threshold=${threshold}%)`);
|
|
234
|
+
console.log(`Report: ${outPath}`);
|
|
235
|
+
if (divergenceFlag) {
|
|
236
|
+
console.warn("Warning: TURNCOUNT_DIVERGENCE — turn-count and token-count reductions diverge by >10pp on at least one role.");
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
process.exit(gatePass ? 0 : 2);
|
|
240
|
+
}
|
|
241
|
+
|
|
242
|
+
main().catch((err) => {
|
|
243
|
+
console.error("KPI gate script error:", err);
|
|
244
|
+
process.exit(1);
|
|
245
|
+
});
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// SPIKE runner: prove ClaudeCodeAdapter satisfies LLMClient.chat() end-to-end
|
|
3
|
+
// against the user's Claude subscription (NO ANTHROPIC_API_KEY).
|
|
4
|
+
//
|
|
5
|
+
// node scripts/spike-claude-code-provider.mjs
|
|
6
|
+
//
|
|
7
|
+
// Builds nothing; imports the compiled dist adapter (run `npm run build` first).
|
|
8
|
+
// Exercises the real `claude -p` subprocess. Prints the normalized ChatResponse
|
|
9
|
+
// and asserts the contract shape. Also demonstrates the tools-rejection guard.
|
|
10
|
+
|
|
11
|
+
import { spawnSync } from "node:child_process";
|
|
12
|
+
import { ClaudeCodeAdapter } from "../dist/providers/claude-code.js";
|
|
13
|
+
|
|
14
|
+
const probe = spawnSync("claude", ["--version"], { stdio: "ignore" });
|
|
15
|
+
if (probe.error || probe.status !== 0) {
|
|
16
|
+
console.log("SKIP: `claude` binary not on PATH — skipping claude-code smoke.");
|
|
17
|
+
process.exit(0);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
function assert(cond, msg) {
|
|
21
|
+
if (!cond) {
|
|
22
|
+
console.error("ASSERT FAILED:", msg);
|
|
23
|
+
process.exit(1);
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
const adapter = new ClaudeCodeAdapter();
|
|
28
|
+
|
|
29
|
+
console.log("── Spike 1: no-tools planner-style completion (real subscription call) ──");
|
|
30
|
+
const res = await adapter.chat({
|
|
31
|
+
model: "haiku", // cheapest for a spike; proves the seam without burning credit
|
|
32
|
+
system:
|
|
33
|
+
"You are a terse planning assistant. Answer in one short sentence, no preamble.",
|
|
34
|
+
messages: [
|
|
35
|
+
{ role: "user", content: "Name one risk of building a feature without tests." },
|
|
36
|
+
],
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
console.log("text:", JSON.stringify(res.text));
|
|
40
|
+
console.log("stopReason:", res.stopReason);
|
|
41
|
+
console.log("usage:", JSON.stringify(res.usage));
|
|
42
|
+
|
|
43
|
+
assert(typeof res.text === "string" && res.text.length > 0, "text should be non-empty");
|
|
44
|
+
assert(Array.isArray(res.toolCalls) && res.toolCalls.length === 0, "toolCalls should be empty");
|
|
45
|
+
assert(typeof res.usage.inputTokens === "number", "usage.inputTokens should be a number");
|
|
46
|
+
assert(typeof res.usage.outputTokens === "number", "usage.outputTokens should be a number");
|
|
47
|
+
console.log("✓ ChatResponse contract satisfied via subscription (no API key)\n");
|
|
48
|
+
|
|
49
|
+
console.log("── Spike 2: tools guard must throw (honest about the limitation) ──");
|
|
50
|
+
let threw = false;
|
|
51
|
+
try {
|
|
52
|
+
await adapter.chat({
|
|
53
|
+
model: "haiku",
|
|
54
|
+
system: "x",
|
|
55
|
+
messages: [{ role: "user", content: "y" }],
|
|
56
|
+
tools: [
|
|
57
|
+
{ name: "do_thing", description: "d", input_schema: { type: "object", properties: {} } },
|
|
58
|
+
],
|
|
59
|
+
});
|
|
60
|
+
} catch (err) {
|
|
61
|
+
threw = true;
|
|
62
|
+
console.log("✓ threw as designed:", err.message.split(":")[0]);
|
|
63
|
+
}
|
|
64
|
+
assert(threw, "adapter must reject custom tools rather than silently drop them");
|
|
65
|
+
|
|
66
|
+
console.log("\nSPIKE PASSED — claude -p backs LLMClient for no-tools roles on the subscription.");
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// SPIKE: verify DeepSeek works through the EXISTING openai-compat adapter,
|
|
3
|
+
// including TOOL CALLING (the capability that makes it usable for ALL roles,
|
|
4
|
+
// unlike the claude-code provider). No new adapter code — this is the whole point.
|
|
5
|
+
//
|
|
6
|
+
// DEEPSEEK_API_KEY=sk-... node scripts/spike-deepseek.mjs
|
|
7
|
+
//
|
|
8
|
+
// Run `npm run build` first (imports compiled dist).
|
|
9
|
+
|
|
10
|
+
import { createClient } from "../dist/providers/factory.js";
|
|
11
|
+
|
|
12
|
+
const key = process.env.DEEPSEEK_API_KEY;
|
|
13
|
+
if (!key) {
|
|
14
|
+
console.log("SKIP: DEEPSEEK_API_KEY not set — skipping DeepSeek smoke.");
|
|
15
|
+
process.exit(0);
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
function assert(c, m) { if (!c) { console.error("ASSERT FAILED:", m); process.exit(1); } }
|
|
19
|
+
|
|
20
|
+
// Existing openai-compat adapter, pointed at DeepSeek's OpenAI-compatible endpoint.
|
|
21
|
+
const client = createClient(
|
|
22
|
+
"openai-compat",
|
|
23
|
+
"https://api.deepseek.com",
|
|
24
|
+
{ apiKey: key },
|
|
25
|
+
"deepseek-v4-pro",
|
|
26
|
+
"Spike",
|
|
27
|
+
);
|
|
28
|
+
|
|
29
|
+
console.log("── Spike 1: plain completion via DeepSeek (openai-compat) ──");
|
|
30
|
+
const r1 = await client.chat({
|
|
31
|
+
model: "deepseek-v4-pro",
|
|
32
|
+
system: "You are terse. One sentence, no preamble.",
|
|
33
|
+
messages: [{ role: "user", content: "What is a code knowledge graph, in one sentence?" }],
|
|
34
|
+
});
|
|
35
|
+
console.log("text:", JSON.stringify(r1.text).slice(0, 200));
|
|
36
|
+
console.log("stopReason:", r1.stopReason, "| usage:", JSON.stringify(r1.usage));
|
|
37
|
+
assert(typeof r1.text === "string" && r1.text.length > 0, "text non-empty");
|
|
38
|
+
|
|
39
|
+
console.log("\n── Spike 2: TOOL CALLING (the differentiator vs claude-code) ──");
|
|
40
|
+
const r2 = await client.chat({
|
|
41
|
+
model: "deepseek-v4-pro",
|
|
42
|
+
system: "You are an agent. When asked to read a file, you MUST call the read_file tool. Do not answer directly.",
|
|
43
|
+
messages: [{ role: "user", content: "Read the file src/index.ts and tell me what it does." }],
|
|
44
|
+
tools: [
|
|
45
|
+
{
|
|
46
|
+
name: "read_file",
|
|
47
|
+
description: "Read a file from the project by path.",
|
|
48
|
+
input_schema: {
|
|
49
|
+
type: "object",
|
|
50
|
+
properties: { file_path: { type: "string", description: "Path to read" } },
|
|
51
|
+
required: ["file_path"],
|
|
52
|
+
},
|
|
53
|
+
},
|
|
54
|
+
],
|
|
55
|
+
});
|
|
56
|
+
console.log("stopReason:", r2.stopReason);
|
|
57
|
+
console.log("toolCalls:", JSON.stringify(r2.toolCalls, null, 2));
|
|
58
|
+
console.log("usage:", JSON.stringify(r2.usage));
|
|
59
|
+
assert(r2.toolCalls.length > 0, "DeepSeek should emit a tool_use call");
|
|
60
|
+
assert(r2.toolCalls[0].name === "read_file", "should call read_file");
|
|
61
|
+
assert(typeof r2.toolCalls[0].input?.file_path === "string", "tool input should parse with file_path");
|
|
62
|
+
|
|
63
|
+
console.log("\nDEEPSEEK SPIKE PASSED — existing openai-compat adapter drives DeepSeek WITH tool calling, all roles, zero new code.");
|