@cohortapp/agent-sdk 2.17.0 → 2.18.5
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/settings.json +18 -0
- package/.env.example +18 -5
- package/README.md +1 -0
- package/bin/maestro.mjs +62 -0
- package/docs/guides/billing-console-keys.md +60 -0
- package/docs/guides/front-door-session.md +54 -9
- package/docs/guides/mac-mini.md +20 -25
- package/docs/guides/setup-wizard.md +1 -1
- package/docs/runbooks/fleet-rollout.md +156 -0
- package/docs/runbooks/mac-mini-bootstrap.md +12 -14
- package/lib/action-executor.js +19 -3
- package/lib/budget-guard.mjs +279 -3
- package/lib/channels/base-adapter.mjs +3 -1
- package/lib/channels/contract.mjs +2 -1
- package/lib/channels/inbox-item.mjs +8 -0
- package/lib/claude-bin.mjs +5 -6
- package/lib/cli/doctor-checks.mjs +141 -10
- package/lib/cli/global-setup-extras.mjs +5 -1
- package/lib/cli/inbox.mjs +100 -15
- package/lib/cli/seat-auth.mjs +463 -0
- package/lib/cli/session.mjs +80 -12
- package/lib/collective/capture-slots.mjs +234 -0
- package/lib/collective/capture.mjs +8 -6
- package/lib/collective/config.mjs +2 -0
- package/lib/collective/global-config.mjs +63 -1
- package/lib/collective/loop-guard.mjs +155 -0
- package/lib/collective/presence.mjs +142 -5
- package/lib/comms/send-gate.mjs +559 -1
- package/lib/diagnostics/alerts.mjs +49 -0
- package/lib/diagnostics/cadence-output-freshness.mjs +288 -0
- package/lib/engine/agents/definitions.mjs +343 -0
- package/lib/engine/agents/persist.mjs +275 -0
- package/lib/engine/agents/runtime.mjs +748 -0
- package/lib/engine/agents/usage.mjs +95 -0
- package/lib/engine/auth-status.mjs +139 -0
- package/lib/engine/budget.mjs +194 -0
- package/lib/engine/cli.mjs +1204 -0
- package/lib/engine/commands/index.mjs +269 -0
- package/lib/engine/context/budget.mjs +219 -0
- package/lib/engine/context/cache.mjs +125 -0
- package/lib/engine/context/child-env.mjs +215 -0
- package/lib/engine/context/compaction.mjs +342 -0
- package/lib/engine/context/images.mjs +90 -0
- package/lib/engine/context/instructions.mjs +327 -0
- package/lib/engine/context/lazy-instructions.mjs +169 -0
- package/lib/engine/context/manager.mjs +182 -0
- package/lib/engine/context/real-path.mjs +91 -0
- package/lib/engine/context/secret-values.mjs +163 -0
- package/lib/engine/context/settings.mjs +274 -0
- package/lib/engine/context/stream-input.mjs +159 -0
- package/lib/engine/guard.mjs +152 -0
- package/lib/engine/hooks.mjs +713 -0
- package/lib/engine/loop.mjs +560 -0
- package/lib/engine/mcp/client.mjs +254 -0
- package/lib/engine/mcp/config.mjs +301 -0
- package/lib/engine/mcp/http.mjs +201 -0
- package/lib/engine/mcp/index.mjs +146 -0
- package/lib/engine/mcp/jsonrpc.mjs +147 -0
- package/lib/engine/mcp/naming.mjs +66 -0
- package/lib/engine/mcp/resources.mjs +89 -0
- package/lib/engine/mcp/results.mjs +133 -0
- package/lib/engine/mcp/stdio.mjs +137 -0
- package/lib/engine/mcp/supervisor.mjs +116 -0
- package/lib/engine/messages.mjs +104 -0
- package/lib/engine/output/json.mjs +164 -0
- package/lib/engine/output/stream-json.mjs +266 -0
- package/lib/engine/permissions.mjs +845 -0
- package/lib/engine/process-identity.mjs +164 -0
- package/lib/engine/process-tree.mjs +551 -0
- package/lib/engine/prompt.mjs +60 -0
- package/lib/engine/session/store.mjs +299 -0
- package/lib/engine/session-runtime/args.mjs +97 -0
- package/lib/engine/session-runtime/host.mjs +143 -0
- package/lib/engine/session-runtime/inbox.mjs +122 -0
- package/lib/engine/session-runtime/notifications.mjs +129 -0
- package/lib/engine/session-runtime/registry.mjs +328 -0
- package/lib/engine/session-runtime/runner.mjs +344 -0
- package/lib/engine/session-runtime/socket.mjs +212 -0
- package/lib/engine/session-runtime/wakeup.mjs +115 -0
- package/lib/engine/skills/index.mjs +321 -0
- package/lib/engine/tools/bash-background.mjs +533 -0
- package/lib/engine/tools/bash.mjs +216 -0
- package/lib/engine/tools/edit.mjs +97 -0
- package/lib/engine/tools/glob.mjs +81 -0
- package/lib/engine/tools/grep.mjs +224 -0
- package/lib/engine/tools/index.mjs +84 -0
- package/lib/engine/tools/list-agents.mjs +32 -0
- package/lib/engine/tools/ls.mjs +127 -0
- package/lib/engine/tools/monitor.mjs +82 -0
- package/lib/engine/tools/notebook-edit.mjs +218 -0
- package/lib/engine/tools/read.mjs +103 -0
- package/lib/engine/tools/schedule-wakeup.mjs +45 -0
- package/lib/engine/tools/schema.mjs +144 -0
- package/lib/engine/tools/send-message.mjs +77 -0
- package/lib/engine/tools/session.mjs +70 -0
- package/lib/engine/tools/todo.mjs +144 -0
- package/lib/engine/tools/toolsearch.mjs +217 -0
- package/lib/engine/tools/walk.mjs +193 -0
- package/lib/engine/tools/web-switch.mjs +31 -0
- package/lib/engine/tools/webfetch-html.mjs +387 -0
- package/lib/engine/tools/webfetch-net.mjs +340 -0
- package/lib/engine/tools/webfetch.mjs +198 -0
- package/lib/engine/tools/websearch.mjs +91 -0
- package/lib/engine/tools/workflow.mjs +95 -0
- package/lib/engine/tools/write.mjs +76 -0
- package/lib/engine/tui/line-editor.mjs +137 -0
- package/lib/engine/tui/render.mjs +86 -0
- package/lib/engine/tui/tui.mjs +274 -0
- package/lib/engine/wire/anthropic-messages.mjs +263 -0
- package/lib/engine/wire/effort.mjs +36 -0
- package/lib/engine/wire/errors.mjs +496 -0
- package/lib/engine/wire/http.mjs +441 -0
- package/lib/engine/wire/index.mjs +76 -0
- package/lib/engine/wire/openai-chat.mjs +332 -0
- package/lib/engine/wire/prompt-cache.mjs +79 -0
- package/lib/engine/wire/search.mjs +140 -0
- package/lib/engine/wire/sse.mjs +114 -0
- package/lib/engine/wire/stall.mjs +349 -0
- package/lib/engine/wire/token-provider.mjs +175 -0
- package/lib/engine/wire/usage.mjs +192 -0
- package/lib/engine/workflow/host.mjs +524 -0
- package/lib/engine/workflow/journal.mjs +188 -0
- package/lib/engine/workflow/json-schema.mjs +171 -0
- package/lib/engine/workflow/meta.mjs +329 -0
- package/lib/engine/workflow/notifications.mjs +52 -0
- package/lib/engine/workflow/runtime.mjs +447 -0
- package/lib/engine/workflow/sandbox.mjs +534 -0
- package/lib/engine/workflow/worker.mjs +141 -0
- package/lib/engine/workflow/worktree.mjs +74 -0
- package/lib/execution/disposition.mjs +1 -1
- package/lib/execution/intake.mjs +10 -0
- package/lib/execution/surface-policy.mjs +15 -0
- package/lib/learning/curator.mjs +8 -6
- package/lib/learning/reflect.mjs +8 -6
- package/lib/model-router/catalog/cohort.yaml +137 -0
- package/lib/model-router/catalog.mjs +118 -1
- package/lib/model-router/failover.mjs +67 -16
- package/lib/model-router/llm-task.mjs +39 -3
- package/lib/model-router/resolve.mjs +89 -3
- package/lib/model-router/spawn.mjs +46 -47
- package/lib/model-router/taxonomy.mjs +126 -4
- package/lib/org/cost-sync.mjs +141 -11
- package/lib/org/inbound/broadcast.mjs +289 -0
- package/lib/org/inbound/collective.mjs +375 -0
- package/lib/org/inbound/directedness.mjs +96 -8
- package/lib/org/inbound/facts.mjs +78 -2
- package/lib/org/inbound/project.mjs +22 -0
- package/lib/org/inbound/surfaces.mjs +14 -0
- package/lib/org/llm-token.mjs +879 -0
- package/lib/org/mesh.mjs +61 -0
- package/lib/org/messaging.mjs +3 -1
- package/lib/org/protocol.checksum +1 -1
- package/lib/org/protocol.mjs +15 -0
- package/lib/org/quota.mjs +520 -0
- package/lib/org/tool-surface.mjs +104 -16
- package/lib/org/ui-parity.mjs +16 -1
- package/lib/org/work-ledger.mjs +37 -6
- package/lib/rate-guard.mjs +114 -1
- package/lib/resource-governor.mjs +41 -6
- package/lib/runtime/adapter.mjs +833 -0
- package/lib/runtime/child-env.mjs +191 -0
- package/lib/runtime/legacy-shell-guard.mjs +97 -0
- package/lib/runtime/seat-engine.mjs +162 -0
- package/lib/session/ask-ledger.mjs +271 -0
- package/lib/session/current-work.mjs +676 -0
- package/lib/session/feed-core.mjs +40 -3
- package/lib/session/launch-args.mjs +56 -4
- package/lib/session/status-summary.mjs +26 -9
- package/lib/session/upgrade-notice.mjs +42 -0
- package/lib/setup/claude-probe.mjs +117 -13
- package/lib/setup/enrich.mjs +13 -10
- package/lib/setup/sections/model.mjs +39 -13
- package/lib/telemetry/collect.mjs +229 -11
- package/lib/upgrade/ignored-drift.mjs +105 -0
- package/lib/voice/post-call-brief.mjs +30 -17
- package/package.json +13 -3
- package/plugins/maestro-skills/skills/board-work.md +5 -0
- package/plugins/maestro-skills/skills/inbound-triage.md +56 -15
- package/plugins/maestro-skills/skills/main-session.md +18 -7
- package/scaffold/config/collective.yaml +7 -0
- package/scripts/ci/check-durable-write-seam.mjs +3 -1
- package/scripts/ci/check-tarball-fidelity.mjs +126 -2
- package/scripts/ci/run-tests.mjs +47 -19
- package/scripts/cohort-llm/api-key-helper.mjs +92 -0
- package/scripts/collective/hook-runner.mjs +142 -19
- package/scripts/continuous-monitor.sh +13 -0
- package/scripts/cost/track-claude-usage.mjs +15 -0
- package/scripts/daemon/agent-daemon.mjs +408 -20
- package/scripts/daemon/assurance.mjs +48 -12
- package/scripts/daemon/cadence-consumer.mjs +218 -68
- package/scripts/daemon/cadence-handlers.mjs +73 -4
- package/scripts/daemon/classifier.mjs +75 -26
- package/scripts/daemon/context-compiler.mjs +51 -37
- package/scripts/daemon/deliver.mjs +30 -1
- package/scripts/daemon/dispatcher.mjs +595 -149
- package/scripts/daemon/health.mjs +14 -1
- package/scripts/daemon/maestro-daemon.mjs +11 -0
- package/scripts/daemon/prompt-builder.mjs +24 -0
- package/scripts/daemon/responder.mjs +246 -79
- package/scripts/daemon/sdk-version.mjs +98 -16
- package/scripts/eval/probe-gateway.mjs +635 -0
- package/scripts/eval/replay/extract.mjs +270 -0
- package/scripts/eval/replay/grade.mjs +260 -0
- package/scripts/eval/replay/lib/config.mjs +50 -0
- package/scripts/eval/replay/lib/effects.mjs +65 -0
- package/scripts/eval/replay/lib/fixture.mjs +188 -0
- package/scripts/eval/replay/lib/judge.mjs +72 -0
- package/scripts/eval/replay/lib/redact.mjs +136 -0
- package/scripts/eval/replay/lib/sandbox.mjs +170 -0
- package/scripts/eval/replay/lib/schema-check.mjs +63 -0
- package/scripts/eval/replay/lib/transcript.mjs +76 -0
- package/scripts/eval/replay/mcp-replay-stub.mjs +101 -0
- package/scripts/eval/replay/report.mjs +185 -0
- package/scripts/eval/replay/run.mjs +404 -0
- package/scripts/fleet/rollout.mjs +1151 -0
- package/scripts/hooks/pre-send-audit.sh +36 -245
- package/scripts/hooks/pre-write-yaml-validate.mjs +275 -0
- package/scripts/hooks/validate-state-yaml.sh +190 -0
- package/scripts/huddle/huddle-llm.mjs +361 -0
- package/scripts/huddle/huddle-server.mjs +46 -121
- package/scripts/local-triggers/autoupdate.sh +465 -81
- package/scripts/local-triggers/run-trigger.sh +13 -0
- package/scripts/maintenance/pin-integrity.mjs +364 -0
- package/scripts/poll-slack-events.sh +41 -9
- package/scripts/poller/slack-socket-mode.mjs +28 -3
- package/scripts/session/supervisor.mjs +80 -13
- package/scripts/spawn-session.sh +13 -0
- package/bin/maestro.test.mjs +0 -1574
- package/lib/action-executor.test.mjs +0 -871
- package/lib/archetype.test.mjs +0 -132
- package/lib/assurance/plan-note.test.mjs +0 -234
- package/lib/assurance/room-budget.test.mjs +0 -486
- package/lib/assurance/tier.test.mjs +0 -174
- package/lib/autonomy.test.mjs +0 -66
- package/lib/backlog.test.mjs +0 -302
- package/lib/backup/policy.test.mjs +0 -305
- package/lib/budget-escalate.test.mjs +0 -232
- package/lib/budget-guard.envelope.test.mjs +0 -476
- package/lib/budget-guard.test.mjs +0 -427
- package/lib/cadence-bus-requeue.test.mjs +0 -83
- package/lib/cadence-bus-schedule.test.mjs +0 -194
- package/lib/cadence-bus.test.mjs +0 -720
- package/lib/cadences.test.mjs +0 -230
- package/lib/capability/inventory.test.mjs +0 -232
- package/lib/capability.test.mjs +0 -78
- package/lib/channels/base-adapter.test.mjs +0 -590
- package/lib/channels/channels.test.mjs +0 -371
- package/lib/channels/contract.test.mjs +0 -162
- package/lib/channels/inbox-item.test.mjs +0 -368
- package/lib/channels/orgmail/adapter.test.mjs +0 -448
- package/lib/channels/pairing.test.mjs +0 -270
- package/lib/channels/repeat-suppressor.test.mjs +0 -134
- package/lib/channels/slack-adapter.test.mjs +0 -212
- package/lib/channels/telegram-adapter.test.mjs +0 -306
- package/lib/channels/voice/adapter.test.mjs +0 -278
- package/lib/channels/whatsapp/adapter-baileys.test.mjs +0 -359
- package/lib/channels/whatsapp/baileys-typing.test.mjs +0 -154
- package/lib/charter.test.mjs +0 -89
- package/lib/claude-bin.test.mjs +0 -131
- package/lib/cli/board.test.mjs +0 -227
- package/lib/cli/design.test.mjs +0 -270
- package/lib/cli/doctor-checks.test.mjs +0 -336
- package/lib/cli/global-setup-extras.test.mjs +0 -462
- package/lib/cli/inbox.test.mjs +0 -230
- package/lib/cli/session-ack.test.mjs +0 -63
- package/lib/cli/session.test.mjs +0 -613
- package/lib/collective/capture.test.mjs +0 -121
- package/lib/collective/cards.test.mjs +0 -114
- package/lib/collective/config.test.mjs +0 -123
- package/lib/collective/global-config.test.mjs +0 -220
- package/lib/collective/global-skills.test.mjs +0 -126
- package/lib/collective/presence.test.mjs +0 -95
- package/lib/collective/recall.test.mjs +0 -116
- package/lib/collective/vendor-skills.test.mjs +0 -306
- package/lib/comms/send-gate.test.mjs +0 -770
- package/lib/comms.test.mjs +0 -41
- package/lib/context/budget.test.mjs +0 -252
- package/lib/context/history-scope.test.mjs +0 -79
- package/lib/cost/ledger-row.test.mjs +0 -183
- package/lib/design/design-md.test.mjs +0 -318
- package/lib/design/fixtures/DESIGN.golden.md +0 -238
- package/lib/design/fixtures/PRODUCT.golden.md +0 -67
- package/lib/design/fixtures/foundation.json +0 -133
- package/lib/design/refresh-gate.test.mjs +0 -144
- package/lib/design/write.test.mjs +0 -241
- package/lib/diagnostics/alerts.test.mjs +0 -318
- package/lib/diagnostics/backup-freshness.test.mjs +0 -185
- package/lib/diagnostics/counters.test.mjs +0 -206
- package/lib/diagnostics/events.test.mjs +0 -290
- package/lib/diagnostics/otel.test.mjs +0 -196
- package/lib/diagnostics/trace.test.mjs +0 -251
- package/lib/env-compat.test.mjs +0 -104
- package/lib/execution/disposition.test.mjs +0 -553
- package/lib/execution/drive.test.mjs +0 -270
- package/lib/execution/effects.test.mjs +0 -344
- package/lib/execution/intake.test.mjs +0 -389
- package/lib/execution/journal.test.mjs +0 -261
- package/lib/execution/match.test.mjs +0 -235
- package/lib/execution/pipeline.test.mjs +0 -392
- package/lib/execution/route.test.mjs +0 -186
- package/lib/execution/surface-policy.test.mjs +0 -162
- package/lib/fs-atomic.test.mjs +0 -72
- package/lib/fs-ownership.test.mjs +0 -158
- package/lib/goals/admission.test.mjs +0 -164
- package/lib/goals/classify.test.mjs +0 -167
- package/lib/goals/collaborate.test.mjs +0 -336
- package/lib/goals/gaps.test.mjs +0 -284
- package/lib/goals/loop.test.mjs +0 -845
- package/lib/hooks/bus.test.mjs +0 -387
- package/lib/identity/persona.test.mjs +0 -142
- package/lib/kpi-sensors.test.mjs +0 -278
- package/lib/kpi.test.mjs +0 -244
- package/lib/learning/config.test.mjs +0 -75
- package/lib/learning/counters.test.mjs +0 -69
- package/lib/learning/curator-consolidate.test.mjs +0 -238
- package/lib/learning/curator.test.mjs +0 -106
- package/lib/learning/reflect.test.mjs +0 -0
- package/lib/learning/session-index.test.mjs +0 -125
- package/lib/learning/skill-writer.test.mjs +0 -210
- package/lib/mandate/audit.test.mjs +0 -195
- package/lib/mandate/contract.test.mjs +0 -185
- package/lib/mandate/derive.test.mjs +0 -274
- package/lib/mandate/model.test.mjs +0 -164
- package/lib/mandate/refresh.test.mjs +0 -389
- package/lib/mcp/server.test.mjs +0 -426
- package/lib/model-router/auth-profiles.test.mjs +0 -580
- package/lib/model-router/catalog.test.mjs +0 -385
- package/lib/model-router/economics.test.mjs +0 -438
- package/lib/model-router/failover.test.mjs +0 -439
- package/lib/model-router/health.test.mjs +0 -338
- package/lib/model-router/integration-coverage.test.mjs +0 -831
- package/lib/model-router/integration.test.mjs +0 -564
- package/lib/model-router/ledger.test.mjs +0 -415
- package/lib/model-router/llm-task.test.mjs +0 -392
- package/lib/model-router/org-credentials.test.mjs +0 -265
- package/lib/model-router/pricing-refresh.test.mjs +0 -286
- package/lib/model-router/reconcile.test.mjs +0 -316
- package/lib/model-router/repair.test.mjs +0 -180
- package/lib/model-router/spawn.test.mjs +0 -446
- package/lib/model-router/taxonomy.test.mjs +0 -410
- package/lib/model-router.test.mjs +0 -1207
- package/lib/org/activity.test.mjs +0 -134
- package/lib/org/approvals.test.mjs +0 -216
- package/lib/org/awareness.test.mjs +0 -159
- package/lib/org/board-mine-cache.test.mjs +0 -53
- package/lib/org/board.test.mjs +0 -187
- package/lib/org/bootstrap-context.test.mjs +0 -153
- package/lib/org/client.test.mjs +0 -1206
- package/lib/org/cohort-client.test.mjs +0 -126
- package/lib/org/cost-sync.test.mjs +0 -153
- package/lib/org/doctor.test.mjs +0 -346
- package/lib/org/engagement-ledger.test.mjs +0 -112
- package/lib/org/engagement.test.mjs +0 -739
- package/lib/org/handoff.test.mjs +0 -269
- package/lib/org/inbound/directedness.test.mjs +0 -668
- package/lib/org/inbound/facts.test.mjs +0 -471
- package/lib/org/inbound/hydrate.test.mjs +0 -908
- package/lib/org/inbound/index.test.mjs +0 -429
- package/lib/org/inbound/project.test.mjs +0 -287
- package/lib/org/integration-tools.test.mjs +0 -160
- package/lib/org/keys.test.mjs +0 -92
- package/lib/org/knowledge.test.mjs +0 -326
- package/lib/org/leases.test.mjs +0 -235
- package/lib/org/mesh-directives.test.mjs +0 -110
- package/lib/org/mesh-integration.test.mjs +0 -127
- package/lib/org/mesh.test.mjs +0 -400
- package/lib/org/messaging.test.mjs +0 -471
- package/lib/org/param-contract.test.mjs +0 -477
- package/lib/org/policy.test.mjs +0 -237
- package/lib/org/protocol.checksum.test.mjs +0 -90
- package/lib/org/protocol.test.mjs +0 -323
- package/lib/org/push.test.mjs +0 -792
- package/lib/org/registry.test.mjs +0 -100
- package/lib/org/resource-tools.test.mjs +0 -361
- package/lib/org/tool-access.test.mjs +0 -144
- package/lib/org/tool-surface-integration.test.mjs +0 -120
- package/lib/org/tool-surface.test.mjs +0 -1268
- package/lib/org/typing.test.mjs +0 -291
- package/lib/org/ui-parity.test.mjs +0 -560
- package/lib/org/verify.test.mjs +0 -194
- package/lib/org/work-ledger.test.mjs +0 -273
- package/lib/plan/adoption-e2e.test.mjs +0 -366
- package/lib/plan/budget-enforcement.test.mjs +0 -400
- package/lib/plan/compile.test.mjs +0 -382
- package/lib/plan/emit.test.mjs +0 -269
- package/lib/plan/explain.test.mjs +0 -188
- package/lib/prompts/parallelism.test.mjs +0 -177
- package/lib/rag/rag.test.mjs +0 -505
- package/lib/rate-guard.test.mjs +0 -272
- package/lib/reactive-gate.test.mjs +0 -57
- package/lib/render.test.mjs +0 -68
- package/lib/resource-governor.test.mjs +0 -488
- package/lib/scheduling/dynamic-jobs.test.mjs +0 -344
- package/lib/scheduling/jitter.test.mjs +0 -140
- package/lib/secrets/broker.test.mjs +0 -280
- package/lib/secrets/providers.test.mjs +0 -274
- package/lib/security/audit-engine.test.mjs +0 -424
- package/lib/security/coerce-args.test.mjs +0 -281
- package/lib/security/dangerous-tools.test.mjs +0 -68
- package/lib/security/external-content.test.mjs +0 -84
- package/lib/security/redact.test.mjs +0 -441
- package/lib/security/secret-equal.test.mjs +0 -55
- package/lib/session/config.test.mjs +0 -92
- package/lib/session/feed-core.test.mjs +0 -198
- package/lib/session/first-run.test.mjs +0 -121
- package/lib/session/frontdoor.test.mjs +0 -205
- package/lib/session/handoffs.test.mjs +0 -183
- package/lib/session/identity.test.mjs +0 -180
- package/lib/session/inbox-claims.test.mjs +0 -286
- package/lib/session/launch-args.test.mjs +0 -157
- package/lib/session/liveness.test.mjs +0 -100
- package/lib/session/status-summary.test.mjs +0 -118
- package/lib/session-permissions.test.mjs +0 -120
- package/lib/setup/claude-probe.test.mjs +0 -187
- package/lib/setup/completeness.test.mjs +0 -110
- package/lib/setup/context-pack.test.mjs +0 -89
- package/lib/setup/enrich.test.mjs +0 -115
- package/lib/setup/enroll-from-cohort.test.mjs +0 -300
- package/lib/setup/integration.test.mjs +0 -162
- package/lib/setup/io.test.mjs +0 -77
- package/lib/setup/runner.test.mjs +0 -132
- package/lib/setup/sections/identity.test.mjs +0 -234
- package/lib/setup/sections/inventory.test.mjs +0 -198
- package/lib/setup/sections/learning.test.mjs +0 -81
- package/lib/setup/sections/mandate.test.mjs +0 -388
- package/lib/setup/sections/messaging.test.mjs +0 -127
- package/lib/setup/sections/model.test.mjs +0 -240
- package/lib/setup/sections/org.test.mjs +0 -346
- package/lib/setup/sections/orgmail.test.mjs +0 -118
- package/lib/setup/sections/recovery.test.mjs +0 -98
- package/lib/setup/sections/subagents.test.mjs +0 -429
- package/lib/setup/sections/verify.test.mjs +0 -175
- package/lib/setup/sot.test.mjs +0 -81
- package/lib/setup/state.test.mjs +0 -115
- package/lib/singleton.test.mjs +0 -151
- package/lib/subagents/cli.test.mjs +0 -389
- package/lib/subagents/client.test.mjs +0 -309
- package/lib/subagents/gap.test.mjs +0 -234
- package/lib/subagents/lock.test.mjs +0 -248
- package/lib/subagents/manifest.test.mjs +0 -175
- package/lib/subagents/refs.test.mjs +0 -204
- package/lib/subagents/resolve.test.mjs +0 -422
- package/lib/subagents/schema.test.mjs +0 -328
- package/lib/telemetry/alerts.test.mjs +0 -109
- package/lib/telemetry/collect.test.mjs +0 -1274
- package/lib/tool-definitions-integration.test.mjs +0 -83
- package/lib/tool-definitions.test.mjs +0 -437
- package/lib/upgrade/global-refresh.test.mjs +0 -65
- package/lib/upgrade/launchd-reconcile.test.mjs +0 -272
- package/lib/upgrade/post-steps.test.mjs +0 -200
- package/lib/upgrade/verify.test.mjs +0 -164
- package/lib/util/fetch-timeout.test.mjs +0 -202
- package/lib/util/reconnect.test.mjs +0 -369
- package/lib/util/unhandled.test.mjs +0 -216
- package/lib/voice/outbound.test.mjs +0 -69
- package/lib/voice/session-rotation.test.mjs +0 -114
- package/lib/voice/stt.test.mjs +0 -226
- package/lib/voice/voice.test.mjs +0 -990
- package/scripts/cadence/enqueue-cadence-tick.test.mjs +0 -187
- package/scripts/ci/check-docs-accuracy.test.mjs +0 -409
- package/scripts/ci/check-durable-write-seam.test.mjs +0 -90
- package/scripts/ci/check-no-build-artifacts.test.mjs +0 -71
- package/scripts/ci/check-no-residual-identity.test.mjs +0 -202
- package/scripts/ci/check-skill-packs.test.mjs +0 -495
- package/scripts/ci/check-subagent-frontmatter.test.mjs +0 -124
- package/scripts/ci/check.test.mjs +0 -194
- package/scripts/ci/conformance-org-api.test.mjs +0 -425
- package/scripts/cloud-relay/voice/relay-identity.test.mjs +0 -96
- package/scripts/collective/hook-runner.test.mjs +0 -173
- package/scripts/cost/fleet-digest.test.mjs +0 -207
- package/scripts/cost/track-claude-usage-pricing.test.mjs +0 -183
- package/scripts/cost/track-claude-usage.test.mjs +0 -148
- package/scripts/daemon/agent-daemon-board-mine.test.mjs +0 -96
- package/scripts/daemon/agent-daemon-design.test.mjs +0 -238
- package/scripts/daemon/agent-daemon-frontdoor.test.mjs +0 -60
- package/scripts/daemon/agent-daemon.test.mjs +0 -995
- package/scripts/daemon/assurance-e2e.test.mjs +0 -613
- package/scripts/daemon/assurance.test.mjs +0 -1791
- package/scripts/daemon/board-mirror.test.mjs +0 -165
- package/scripts/daemon/cadence-consumer-frontdoor.test.mjs +0 -393
- package/scripts/daemon/cadence-consumer-governance.test.mjs +0 -276
- package/scripts/daemon/cadence-consumer.test.mjs +0 -776
- package/scripts/daemon/cadence-handlers.test.mjs +0 -837
- package/scripts/daemon/classifier-identity.test.mjs +0 -137
- package/scripts/daemon/classifier.test.mjs +0 -266
- package/scripts/daemon/classify-kind.test.mjs +0 -40
- package/scripts/daemon/context-compiler.test.mjs +0 -406
- package/scripts/daemon/deliver.test.mjs +0 -564
- package/scripts/daemon/dispatcher-cooldown.test.mjs +0 -122
- package/scripts/daemon/dispatcher-governance.test.mjs +0 -1013
- package/scripts/daemon/dispatcher-resume.test.mjs +0 -166
- package/scripts/daemon/dispatcher-session-continuity.test.mjs +0 -365
- package/scripts/daemon/execution-ladder.test.mjs +0 -470
- package/scripts/daemon/goal-steward-cadence.test.mjs +0 -312
- package/scripts/daemon/inbox-deferral-session.test.mjs +0 -49
- package/scripts/daemon/inbox-deferral.test.mjs +0 -336
- package/scripts/daemon/inbox-wake.test.mjs +0 -199
- package/scripts/daemon/integration.test.mjs +0 -149
- package/scripts/daemon/lib/self-echo.test.mjs +0 -153
- package/scripts/daemon/lib/session-router.test.mjs +0 -554
- package/scripts/daemon/prompt-builder-preamble.test.mjs +0 -210
- package/scripts/daemon/prompt-builder.test.mjs +0 -556
- package/scripts/daemon/responder-cost.test.mjs +0 -68
- package/scripts/daemon/responder-history.test.mjs +0 -221
- package/scripts/daemon/sdk-version.test.mjs +0 -31
- package/scripts/daemon/session-lock.test.mjs +0 -252
- package/scripts/daemon/session-outcomes.test.mjs +0 -533
- package/scripts/daemon/typing-registry.test.mjs +0 -102
- package/scripts/hooks/pre-send-audit.test.mjs +0 -354
- package/scripts/huddle/huddle-prompt.test.mjs +0 -176
- package/scripts/local-triggers/autoupdate.test.mjs +0 -518
- package/scripts/local-triggers/generate-plists.test.mjs +0 -456
- package/scripts/media-generation/brand-clause.test.mjs +0 -135
- package/scripts/org/send-orgmail.first-contact.test.mjs +0 -102
- package/scripts/poller/inbox-privilege-injection.test.mjs +0 -167
- package/scripts/poller/inbox-scan-poller.test.mjs +0 -295
- package/scripts/poller/lib/cloud-relay-dedup.test.mjs +0 -133
- package/scripts/poller/slack-socket-mode.test.mjs +0 -805
- package/scripts/poller-launchd/install.test.mjs +0 -243
- package/scripts/restore-from-backup.test.mjs +0 -181
- package/scripts/session/feed.test.mjs +0 -196
- package/scripts/session/supervisor-sh.test.mjs +0 -218
- package/scripts/session/supervisor.test.mjs +0 -482
- package/scripts/setup/configure-macos.test.mjs +0 -306
- package/scripts/setup/gen-subagent-manifest.test.mjs +0 -124
- package/scripts/setup/generate-agent-package-json.test.mjs +0 -143
- package/scripts/setup/generate-capability.test.mjs +0 -134
- package/scripts/setup/init-agent.test.mjs +0 -370
- package/scripts/setup/init-skill-marketplace.test.mjs +0 -193
- package/scripts/vendor/sync-skill-packs.test.mjs +0 -103
- package/scripts/watchdog/memory-watchdog.test.mjs +0 -64
|
@@ -31,6 +31,10 @@ a slower reply, never a dropped one.
|
|
|
31
31
|
counts open handoffs and board items from `state/org/board-mine.json`, the
|
|
32
32
|
daemon's five-minute cache — when that file is missing the count is 0 and
|
|
33
33
|
you run `maestro board mine` yourself.
|
|
34
|
+
`maestro session status` (and the `session_status` tool) also carries
|
|
35
|
+
`currentWork` — what is running, queued and blocked across your sessions on
|
|
36
|
+
this machine; a "what are you doing right now?" is answered from that, not
|
|
37
|
+
from memory.
|
|
34
38
|
|
|
35
39
|
3. Drain what is already waiting: `maestro inbox list --new`, then
|
|
36
40
|
`maestro session handoffs` — anything there arrived while you were down.
|
|
@@ -43,12 +47,14 @@ Each line is a JSON object with a `type`. Handle it in the turn it arrives.
|
|
|
43
47
|
|
|
44
48
|
- `inbound` — `{id, surface, topic, from, channelId, threadId, preview, path}`.
|
|
45
49
|
`maestro inbox show <id>` for the full item, then follow the
|
|
46
|
-
`inbound-triage` skill: reply now, or
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
50
|
+
`inbound-triage` skill: reply now, work it here, or spawn a peer. Saying
|
|
51
|
+
something BEFORE the answer is the exception, not the rule — see that skill's
|
|
52
|
+
one-interim rule. Claim it first (`maestro inbox claim <id>`) so the daemon's
|
|
53
|
+
sweep does not re-deliver it, reply with `maestro inbox reply <id> --text "…"`,
|
|
54
|
+
and close with `maestro inbox done <id>`. Those four commands ALSO write the
|
|
55
|
+
ask's board row — open, running, closed, channel tagged — so there is no
|
|
56
|
+
separate `board track` step to remember; the server's gate decides whether a
|
|
57
|
+
given ask earns a row at all. The reply command is the reply lane: it runs the
|
|
52
58
|
outbound gate — banned phrases, disclosure, barriers and the persona check —
|
|
53
59
|
in-process before anything is sent. In the agent directory the
|
|
54
60
|
`messaging_send` tool is blocked by the repo's own hook; do not try to route
|
|
@@ -62,7 +68,12 @@ Each line is a JSON object with a `type`. Handle it in the turn it arrives.
|
|
|
62
68
|
the old way, so ack promptly and never twice.
|
|
63
69
|
- `directive` — `restart`: finish the current turn, then `maestro session
|
|
64
70
|
restart` (the supervisor brings you back on the same session id).
|
|
65
|
-
`upgrade-available`: same, at the next idle moment. `daemon-
|
|
71
|
+
`upgrade-available`: same, at the next idle moment. `daemon-unhealthy`:
|
|
72
|
+
NOT a restart cue — the hourly autoupdate is reporting the daemon unhealthy
|
|
73
|
+
on the version already installed (`detail.notice.reason` says why: crash
|
|
74
|
+
loop, fatal line, or the org rejecting its beat); there is nothing to
|
|
75
|
+
restart onto, so keep your context, tell your principal and run `maestro
|
|
76
|
+
doctor`. `daemon-stale`: the
|
|
66
77
|
daemon has not beaten for 5 minutes; say so to your principal if it persists
|
|
67
78
|
past a second event, and keep working — the feed still delivers what is on
|
|
68
79
|
disk.
|
|
@@ -19,6 +19,13 @@ captureOn: [Stop, PreCompact]
|
|
|
19
19
|
minTurnsToCapture: 2
|
|
20
20
|
# Hard cap on cards distilled from a single session (anti-bloat + cost guard).
|
|
21
21
|
maxCardsPerSession: 12
|
|
22
|
+
# Machine-wide ceiling on capture workers doing model work at once. Each worker
|
|
23
|
+
# runs one or two `claude --print` passes; the ceiling keeps a burst of session
|
|
24
|
+
# ends from fanning out into unbounded model processes.
|
|
25
|
+
captureMaxConcurrent: 2
|
|
26
|
+
# How long a worker waits for a free slot before it gives up and records a
|
|
27
|
+
# skipped capture (counter `collective.capture_skipped`, reason `no-slot`).
|
|
28
|
+
captureQueueWaitMs: 30000
|
|
22
29
|
# Repos/paths whose sessions must NOT contribute to memory (substring or glob,
|
|
23
30
|
# matched against the session cwd). Client work, secrets, anything ring-fenced.
|
|
24
31
|
# Information-barrier domains are always excluded regardless of this list.
|
|
@@ -42,7 +42,7 @@
|
|
|
42
42
|
* `eslint.config.mjs`/`authz-drift.test.ts` use in the Cohort repo.
|
|
43
43
|
*
|
|
44
44
|
* Set equality also makes this guard self-canarying: the register is non-empty,
|
|
45
|
-
* so a regex broken by a refactor yields zero matches and fails LOUDLY as
|
|
45
|
+
* so a regex broken by a refactor yields zero matches and fails LOUDLY as
|
|
46
46
|
* stale entries, rather than passing vacuously.
|
|
47
47
|
*
|
|
48
48
|
* Pure, dependency-light: Node builtins only. ESM.
|
|
@@ -71,6 +71,8 @@ export const SANCTIONED_DIRECT_WRITES = {
|
|
|
71
71
|
"acquireScheduleLock: reclaim of a lock already proven stale by mtime; must land in place under the same name.",
|
|
72
72
|
"lib/cadence-bus.mjs:328":
|
|
73
73
|
"acquireScheduleLock: second O_EXCL attempt after the stale holder vanished.",
|
|
74
|
+
"lib/collective/capture-slots.mjs:152":
|
|
75
|
+
"tryAcquireLock: O_EXCL create of a capture slot/session lock (the machine-wide capture ceiling). A lock published by rename is not a lock — two workers could both hold one slot.",
|
|
74
76
|
};
|
|
75
77
|
|
|
76
78
|
/** Argument spellings that are already safe and must never be flagged. */
|
|
@@ -16,6 +16,12 @@
|
|
|
16
16
|
* pack/install; cf. the broken `validate_outbound.py` cross-tenant link).
|
|
17
17
|
* 3. Requireability — the package main (exports["."], default lib/index.js)
|
|
18
18
|
* is present in the extracted tree, so a consumer's `import` resolves.
|
|
19
|
+
* 4. No tests or fixtures (CF-15) — `*.test.mjs`, `fixtures/`, `test-fixtures/`,
|
|
20
|
+
* `test/` and the replay examples are negated in files[] and must not ship;
|
|
21
|
+
* every relative import/require/`new URL(…, import.meta.url)` in the
|
|
22
|
+
* packaged JS that names a file in the source tree names a packaged file;
|
|
23
|
+
* and every exports[] module and lib/**\/index imports from the extracted
|
|
24
|
+
* tarball (with the source tree's node_modules linked in after the walk).
|
|
19
25
|
*
|
|
20
26
|
* This is a SLOW check (it shells out to `npm pack` and `tar`), so it is wired
|
|
21
27
|
* as its own opt-in npm script (`npm run test:pack`) and is NOT part of the
|
|
@@ -37,6 +43,7 @@ import {
|
|
|
37
43
|
readdirSync,
|
|
38
44
|
lstatSync,
|
|
39
45
|
existsSync,
|
|
46
|
+
symlinkSync,
|
|
40
47
|
} from "node:fs";
|
|
41
48
|
import { tmpdir } from "node:os";
|
|
42
49
|
import path from "node:path";
|
|
@@ -50,8 +57,98 @@ export const FORBIDDEN_PATTERNS = [
|
|
|
50
57
|
{ label: "python bytecode (*.pyc)", re: /\.pyc$/ },
|
|
51
58
|
{ label: "python bytecode (*.pyo)", re: /\.pyo$/ },
|
|
52
59
|
{ label: "bytecode cache dir (__pycache__)", re: /(^|\/)__pycache__(\/|$)/ },
|
|
60
|
+
// CF-15 (W5): tests and their fixtures are not runtime; package.json files[] negates them.
|
|
61
|
+
{ label: "test file (*.test.mjs / *.test.js)", re: /\.test\.(mjs|js|cjs)$/ },
|
|
62
|
+
{ label: "test fixture directory", re: /(^|\/)(fixtures|test-fixtures|__fixtures__)\// },
|
|
63
|
+
{ label: "test directory (test/)", re: /^test\// },
|
|
64
|
+
{ label: "eval example fixtures", re: /^scripts\/eval\/replay\/examples\// },
|
|
53
65
|
];
|
|
54
66
|
|
|
67
|
+
/**
|
|
68
|
+
* Relative module and file references in a JS source: static `import`/`export … from`,
|
|
69
|
+
* literal `import("…")` and `require("…")`, and `new URL("…", import.meta.url)` naming a
|
|
70
|
+
* file (with an extension). Pure.
|
|
71
|
+
* @param {string} source
|
|
72
|
+
* @returns {string[]} the relative specifiers, as written
|
|
73
|
+
*/
|
|
74
|
+
export function relativeReferences(source) {
|
|
75
|
+
const out = new Set();
|
|
76
|
+
const patterns = [
|
|
77
|
+
/\b(?:import|export)\s[^'"`;]*?\bfrom\s*["'](\.{1,2}\/[^"']+)["']/g,
|
|
78
|
+
/\bimport\s*["'](\.{1,2}\/[^"']+)["']/g,
|
|
79
|
+
/\bimport\(\s*["'](\.{1,2}\/[^"']+)["']\s*\)/g,
|
|
80
|
+
/\brequire\(\s*["'](\.{1,2}\/[^"']+)["']\s*\)/g,
|
|
81
|
+
/\bnew URL\(\s*["'](\.{1,2}\/[^"']*\.[A-Za-z0-9]+)["']\s*,\s*import\.meta\.url\s*\)/g,
|
|
82
|
+
];
|
|
83
|
+
for (const re of patterns) for (const m of source.matchAll(re)) out.add(m[1]);
|
|
84
|
+
return [...out];
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
/**
|
|
88
|
+
* Every relative reference in the packaged JS that resolves to a file present in
|
|
89
|
+
* the source tree but absent from the tarball — a runtime path the packaging
|
|
90
|
+
* cut off. References that do not resolve in the source tree either (optional,
|
|
91
|
+
* generated or seat-local files) are not a packaging fault and are not reported.
|
|
92
|
+
* Comment lines are skipped. Pure over its inputs.
|
|
93
|
+
* @param {{files:string[], read:(rel:string)=>string, existsInSource:(rel:string)=>boolean}} p
|
|
94
|
+
* @returns {Array<{file:string, ref:string, target:string}>}
|
|
95
|
+
*/
|
|
96
|
+
export function brokenPackagedReferences({ files, read, existsInSource }) {
|
|
97
|
+
const shipped = new Set(files);
|
|
98
|
+
const broken = [];
|
|
99
|
+
for (const file of files) {
|
|
100
|
+
if (!/\.(mjs|js|cjs)$/.test(file)) continue;
|
|
101
|
+
const source = read(file)
|
|
102
|
+
.split("\n")
|
|
103
|
+
.filter((l) => !/^\s*(\/\/|\*|\/\*)/.test(l))
|
|
104
|
+
.join("\n");
|
|
105
|
+
for (const ref of relativeReferences(source)) {
|
|
106
|
+
const target = path.posix.normalize(path.posix.join(path.posix.dirname(file), ref));
|
|
107
|
+
if (shipped.has(target) || !existsInSource(target)) continue;
|
|
108
|
+
broken.push({ file, ref, target });
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
return broken;
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
/**
|
|
115
|
+
* The modules a consumer (or the CLI) imports by name: every exports[] target
|
|
116
|
+
* that is JavaScript, and every lib/**\/index.(mjs|js). Pure.
|
|
117
|
+
* @param {object} pkg @param {string[]} files
|
|
118
|
+
*/
|
|
119
|
+
export function smokeImportTargets(pkg, files) {
|
|
120
|
+
const fromExports = Object.values((pkg && pkg.exports) || {})
|
|
121
|
+
.map((v) => (typeof v === "string" ? v : v && (v.import || v.default)))
|
|
122
|
+
.filter((v) => typeof v === "string" && /\.(mjs|js)$/.test(v))
|
|
123
|
+
.map((v) => v.replace(/^\.\//, ""));
|
|
124
|
+
const indexes = files.filter((f) => /^lib\/(.+\/)?index\.(mjs|js)$/.test(f));
|
|
125
|
+
return [...new Set([...fromExports, ...indexes])].sort();
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
/**
|
|
129
|
+
* Import each module in a child node process run in `root`; returns the ones that
|
|
130
|
+
* failed, with the first line of the error. Bounded by `timeoutMs`.
|
|
131
|
+
* @param {string} root @param {string[]} modules @param {number} [timeoutMs]
|
|
132
|
+
* @returns {Array<{module:string, error:string}>}
|
|
133
|
+
*/
|
|
134
|
+
export function smokeImport(root, modules, timeoutMs = 180_000) {
|
|
135
|
+
const script = [
|
|
136
|
+
"const mods = JSON.parse(process.argv[1]);",
|
|
137
|
+
"const failed = [];",
|
|
138
|
+
"for (const m of mods) { try { await import(new URL(m, 'file://' + process.cwd() + '/').href); } catch (e) { failed.push({ module: m, error: String((e && e.message) || e).split('\\n')[0] }); } }",
|
|
139
|
+
"process.stdout.write(JSON.stringify(failed));",
|
|
140
|
+
"process.exit(0);",
|
|
141
|
+
].join("\n");
|
|
142
|
+
const env = { PATH: process.env.PATH || "/usr/bin:/bin", HOME: mkdtempSync(path.join(tmpdir(), "maestro-pack-home-")), NODE_ENV: "production" };
|
|
143
|
+
try {
|
|
144
|
+
const out = execFileSync(process.execPath, ["--input-type=module", "-e", script, JSON.stringify(modules)], { cwd: root, env, encoding: "utf8", timeout: timeoutMs, maxBuffer: 16 * 1024 * 1024, stdio: ["ignore", "pipe", "ignore"] });
|
|
145
|
+
const last = out.trim().split("\n").pop() || "[]";
|
|
146
|
+
return JSON.parse(last);
|
|
147
|
+
} finally {
|
|
148
|
+
try { rmSync(env.HOME, { recursive: true, force: true }); } catch { /* */ }
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
|
|
55
152
|
/**
|
|
56
153
|
* The "main" file a consumer's bare `import "@cohortapp/agent-sdk"` resolves to.
|
|
57
154
|
* Falls back to lib/index.js (the documented default) when exports["."] is odd.
|
|
@@ -146,9 +243,11 @@ export function checkTarball(opts = {}) {
|
|
|
146
243
|
|
|
147
244
|
// 4) Completeness — every files[] entry must be represented. A directory
|
|
148
245
|
// entry (e.g. "lib/") is satisfied by any packaged path beneath it; a
|
|
149
|
-
// file entry must appear verbatim.
|
|
246
|
+
// file entry must appear verbatim. A negation ("!**/*.test.mjs") removes
|
|
247
|
+
// paths rather than declaring them (CF-15), so it has nothing to find.
|
|
150
248
|
const missing = [];
|
|
151
249
|
for (const decl of filesAllowlist) {
|
|
250
|
+
if (typeof decl !== "string" || decl.startsWith("!")) continue;
|
|
152
251
|
const norm = decl.replace(/^\.\//, "").replace(/\/+$/, "");
|
|
153
252
|
const asDirPrefix = norm + "/";
|
|
154
253
|
const present = filePaths.some(
|
|
@@ -162,12 +261,37 @@ export function checkTarball(opts = {}) {
|
|
|
162
261
|
missing.push(`${mainEntry} (package main / exports["."])`);
|
|
163
262
|
}
|
|
164
263
|
|
|
264
|
+
// 6) CF-15: no packaged module points at a file the packaging left out.
|
|
265
|
+
const broken = brokenPackagedReferences({
|
|
266
|
+
files: filePaths,
|
|
267
|
+
read: (rel) => readFileSync(path.join(pkgRoot, rel), "utf8"),
|
|
268
|
+
existsInSource: (rel) => existsSync(path.join(cwd, rel)),
|
|
269
|
+
});
|
|
270
|
+
for (const b of broken) missing.push(`${b.target} (referenced as "${b.ref}" by ${b.file}, excluded from the tarball)`);
|
|
271
|
+
|
|
272
|
+
// 7) CF-15: every exported entry and lib/**/index imports from the extracted
|
|
273
|
+
// tarball (dependencies from the source tree's node_modules). A module that
|
|
274
|
+
// also fails from the source tree is not a packaging fault.
|
|
275
|
+
let smoked = 0;
|
|
276
|
+
if (opts.smoke !== false) {
|
|
277
|
+
const targets = smokeImportTargets(pkg, filePaths);
|
|
278
|
+
const sourceModules = path.join(cwd, "node_modules");
|
|
279
|
+
if (existsSync(sourceModules)) symlinkSync(sourceModules, path.join(pkgRoot, "node_modules"), "dir");
|
|
280
|
+
const failedPacked = smokeImport(pkgRoot, targets);
|
|
281
|
+
const failedSource = failedPacked.length > 0 ? new Set(smokeImport(cwd, failedPacked.map((f) => f.module)).map((f) => f.module)) : new Set();
|
|
282
|
+
for (const f of failedPacked) {
|
|
283
|
+
if (!failedSource.has(f.module)) missing.push(`${f.module} (does not import from the tarball: ${f.error})`);
|
|
284
|
+
}
|
|
285
|
+
smoked = targets.length;
|
|
286
|
+
}
|
|
287
|
+
|
|
165
288
|
return {
|
|
166
289
|
ok: offenders.length === 0 && missing.length === 0,
|
|
167
290
|
offenders,
|
|
168
291
|
missing,
|
|
169
292
|
tarballFiles: filePaths.length,
|
|
170
293
|
mainEntry,
|
|
294
|
+
smoked,
|
|
171
295
|
};
|
|
172
296
|
} finally {
|
|
173
297
|
try { rmSync(work, { recursive: true, force: true }); } catch { /* */ }
|
|
@@ -184,7 +308,7 @@ export async function run(cwd = REPO_ROOT) {
|
|
|
184
308
|
return 2;
|
|
185
309
|
}
|
|
186
310
|
if (res.ok) {
|
|
187
|
-
console.log(`check-tarball-fidelity: OK (${res.tarballFiles} files; main "${res.mainEntry}" present; no node_modules/.pyc/symlinks)`);
|
|
311
|
+
console.log(`check-tarball-fidelity: OK (${res.tarballFiles} files; main "${res.mainEntry}" present; no node_modules/.pyc/symlinks/tests/fixtures; every relative reference resolves; ${res.smoked} entry modules import from the tarball)`);
|
|
188
312
|
return 0;
|
|
189
313
|
}
|
|
190
314
|
if (res.missing.length) {
|
package/scripts/ci/run-tests.mjs
CHANGED
|
@@ -10,24 +10,31 @@
|
|
|
10
10
|
*
|
|
11
11
|
* Node builtins only (maestro is "type":"module", near-zero-dep by design).
|
|
12
12
|
*
|
|
13
|
-
* Usage: `node scripts/ci/run-tests.mjs`
|
|
13
|
+
* Usage: `node scripts/ci/run-tests.mjs [--list]`
|
|
14
14
|
* exit 0 → all tests passed; non-zero → at least one failed (or none found).
|
|
15
|
+
* `--list` prints the discovered files and runs nothing. It exists so that
|
|
16
|
+
* "what does the suite cover?" has ONE answer. `package.json` used to answer
|
|
17
|
+
* it a second time with a hand-enumerated `test:list`, which had drifted to
|
|
18
|
+
* 46 of 82 files by the time an audit caught it (L25) and was still missing
|
|
19
|
+
* newly added suites afterwards — a second source of truth about coverage
|
|
20
|
+
* that lies is worse than none, because it reads like an inventory.
|
|
15
21
|
*
|
|
16
22
|
* @module scripts/ci/run-tests
|
|
17
23
|
*/
|
|
18
24
|
|
|
19
25
|
import { readdirSync } from "node:fs";
|
|
20
|
-
import { join, dirname } from "node:path";
|
|
26
|
+
import { join, dirname, relative, resolve } from "node:path";
|
|
21
27
|
import { fileURLToPath } from "node:url";
|
|
22
28
|
import { spawnSync } from "node:child_process";
|
|
23
29
|
|
|
24
30
|
const REPO_ROOT = join(dirname(fileURLToPath(import.meta.url)), "..", "..");
|
|
25
|
-
const ROOTS = ["lib", "scripts", "bin", "services"];
|
|
31
|
+
const ROOTS = ["lib", "scripts", "bin", "services", "test"];
|
|
26
32
|
const SKIP_DIRS = new Set(["node_modules", ".git", "state", "logs", "audit"]);
|
|
27
33
|
|
|
28
34
|
/**
|
|
29
|
-
* Recursively collect `*.test.mjs` files under `dir
|
|
30
|
-
* paths
|
|
35
|
+
* Recursively collect `*.test.mjs` files under `dir`, returning ABSOLUTE
|
|
36
|
+
* paths — `node --test` is spawned with cwd REPO_ROOT, but absolute paths
|
|
37
|
+
* survive a caller that is not. `--list` relativises them for readability.
|
|
31
38
|
* @param {string} dir
|
|
32
39
|
* @returns {string[]}
|
|
33
40
|
*/
|
|
@@ -50,22 +57,43 @@ function findTests(dir) {
|
|
|
50
57
|
return out;
|
|
51
58
|
}
|
|
52
59
|
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
60
|
+
/**
|
|
61
|
+
* Every test file the suite runs, repo-relative and sorted. The single source
|
|
62
|
+
* of truth about what `npm test` covers.
|
|
63
|
+
* @returns {string[]}
|
|
64
|
+
*/
|
|
65
|
+
export function discoverTests() {
|
|
66
|
+
return ROOTS.flatMap((r) => findTests(join(REPO_ROOT, r))).sort();
|
|
58
67
|
}
|
|
59
68
|
|
|
60
|
-
|
|
69
|
+
function main(argv) {
|
|
70
|
+
const files = discoverTests();
|
|
71
|
+
|
|
72
|
+
if (files.length === 0) {
|
|
73
|
+
console.error("run-tests: no *.test.mjs files found — refusing to report success.");
|
|
74
|
+
return 1;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
if (argv.includes("--list")) {
|
|
78
|
+
for (const f of files) console.log(relative(REPO_ROOT, f));
|
|
79
|
+
console.error(`run-tests: ${files.length} test file(s) discovered (nothing was run).`);
|
|
80
|
+
return 0;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
console.log(`run-tests: discovered ${files.length} test file(s).`);
|
|
61
84
|
|
|
62
|
-
const result = spawnSync(process.execPath, ["--test", ...files], {
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
});
|
|
85
|
+
const result = spawnSync(process.execPath, ["--test", ...files], {
|
|
86
|
+
cwd: REPO_ROOT,
|
|
87
|
+
stdio: "inherit",
|
|
88
|
+
});
|
|
89
|
+
|
|
90
|
+
if (result.error) {
|
|
91
|
+
console.error("run-tests: failed to launch node --test:", result.error.message);
|
|
92
|
+
return 1;
|
|
93
|
+
}
|
|
94
|
+
return result.status ?? 1;
|
|
95
|
+
}
|
|
66
96
|
|
|
67
|
-
if (
|
|
68
|
-
|
|
69
|
-
process.exit(1);
|
|
97
|
+
if (process.argv[1] && resolve(process.argv[1]) === fileURLToPath(import.meta.url)) {
|
|
98
|
+
process.exit(main(process.argv.slice(2)));
|
|
70
99
|
}
|
|
71
|
-
process.exit(result.status ?? 1);
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* scripts/cohort-llm/api-key-helper.mjs — Claude Code `apiKeyHelper` for a
|
|
4
|
+
* seat retargeted to cohort-llm (the internal "Path B" testbed, design C1).
|
|
5
|
+
*
|
|
6
|
+
* Claude Code runs this in /bin/sh and sends stdout as the request credential
|
|
7
|
+
* (public docs, code.claude.com/docs/en/iam: `apiKeyHelper` ranks below
|
|
8
|
+
* ANTHROPIC_AUTH_TOKEN, so a cohort retarget carries NO auth token and lets this
|
|
9
|
+
* helper supply — and, every CLAUDE_CODE_API_KEY_HELPER_TTL_MS, refresh — the
|
|
10
|
+
* seat token for the whole life of a long session).
|
|
11
|
+
*
|
|
12
|
+
* node scripts/cohort-llm/api-key-helper.mjs [--agent-root <dir>]
|
|
13
|
+
*
|
|
14
|
+
* stdout: exactly one fresh `cst_…` token and a newline. Nothing else ever goes
|
|
15
|
+
* to stdout — anything printed there would be sent as the credential.
|
|
16
|
+
* failure: exit 1 with one line on stderr naming the typed error. The token and
|
|
17
|
+
* the seat's key never appear on stderr.
|
|
18
|
+
*
|
|
19
|
+
* Key resolution: the cached token (state/cohort-llm/token.json) when it is
|
|
20
|
+
* before its refresh point; otherwise the seat's OrgApiKey from config/org.yaml,
|
|
21
|
+
* the environment, or the agent's .env (a retarget child's env is scrubbed of
|
|
22
|
+
* credentials, so the .env is the usual source here).
|
|
23
|
+
*
|
|
24
|
+
* @module scripts/cohort-llm/api-key-helper
|
|
25
|
+
*/
|
|
26
|
+
|
|
27
|
+
import { resolve } from "node:path";
|
|
28
|
+
import { realpathSync } from "node:fs";
|
|
29
|
+
import { pathToFileURL } from "node:url";
|
|
30
|
+
|
|
31
|
+
import { seatTokenManager, redactSecrets, REJECTED_TOKEN_FP_ENV } from "../../lib/org/llm-token.mjs";
|
|
32
|
+
|
|
33
|
+
/** @param {string[]} argv */
|
|
34
|
+
export function parseHelperArgs(argv) {
|
|
35
|
+
const out = { agentRoot: null };
|
|
36
|
+
for (let i = 0; i < argv.length; i++) {
|
|
37
|
+
const a = argv[i];
|
|
38
|
+
if (a === "--agent-root") out.agentRoot = argv[++i] || null;
|
|
39
|
+
else if (a.startsWith("--agent-root=")) out.agentRoot = a.slice("--agent-root=".length) || null;
|
|
40
|
+
}
|
|
41
|
+
return out;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
/**
|
|
45
|
+
* @param {object} [deps]
|
|
46
|
+
* @param {string[]} [deps.argv]
|
|
47
|
+
* @param {object} [deps.env]
|
|
48
|
+
* @param {{write:(s:string)=>unknown}} [deps.stdout]
|
|
49
|
+
* @param {{write:(s:string)=>unknown}} [deps.stderr]
|
|
50
|
+
* @param {typeof fetch} [deps.fetchImpl]
|
|
51
|
+
* @param {() => number} [deps.now]
|
|
52
|
+
* @param {object} [deps.cfg]
|
|
53
|
+
* @returns {Promise<number>} exit code
|
|
54
|
+
*/
|
|
55
|
+
export async function main(deps = {}) {
|
|
56
|
+
const env = deps.env || process.env;
|
|
57
|
+
const stdout = deps.stdout || process.stdout;
|
|
58
|
+
const stderr = deps.stderr || process.stderr;
|
|
59
|
+
const args = parseHelperArgs(deps.argv || process.argv.slice(2));
|
|
60
|
+
const agentRoot = resolve(args.agentRoot || env.AGENT_ROOT || env.AGENT_DIR || process.cwd());
|
|
61
|
+
try {
|
|
62
|
+
const manager = seatTokenManager({ agentRoot, env, cfg: deps.cfg, readDotEnv: true, fetchImpl: deps.fetchImpl, now: deps.now });
|
|
63
|
+
// The engine re-runs this helper after a 401 and names the refused token by
|
|
64
|
+
// fingerprint: the manager serves a replacement if one exists, else re-mints
|
|
65
|
+
// under its per-window cap. A plain run (TTL refresh) never forces a mint.
|
|
66
|
+
const rejectedFp = typeof env[REJECTED_TOKEN_FP_ENV] === "string" ? env[REJECTED_TOKEN_FP_ENV].trim() : "";
|
|
67
|
+
const r = await manager.getToken(rejectedFp ? { rejectedFp } : {});
|
|
68
|
+
if (r.ok && typeof r.token === "string" && r.token) {
|
|
69
|
+
stdout.write(`${r.token}\n`);
|
|
70
|
+
return 0;
|
|
71
|
+
}
|
|
72
|
+
const e = (r && r.error) || { code: "cohort_unavailable", message: "no token" };
|
|
73
|
+
stderr.write(`cohort-llm api-key-helper: ${e.code}: ${redactSecrets(e.message)}\n`);
|
|
74
|
+
return 1;
|
|
75
|
+
} catch (err) {
|
|
76
|
+
stderr.write(`cohort-llm api-key-helper: cohort_unavailable: ${redactSecrets(err && err.message ? err.message : err)}\n`);
|
|
77
|
+
return 1;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
function isEntrypoint() {
|
|
82
|
+
if (!process.argv[1]) return false;
|
|
83
|
+
try {
|
|
84
|
+
return import.meta.url === pathToFileURL(realpathSync(process.argv[1])).href;
|
|
85
|
+
} catch {
|
|
86
|
+
return false;
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
if (isEntrypoint()) {
|
|
91
|
+
process.exitCode = await main();
|
|
92
|
+
}
|