session-orchestrator 3.23.0 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.agents/skills/architecture/SKILL.md +18 -0
- package/.agents/skills/autopilot/SKILL.md +17 -0
- package/.agents/skills/bootstrap/SKILL.md +20 -0
- package/.agents/skills/brainstorm/SKILL.md +22 -0
- package/.agents/skills/claude-md-drift-check/SKILL.md +15 -0
- package/.agents/skills/convergence-monitoring/SKILL.md +22 -0
- package/.agents/skills/debug/SKILL.md +22 -0
- package/.agents/skills/discovery/SKILL.md +20 -0
- package/.agents/skills/dispatcher/SKILL.md +15 -0
- package/.agents/skills/docs-orchestrator/SKILL.md +18 -0
- package/.agents/skills/ecosystem-health/SKILL.md +20 -0
- package/.agents/skills/eli5/SKILL.md +20 -0
- package/.agents/skills/eval/SKILL.md +21 -0
- package/.agents/skills/evolve/SKILL.md +21 -0
- package/.agents/skills/frontmatter-guard/SKILL.md +15 -0
- package/.agents/skills/gitlab-ops/SKILL.md +20 -0
- package/.agents/skills/gitlab-portfolio/SKILL.md +15 -0
- package/.agents/skills/grill/SKILL.md +22 -0
- package/.agents/skills/hook-development/SKILL.md +15 -0
- package/.agents/skills/mcp-builder/SKILL.md +15 -0
- package/.agents/skills/memory-cleanup/SKILL.md +21 -0
- package/.agents/skills/mode-selector/SKILL.md +17 -0
- package/.agents/skills/npm-publish/SKILL.md +16 -0
- package/.agents/skills/peekaboo-driver/SKILL.md +18 -0
- package/.agents/skills/persona-panel/SKILL.md +17 -0
- package/.agents/skills/plan/SKILL.md +20 -0
- package/.agents/skills/playwright-driver/SKILL.md +20 -0
- package/.agents/skills/quality-gates/SKILL.md +20 -0
- package/.agents/skills/reconcile/SKILL.md +21 -0
- package/.agents/skills/remote-offload/SKILL.md +20 -0
- package/.agents/skills/repo-audit/SKILL.md +16 -0
- package/.agents/skills/session-end/SKILL.md +20 -0
- package/.agents/skills/session-plan/SKILL.md +20 -0
- package/.agents/skills/session-start/SKILL.md +20 -0
- package/.agents/skills/spinout/SKILL.md +16 -0
- package/.agents/skills/sunset-review/SKILL.md +16 -0
- package/.agents/skills/test-runner/SKILL.md +20 -0
- package/.agents/skills/tmux-layout/SKILL.md +21 -0
- package/.agents/skills/using-orchestrator/SKILL.md +17 -0
- package/.agents/skills/vault-mirror/SKILL.md +15 -0
- package/.agents/skills/vault-sync/SKILL.md +15 -0
- package/.agents/skills/wave-executor/SKILL.md +20 -0
- package/.agents/skills/write-executable-plan/SKILL.md +22 -0
- package/.claude-plugin/marketplace.json +1 -1
- package/.claude-plugin/plugin.json +1 -1
- package/.codex-plugin/plugin.json +1 -1
- package/.cursor/commands/autopilot.md +2 -2
- package/.cursor/commands/bootstrap.md +1 -1
- package/.cursor/commands/brainstorm.md +1 -1
- package/.cursor/commands/debug.md +1 -1
- package/.cursor/commands/discovery.md +1 -1
- package/.cursor/commands/dispatcher.md +2 -2
- package/.cursor/commands/eli5.md +2 -2
- package/.cursor/commands/eval.md +2 -2
- package/.cursor/commands/evolve.md +1 -1
- package/.cursor/commands/go.md +1 -1
- package/.cursor/commands/grill.md +2 -2
- package/.cursor/commands/memory-cleanup.md +2 -2
- package/.cursor/commands/persona-panel.md +1 -1
- package/.cursor/commands/plan.md +1 -1
- package/.cursor/commands/portfolio.md +1 -1
- package/.cursor/commands/reconcile.md +2 -2
- package/.cursor/commands/release.md +2 -2
- package/.cursor/commands/session.md +2 -2
- package/.cursor/commands/spinout.md +2 -2
- package/.cursor/commands/sunset-review.md +2 -2
- package/.cursor/commands/templates-ack.md +2 -2
- package/.cursor/commands/test.md +2 -2
- package/.cursor/skills/brainstorm/SKILL.md +1 -1
- package/.cursor/skills/eval/SKILL.md +1 -1
- package/.cursor/skills/quality-gates/SKILL.md +1 -1
- package/.cursor/skills/remote-offload/SKILL.md +13 -0
- package/.orchestrator/policy/blocked-commands.json +121 -0
- package/.orchestrator/policy/ecosystem.schema.json +66 -0
- package/.orchestrator/policy/quality-gates.example.json +16 -0
- package/.orchestrator/policy/quality-gates.schema.json +38 -0
- package/.orchestrator/policy/templates-policy.json +27 -0
- package/.orchestrator/policy/test-profiles.json +47 -0
- package/AGENTS.md +225 -0
- package/CHANGELOG.md +1401 -0
- package/NOTICE +11 -6
- package/README.md +127 -92
- package/agents/db-specialist.md +0 -1
- package/agents/eval-judge.md +1 -1
- package/agents/skill-applied-judge.md +1 -1
- package/assets/wave-lifecycle.svg +98 -0
- package/commands/release.md +6 -3
- package/commands/session.md +18 -3
- package/docs/README.md +4 -0
- package/{agents/AGENTS.md → docs/agent-authoring.md} +19 -26
- package/docs/baseline.md +67 -0
- package/docs/ci-setup.md +249 -48
- package/docs/codex-setup.md +66 -22
- package/docs/components.md +37 -16
- package/docs/cursor-setup.md +6 -2
- package/docs/events-schema.md +51 -10
- package/docs/instruction-delivery.md +62 -0
- package/{agents/memory-proposal-collector.md → docs/memory-proposal-flow.md} +1 -8
- package/docs/migration-v4.md +341 -0
- package/docs/pi-setup.md +6 -1
- package/docs/plugin-architecture-v3.md +1 -1
- package/docs/rule-authoring.md +85 -19
- package/docs/scope-collision-guard.md +8 -8
- package/docs/session-config-reference.md +120 -61
- package/docs/session-config-template.md +40 -33
- package/docs/telemetry/telemetry-claims.md +11 -10
- package/docs/telemetry.md +187 -4
- package/docs/vault-docs-architecture.md +50 -11
- package/hooks/_lib/atomic-json.mjs +111 -0
- package/hooks/_lib/hook-import-set.json +1487 -0
- package/hooks/_lib/subagent-paths.mjs +143 -0
- package/hooks/_lib/subagent-transcript.mjs +562 -0
- package/hooks/config-protection.mjs +2 -2
- package/hooks/cwd-change-restore.mjs +11 -31
- package/hooks/enforce-commands.mjs +69 -0
- package/hooks/enforce-scope.mjs +35 -6
- package/hooks/hooks-codex.json +1 -1
- package/hooks/hooks-cursor.json +10 -0
- package/hooks/hooks-pi.json +5 -0
- package/hooks/hooks.json +6 -1
- package/hooks/loop-guard.mjs +3 -3
- package/hooks/on-session-end.mjs +280 -14
- package/hooks/on-session-start.mjs +153 -4
- package/hooks/on-stop.mjs +371 -17
- package/hooks/operator-steer.mjs +2 -2
- package/hooks/post-bash-write-verify.mjs +189 -4
- package/hooks/post-edit-import-probe.mjs +344 -0
- package/hooks/post-subagent-discovery-validator.mjs +278 -392
- package/hooks/post-tool-batch-wave-signal.mjs +272 -44
- package/hooks/post-tool-failure-corrective-context.mjs +11 -34
- package/hooks/post-tooluse-frontend-slop.mjs +3 -3
- package/hooks/pre-bash-destructive-guard.mjs +39 -13
- package/hooks/pre-bash-memory-propose-audit.mjs +13 -7
- package/hooks/skill-invocation-telemetry.mjs +17 -5
- package/hooks/subagent-telemetry.mjs +24 -30
- package/monitors/monitors.json +3 -3
- package/package.json +9 -1
- package/pi/prompts/session.md +2 -2
- package/plugin.json +27 -0
- package/scripts/autopilot.mjs +26 -12
- package/scripts/backfill-abandoned-sessions.mjs +130 -15
- package/scripts/backfill-learnings-from-vault.mjs +9 -3
- package/scripts/dialectic-deriver.mjs +73 -8
- package/scripts/emit-event.mjs +10 -2
- package/scripts/export-hw-learnings.mjs +113 -1
- package/scripts/generate-agents-skills.mjs +378 -0
- package/scripts/generate-cursor-adapter.mjs +45 -8
- package/scripts/generate-hook-import-set.mjs +249 -0
- package/scripts/lib/agent-status.mjs +13 -2
- package/scripts/lib/auq/parse.mjs +5 -29
- package/scripts/lib/auto-dialectic.mjs +68 -0
- package/scripts/lib/auto-dream.mjs +38 -36
- package/scripts/lib/autonomy/suitability.mjs +6 -0
- package/scripts/lib/autopilot/loop.mjs +2 -2
- package/scripts/lib/autopilot/worktree-pipeline.mjs +82 -6
- package/scripts/lib/build-live-signals.mjs +25 -22
- package/scripts/lib/ci-status-banner.mjs +220 -75
- package/scripts/lib/codex/plugin-contract.mjs +82 -6
- package/scripts/lib/cold-start-detector.mjs +23 -14
- package/scripts/lib/config/auto-dream.mjs +2 -1
- package/scripts/lib/config/block-header.mjs +63 -0
- package/scripts/lib/config/block-preprocess.mjs +177 -0
- package/scripts/lib/config/broken-window.mjs +2 -1
- package/scripts/lib/config/cold-start.mjs +2 -1
- package/scripts/lib/config/config-protection.mjs +22 -2
- package/scripts/lib/config/context-coverage.mjs +2 -1
- package/scripts/lib/config/cross-repo.mjs +2 -1
- package/scripts/lib/config/custom-phases.mjs +2 -1
- package/scripts/lib/config/dialectic.mjs +2 -1
- package/scripts/lib/config/discovery-validator.mjs +9 -3
- package/scripts/lib/config/dispatcher-autonomy-capture.mjs +24 -1
- package/scripts/lib/config/dispatcher-autonomy.mjs +2 -1
- package/scripts/lib/config/docs-orchestrator.mjs +2 -1
- package/scripts/lib/config/docs-staleness.mjs +2 -1
- package/scripts/lib/config/drift-check.mjs +2 -1
- package/scripts/lib/config/eval.mjs +2 -1
- package/scripts/lib/config/events-rotation.mjs +2 -1
- package/scripts/lib/config/evolve.mjs +8 -2
- package/scripts/lib/config/frontend-slop-hook.mjs +7 -3
- package/scripts/lib/config/gitlab-portfolio.mjs +2 -1
- package/scripts/lib/config/handover-gate.mjs +2 -1
- package/scripts/lib/config/health-endpoints.mjs +388 -0
- package/scripts/lib/config/issue-budget.mjs +2 -1
- package/scripts/lib/config/loop-guard.mjs +2 -1
- package/scripts/lib/config/memory.mjs +2 -1
- package/scripts/lib/config/moc-staleness.mjs +2 -1
- package/scripts/lib/config/persona-gate-wave.mjs +2 -1
- package/scripts/lib/config/private-config-dir.mjs +67 -0
- package/scripts/lib/config/reconcile.mjs +2 -1
- package/scripts/lib/config/remote-hosts.mjs +234 -0
- package/scripts/lib/config/section-extractor.mjs +7 -1
- package/scripts/lib/config/skill-evolution.mjs +2 -1
- package/scripts/lib/config/slopcheck.mjs +2 -1
- package/scripts/lib/config/state-md-lock.mjs +2 -1
- package/scripts/lib/config/templates-first.mjs +2 -1
- package/scripts/lib/config/test.mjs +2 -1
- package/scripts/lib/config/vault-integration.mjs +7 -1
- package/scripts/lib/config/vault-mirror-quality.mjs +2 -1
- package/scripts/lib/config/vault-staleness.mjs +2 -1
- package/scripts/lib/config/vault-sync.mjs +2 -1
- package/scripts/lib/config/verification-auto-fix.mjs +2 -1
- package/scripts/lib/config/wave-reviewers.mjs +2 -1
- package/scripts/lib/config/worktree-orphans.mjs +2 -1
- package/scripts/lib/config.mjs +31 -3
- package/scripts/lib/convergence-monitor.mjs +82 -16
- package/scripts/lib/dispatcher/enumerate.mjs +2 -17
- package/scripts/lib/dispatcher/rank.mjs +124 -48
- package/scripts/lib/ecosystem-health.mjs +16 -2
- package/scripts/lib/eval/engine.mjs +9 -1
- package/scripts/lib/eval/session-resolve.mjs +23 -4
- package/scripts/lib/events-schema.mjs +48 -0
- package/scripts/lib/events.mjs +256 -7
- package/scripts/lib/evolve/autonomy-verdict.mjs +9 -4
- package/scripts/lib/evolve/autopilot-effectiveness.mjs +18 -1
- package/scripts/lib/frontmatter-guard.mjs +131 -13
- package/scripts/lib/gates/gate-full.mjs +26 -0
- package/scripts/lib/gates/gate-helpers.mjs +76 -0
- package/scripts/lib/gitlab-portfolio/cli.mjs +3 -15
- package/scripts/lib/hardware-pattern-detector.mjs +18 -1
- package/scripts/lib/harness-audit/categories/category1.mjs +17 -6
- package/scripts/lib/harness-audit/categories/category4.mjs +31 -11
- package/scripts/lib/host-identity.mjs +50 -11
- package/scripts/lib/instruction-budget-guard.mjs +171 -5
- package/scripts/lib/learnings/evolve-telemetry.mjs +178 -0
- package/scripts/lib/learnings/io.mjs +60 -6
- package/scripts/lib/memory-banner.mjs +20 -8
- package/scripts/lib/memory-proposals/store.mjs +30 -22
- package/scripts/lib/owner-config-banner.mjs +43 -6
- package/scripts/lib/owner-config-loader.mjs +21 -10
- package/scripts/lib/owner-interview.mjs +3 -3
- package/scripts/lib/owner-yaml.mjs +207 -14
- package/scripts/lib/peer-discovery.mjs +20 -2
- package/scripts/lib/platform.mjs +108 -15
- package/scripts/lib/plugin-update-banner.mjs +406 -0
- package/scripts/lib/project-hygiene.mjs +38 -2
- package/scripts/lib/qg-command-drift-banner.mjs +50 -12
- package/scripts/lib/quality-gate.mjs +133 -44
- package/scripts/lib/reconcile/emitter.mjs +68 -6
- package/scripts/lib/reconcile/engine.mjs +249 -9
- package/scripts/lib/reconcile/idempotency.mjs +37 -4
- package/scripts/lib/reconcile/writer.mjs +40 -18
- package/scripts/lib/scope-gate.mjs +36 -0
- package/scripts/lib/session-close-backfill.mjs +125 -18
- package/scripts/lib/session-discovery.mjs +57 -3
- package/scripts/lib/session-end/phase-skip.mjs +2 -2
- package/scripts/lib/session-id.mjs +12 -23
- package/scripts/lib/session-identity/own-session.mjs +187 -11
- package/scripts/lib/session-lock-shape.mjs +43 -0
- package/scripts/lib/session-lock.mjs +5 -10
- package/scripts/lib/session-registry.mjs +25 -9
- package/scripts/lib/session-schema/constants.mjs +36 -2
- package/scripts/lib/session-schema/validator.mjs +38 -4
- package/scripts/lib/session-start-probes.mjs +18 -1
- package/scripts/lib/session-transition.mjs +1 -1
- package/scripts/lib/sessions-canonical.mjs +446 -0
- package/scripts/lib/sessions-staleness-banner.mjs +18 -11
- package/scripts/lib/skill-health/join.mjs +17 -4
- package/scripts/lib/state-md.mjs +78 -0
- package/scripts/lib/sunset/walker.mjs +6 -0
- package/scripts/lib/telemetry/schema.mjs +255 -17
- package/scripts/lib/telemetry/sync.mjs +417 -24
- package/scripts/lib/tmux-layout/telemetry.mjs +14 -2
- package/scripts/lib/validate/check-agents-skills.mjs +327 -0
- package/scripts/lib/validate/check-agents.mjs +3 -3
- package/scripts/lib/validate/check-cursor-adapter.mjs +234 -72
- package/scripts/lib/validate/check-doc-cli-commands.mjs +9 -33
- package/scripts/lib/validate/check-hooks-emit-event-guard.mjs +370 -0
- package/scripts/lib/validate/check-hooks-symmetry.mjs +45 -16
- package/scripts/lib/validate/check-owner-leakage.mjs +281 -20
- package/scripts/lib/validate/check-skill-links.mjs +163 -0
- package/scripts/lib/validate/check-skill-script-paths.mjs +455 -0
- package/scripts/lib/validate/check-untracked-test-deps.mjs +10 -0
- package/scripts/lib/validate/check-unwired-features.mjs +0 -9
- package/scripts/lib/validate/check-validator-registration.mjs +254 -0
- package/scripts/lib/validate/check-vcs-repo-flag.mjs +6 -28
- package/scripts/lib/validate/enumerate-repo-files.mjs +317 -0
- package/scripts/lib/validate/markdown-fences.mjs +196 -0
- package/scripts/lib/vault-backfill/template.mjs +63 -6
- package/scripts/lib/vault-mirror/process.mjs +165 -42
- package/scripts/lib/vault-mirror/telemetry.mjs +2 -2
- package/scripts/lib/vault-status/board-lock.mjs +185 -0
- package/scripts/lib/vault-status/board-writer.mjs +174 -135
- package/scripts/lib/vault-status/narrative-mirror.mjs +129 -37
- package/scripts/lib/wave-executor/dispatch-common.mjs +164 -0
- package/scripts/lib/wave-executor/foreign-dispatch.mjs +7 -142
- package/scripts/lib/wave-executor/remote-dispatch.mjs +502 -0
- package/scripts/lib/wave-resource-gate.mjs +133 -7
- package/scripts/lib/wave-sizing.mjs +4 -1
- package/scripts/lib/wave-transcript-tail.mjs +142 -8
- package/scripts/materialize-wave-scope.mjs +32 -9
- package/scripts/memory-propose.mjs +146 -8
- package/scripts/migrate-cold-start-seed.mjs +4 -1
- package/scripts/parse-config.mjs +60 -3
- package/scripts/promote-vault-strict.mjs +4 -15
- package/scripts/release.mjs +337 -29
- package/scripts/repair-invalid-sessions.mjs +3 -3
- package/scripts/run-quality-gate.mjs +128 -11
- package/scripts/site-numbers.mjs +36 -4
- package/scripts/sweep-expired-learnings.mjs +90 -0
- package/scripts/sync-vault-schema.mjs +3 -1
- package/scripts/telemetry.mjs +2 -2
- package/scripts/validate-plugin.mjs +187 -0
- package/scripts/validate-wave-scope.mjs +28 -8
- package/scripts/vault-consolidate.mjs +3 -11
- package/scripts/vault-integration-watcher.mjs +2 -4
- package/scripts/vault-mirror.mjs +111 -26
- package/scripts/wave-scope-binding.mjs +215 -0
- package/skills/_shared/instruction-file-resolution.md +10 -0
- package/skills/_shared/parallel-aware-auq.md +31 -2
- package/skills/_shared/parallel-aware-preamble.md +18 -4
- package/skills/_shared/platform-tools.md +1 -1
- package/skills/_shared/state-ownership.md +1 -1
- package/skills/architecture/SKILL.md +7 -5
- package/skills/{domain-model/SKILL.md → architecture/references/domain-model.md} +9 -9
- package/skills/autopilot/SKILL.md +4 -18
- package/skills/claude-md-drift-check/SKILL.md +5 -1
- package/skills/claude-md-drift-check/checker.mjs +62 -2
- package/skills/convergence-monitoring/SIGNALS.md +55 -0
- package/skills/discovery/probes/vault-staleness.mjs +37 -13
- package/skills/discovery/probes-arch.md +20 -18
- package/skills/dispatcher/SKILL.md +3 -2
- package/skills/ecosystem-health/SKILL.md +4 -1
- package/skills/ecosystem-health/wizard.md +5 -0
- package/skills/evolve/SKILL.md +87 -11
- package/skills/frontmatter-guard/SKILL.md +11 -5
- package/skills/npm-publish/SKILL.md +1 -1
- package/skills/reconcile/SKILL.md +38 -2
- package/skills/remote-offload/SKILL.md +89 -0
- package/skills/session-end/SKILL.md +18 -905
- package/skills/session-end/phase-3-6-tail.md +19 -9
- package/skills/session-end/plan-verification.md +221 -155
- package/skills/session-end/references/phase-2-quality-gate.md +93 -0
- package/skills/session-end/references/phase-3-documentation-updates.md +229 -0
- package/skills/session-end/references/phase-4a-worktree-cleanup.md +120 -0
- package/skills/session-end/references/phase-4b-worktree-orphan-sweep.md +58 -0
- package/skills/session-end/references/phase-5-issue-cleanup.md +104 -0
- package/skills/session-end/references/session-summary-template.md +62 -0
- package/skills/session-plan/SKILL.md +49 -0
- package/skills/session-start/SKILL.md +41 -900
- package/skills/session-start/phase-8-5-express-path.md +1 -1
- package/skills/session-start/references/phase-1-1-dispatcher-autonomy-capture.md +55 -0
- package/skills/session-start/references/phase-1-2-session-lock.md +140 -0
- package/skills/session-start/references/phase-1-5-session-continuity.md +254 -0
- package/skills/session-start/references/phase-1-7-vault-status-board.md +53 -0
- package/skills/session-start/references/phase-2-7-portfolio-snapshot.md +75 -0
- package/skills/session-start/references/phase-4-ssot-environment-check.md +155 -0
- package/skills/session-start/references/phase-6-5-forced-reads.md +75 -0
- package/skills/session-start/references/phase-6-6-project-intelligence.md +81 -0
- package/skills/session-start/references/phase-6-7-memory-banner-telemetry-consent.md +103 -0
- package/skills/vault-sync/validator.mjs +21 -27
- package/skills/wave-executor/SKILL.md +16 -2
- package/skills/wave-executor/references/wave-loop-dispatch.md +612 -0
- package/skills/wave-executor/references/wave-loop-review.md +570 -0
- package/skills/wave-executor/references/wave-loop-scope-manifest.md +162 -0
- package/skills/wave-executor/wave-loop.md +14 -1271
- package/templates/_shared/journey-manifest.md +10 -6
- package/.cursor/commands/autopilot-multi.md +0 -14
- package/.cursor/commands/contract-version-bump.md +0 -14
- package/.cursor/commands/journey-audit.md +0 -14
- package/.cursor/skills/contract-version-bump/SKILL.md +0 -12
- package/.cursor/skills/daily/SKILL.md +0 -12
- package/.cursor/skills/domain-model/SKILL.md +0 -13
- package/.cursor/skills/journey-audit/SKILL.md +0 -13
- package/.cursor/skills/skill-creator/SKILL.md +0 -13
- package/.cursor/skills/ubiquitous-language/SKILL.md +0 -13
- package/commands/autopilot-multi.md +0 -74
- package/commands/contract-version-bump.md +0 -28
- package/commands/journey-audit.md +0 -43
- package/pi/prompts/autopilot-multi.md +0 -12
- package/pi/prompts/contract-version-bump.md +0 -12
- package/pi/prompts/journey-audit.md +0 -12
- package/scripts/autopilot-multi.mjs +0 -885
- package/scripts/backfill-learnings-expires.mjs +0 -196
- package/scripts/backfill-learnings.mjs +0 -203
- package/scripts/fleet-instruction-scan.mjs +0 -141
- package/scripts/lib/autopilot/dep-graph.mjs +0 -417
- package/scripts/lib/autopilot/multi-killswitch.mjs +0 -184
- package/scripts/lib/webhook-url.mjs +0 -105
- package/scripts/lifecycle-sim-v6.mjs +0 -347
- package/scripts/migrate-learnings-jsonl.mjs +0 -189
- package/scripts/migrate-subagents-jsonl.mjs +0 -196
- package/scripts/upload-social-preview.mjs +0 -316
- package/skills/_shared/model-selection.md +0 -64
- package/skills/contract-version-bump/SKILL.md +0 -219
- package/skills/daily/SKILL.md +0 -222
- package/skills/daily/generate.sh +0 -92
- package/skills/daily/templates/daily.md.tpl +0 -36
- package/skills/journey-audit/SKILL.md +0 -269
- package/skills/skill-creator/SKILL.md +0 -168
- package/skills/ubiquitous-language/SKILL.md +0 -97
- package/skills/vault-sync/package-lock.json +0 -40
- /package/skills/{domain-model → architecture/references}/ADR-FORMAT.md +0 -0
- /package/skills/{domain-model → architecture/references}/CONTEXT-FORMAT.md +0 -0
|
@@ -47,6 +47,8 @@ import { randomBytes } from 'node:crypto';
|
|
|
47
47
|
|
|
48
48
|
import { readPeerCards } from './lib/peer-cards/reader.mjs';
|
|
49
49
|
import { filterRealSessions } from './lib/session-schema/filters.mjs';
|
|
50
|
+
import { readCanonicalSessions } from './lib/sessions-canonical.mjs';
|
|
51
|
+
import { recordDialecticRun } from './lib/learnings/evolve-telemetry.mjs';
|
|
50
52
|
|
|
51
53
|
// ---------------------------------------------------------------------------
|
|
52
54
|
// Constants
|
|
@@ -174,6 +176,30 @@ function countContentLines(body) {
|
|
|
174
176
|
return n;
|
|
175
177
|
}
|
|
176
178
|
|
|
179
|
+
/**
|
|
180
|
+
* Count the peer-card sections a proposed diff body would change (#1206 —
|
|
181
|
+
* `orchestrator.dialectic.completed`'s `user_deltas` / `agent_deltas` in
|
|
182
|
+
* dry-run mode, where there is no `mergePeerCard()` stats object to read).
|
|
183
|
+
* Pure function — no I/O.
|
|
184
|
+
*
|
|
185
|
+
* Counts `<!-- BEGIN MANAGED: <name> -->` sentinels (the same grammar
|
|
186
|
+
* `scripts/lib/peer-cards/merger.mjs` parses). A proposed body that carries
|
|
187
|
+
* none — the LLM emits a bare full-body replacement per the current prompt
|
|
188
|
+
* contract in {@link buildPrompt}, not per-section sentinels — still counts
|
|
189
|
+
* as ONE delta: a non-empty full-body replacement is a real change to the
|
|
190
|
+
* target, and an empty proposed body counts as zero (nothing to report for a
|
|
191
|
+
* target the response never touched).
|
|
192
|
+
*
|
|
193
|
+
* @param {string | undefined} diffText — `diff.user` or `diff.agent` from
|
|
194
|
+
* {@link parseResponse}; `undefined` when the target was not emitted.
|
|
195
|
+
* @returns {number}
|
|
196
|
+
*/
|
|
197
|
+
export function countManagedSections(diffText) {
|
|
198
|
+
if (typeof diffText !== 'string' || diffText.length === 0) return 0;
|
|
199
|
+
const matches = diffText.match(/<!--\s*BEGIN\s+MANAGED:\s*[\w-]+\s*-->/g);
|
|
200
|
+
return matches && matches.length > 0 ? matches.length : 1;
|
|
201
|
+
}
|
|
202
|
+
|
|
177
203
|
/**
|
|
178
204
|
* Assemble the prompt-ready payload object. Pure function — no I/O.
|
|
179
205
|
*
|
|
@@ -393,19 +419,25 @@ async function readTopLearnings(repoRoot, topN) {
|
|
|
393
419
|
}
|
|
394
420
|
|
|
395
421
|
/**
|
|
396
|
-
* Read and rank sessions:
|
|
397
|
-
*
|
|
422
|
+
* Read and rank sessions: collapse ledger duplicates (#1209 — the ledger is
|
|
423
|
+
* append-only and can carry more than one raw line per physical session, see
|
|
424
|
+
* `scripts/lib/sessions-canonical.mjs` header), filter out phantom
|
|
425
|
+
* `status: 'abandoned'` stubs (#834, session-close-backfill), sort by
|
|
426
|
+
* `completed_at` DESC, take last K.
|
|
427
|
+
*
|
|
428
|
+
* Without the dedup, a duplicate ledger line for the SAME session can occupy
|
|
429
|
+
* two of the K context slots and evict a genuinely distinct, older session.
|
|
430
|
+
* Without the phantom filter, phantoms (0 waves, seconds of runtime) can
|
|
431
|
+
* displace REAL session context out of the K-window the derivation prompt sees.
|
|
398
432
|
*
|
|
399
|
-
*
|
|
400
|
-
* REAL session context out of the K-window the derivation prompt sees.
|
|
433
|
+
* Synchronous — `readCanonicalSessions()` reads the file itself.
|
|
401
434
|
*
|
|
402
435
|
* @param {string} repoRoot
|
|
403
436
|
* @param {number} lastK
|
|
404
|
-
* @returns {
|
|
437
|
+
* @returns {Array<object>}
|
|
405
438
|
*/
|
|
406
|
-
|
|
407
|
-
const
|
|
408
|
-
const entries = filterRealSessions(await readJsonlBestEffort(path));
|
|
439
|
+
function readLastSessions(repoRoot, lastK) {
|
|
440
|
+
const entries = filterRealSessions(readCanonicalSessions({ repoRoot }));
|
|
409
441
|
entries.sort((a, b) => {
|
|
410
442
|
const ta = typeof a?.completed_at === 'string' ? a.completed_at : '';
|
|
411
443
|
const tb = typeof b?.completed_at === 'string' ? b.completed_at : '';
|
|
@@ -488,6 +520,15 @@ export async function runDialecticDeriver({
|
|
|
488
520
|
throw new TypeError('runDialecticDeriver: repoRoot (absolute path) is required');
|
|
489
521
|
}
|
|
490
522
|
|
|
523
|
+
// #1206 — telemetry start marker for the mechanical `orchestrator.dialectic.
|
|
524
|
+
// completed` emits below. Mechanical (measured), not the coordinator's own
|
|
525
|
+
// typed DURATION_MS placeholder — covers every return path THIS function
|
|
526
|
+
// can determine on its own; see the module header for the two abort classes
|
|
527
|
+
// (`unknown-model`, thrown above; `subagent-crash`) and APPLY-mode success
|
|
528
|
+
// that only the skill-prose caller can record (merge + Agent() dispatch
|
|
529
|
+
// both happen one layer up, outside this pure pipeline).
|
|
530
|
+
const t0 = Date.now();
|
|
531
|
+
|
|
491
532
|
// Gate 1: model fail-fast. Throws Error with the canonical message.
|
|
492
533
|
validateModel(model);
|
|
493
534
|
|
|
@@ -516,6 +557,7 @@ export async function runDialecticDeriver({
|
|
|
516
557
|
&& (peerCards.agent === null || peerCards.agent === undefined)
|
|
517
558
|
&& (steering === null || steering === undefined)
|
|
518
559
|
) {
|
|
560
|
+
await recordDialecticRun({ repoRoot, status: 'empty-input', durationMs: Date.now() - t0 });
|
|
519
561
|
return { status: 'empty-input', skipped_reason: 'no-input', diff: {} };
|
|
520
562
|
}
|
|
521
563
|
|
|
@@ -533,6 +575,7 @@ export async function runDialecticDeriver({
|
|
|
533
575
|
const estimatedInput = estimateInputTokens(prompt);
|
|
534
576
|
const verdict = checkBudget(estimatedInput, budget);
|
|
535
577
|
if (verdict.ok === false) {
|
|
578
|
+
await recordDialecticRun({ repoRoot, status: 'budget-exceeded', durationMs: Date.now() - t0 });
|
|
536
579
|
return {
|
|
537
580
|
status: 'budget-exceeded',
|
|
538
581
|
used: verdict.used,
|
|
@@ -551,6 +594,7 @@ export async function runDialecticDeriver({
|
|
|
551
594
|
|
|
552
595
|
// Gate 4: would-empty-card — refuse unless caller passed allowEmptying.
|
|
553
596
|
if (!allowEmptying && detectEmptying(diff, peerCards)) {
|
|
597
|
+
await recordDialecticRun({ repoRoot, status: 'would-empty-card', durationMs: Date.now() - t0 });
|
|
554
598
|
return {
|
|
555
599
|
status: 'would-empty-card',
|
|
556
600
|
skipped_reason: 'detected-empty-card-target',
|
|
@@ -563,6 +607,27 @@ export async function runDialecticDeriver({
|
|
|
563
607
|
};
|
|
564
608
|
}
|
|
565
609
|
|
|
610
|
+
// #1206 success telemetry — DRY-RUN ONLY. `diff` here is the run's FINAL
|
|
611
|
+
// artefact in dry-run mode (Step 6.4 writes it verbatim to
|
|
612
|
+
// `.orchestrator/dialectic-pending.md`), so the delta counts are knowable
|
|
613
|
+
// right here via the pure `countManagedSections()` helper. In APPLY mode
|
|
614
|
+
// the artefact is NOT final yet — `mergePeerCard()` still has to run, and
|
|
615
|
+
// that happens one layer up in `skills/evolve/SKILL.md` Step 6.4 — so the
|
|
616
|
+
// success emit for that branch is that caller's job, using the SAME
|
|
617
|
+
// `recordDialecticRun()` with the real merge-stats deltas.
|
|
618
|
+
if (dryRun) {
|
|
619
|
+
await recordDialecticRun({
|
|
620
|
+
repoRoot,
|
|
621
|
+
status: 'ok',
|
|
622
|
+
mode: 'dry-run',
|
|
623
|
+
userDeltas: countManagedSections(diff.user),
|
|
624
|
+
agentDeltas: countManagedSections(diff.agent),
|
|
625
|
+
tokensIn: response?.usage?.input_tokens,
|
|
626
|
+
tokensOut: response?.usage?.output_tokens,
|
|
627
|
+
durationMs: Date.now() - t0,
|
|
628
|
+
});
|
|
629
|
+
}
|
|
630
|
+
|
|
566
631
|
return {
|
|
567
632
|
status: 'ok',
|
|
568
633
|
diff,
|
package/scripts/emit-event.mjs
CHANGED
|
@@ -22,7 +22,8 @@
|
|
|
22
22
|
*
|
|
23
23
|
* Exit codes (per .claude/rules/cli-design.md):
|
|
24
24
|
* 0 — success (event emitted)
|
|
25
|
-
* 1 — user/input error (missing --type, malformed --payload JSON, non-object
|
|
25
|
+
* 1 — user/input error (missing --type, malformed --payload JSON, non-object
|
|
26
|
+
* payload, or a record rejected by validateEventRecord — #1177)
|
|
26
27
|
* 2 — system error (write failure, unexpected internal error)
|
|
27
28
|
*
|
|
28
29
|
* Data → stdout (only with --json). Diagnostics → stderr (always). Related: #611.
|
|
@@ -49,7 +50,8 @@ Flags:
|
|
|
49
50
|
|
|
50
51
|
Exit codes:
|
|
51
52
|
0 — success
|
|
52
|
-
1 — user/input error (missing --type, malformed --payload, non-object payload
|
|
53
|
+
1 — user/input error (missing --type, malformed --payload, non-object payload,
|
|
54
|
+
or an event record rejected by the events schema)
|
|
53
55
|
2 — system error (write failure / internal error)
|
|
54
56
|
`;
|
|
55
57
|
|
|
@@ -147,6 +149,12 @@ try {
|
|
|
147
149
|
try {
|
|
148
150
|
await emitEvent(type, payload, filePath ? { filePath } : {});
|
|
149
151
|
} catch (err) {
|
|
152
|
+
// A schema-validation rejection is a USER/INPUT error (bad --type or a
|
|
153
|
+
// payload key colliding with the schema) — exit 1, not 2. Nothing was
|
|
154
|
+
// written: emitEvent validates before it touches the filesystem (#1177).
|
|
155
|
+
if (err?.name === 'EventValidationError') {
|
|
156
|
+
fail(`invalid event: ${err.message}`, 1, jsonMode);
|
|
157
|
+
}
|
|
150
158
|
// Write/IO failures are system errors (exit 2).
|
|
151
159
|
fail(`failed to emit event: ${err.message}`, 2, jsonMode);
|
|
152
160
|
}
|
|
@@ -62,6 +62,7 @@ import { findProjectRoot, resolveInstructionFile, expandTilde } from './lib/comm
|
|
|
62
62
|
import { parseSessionConfig } from './lib/config.mjs';
|
|
63
63
|
import { createSecretValueMasker } from './lib/secret-masker.mjs';
|
|
64
64
|
import { stableHostname, readHostAliases } from './lib/host-identity.mjs';
|
|
65
|
+
import { emitEvent, sessionAttribution } from './lib/events.mjs';
|
|
65
66
|
|
|
66
67
|
// Vault-relative default write target (Epic #774 — docs Public-Split removed
|
|
67
68
|
// the prior in-repo generated telemetry doc in favor of the private Meta-Vault).
|
|
@@ -310,6 +311,15 @@ export function redactLocalHostNames(s, names) {
|
|
|
310
311
|
*/
|
|
311
312
|
let _secretMasker = null;
|
|
312
313
|
|
|
314
|
+
/**
|
|
315
|
+
* Learning entries handed to `anonymizeLearning` this process. Counts only
|
|
316
|
+
* (#1028 residue 2) — mirrors `_maskedRecords` in
|
|
317
|
+
* `scripts/lib/vault-mirror/process.mjs`.
|
|
318
|
+
*/
|
|
319
|
+
let _maskedRecords = 0;
|
|
320
|
+
/** String values this process that masking actually CHANGED. Counts only. */
|
|
321
|
+
let _maskHits = 0;
|
|
322
|
+
|
|
313
323
|
/**
|
|
314
324
|
* Mask env-derived secret VALUES in a free-form string.
|
|
315
325
|
*
|
|
@@ -322,7 +332,68 @@ let _secretMasker = null;
|
|
|
322
332
|
function maskSecretValues(s) {
|
|
323
333
|
if (typeof s !== 'string') return s;
|
|
324
334
|
if (_secretMasker === null) _secretMasker = createSecretValueMasker(process.env);
|
|
325
|
-
|
|
335
|
+
const masked = _secretMasker.mask(s);
|
|
336
|
+
if (masked !== s) _maskHits++;
|
|
337
|
+
return masked;
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
/**
|
|
341
|
+
* Counts-only view of the masking that happened in this process (#1028
|
|
342
|
+
* residue 2). FORCE-BUILDS the masker rather than reporting 0 for an unbuilt
|
|
343
|
+
* one — same reasoning as `getMaskerStats()` in
|
|
344
|
+
* `scripts/lib/vault-mirror/process.mjs`: at 0 anonymized entries the lazy
|
|
345
|
+
* build in `maskSecretValues` above never fires, and a `needle_count: 0` from
|
|
346
|
+
* that path would be indistinguishable from "this channel has no masking
|
|
347
|
+
* wired at all" — the exact ambiguity the telemetry exists to remove.
|
|
348
|
+
*
|
|
349
|
+
* NEVER returns a needle, a prefix of one, or any masked text — only cardinals.
|
|
350
|
+
*
|
|
351
|
+
* @returns {{ needleCount: number, records: number, hits: number }}
|
|
352
|
+
*/
|
|
353
|
+
function getExportMaskerStats() {
|
|
354
|
+
if (_secretMasker === null) _secretMasker = createSecretValueMasker(process.env);
|
|
355
|
+
return { needleCount: _secretMasker.needleCount, records: _maskedRecords, hits: _maskHits };
|
|
356
|
+
}
|
|
357
|
+
|
|
358
|
+
/**
|
|
359
|
+
* Emit this channel's `orchestrator.secret_masker.applied` record — the third
|
|
360
|
+
* of the three masker channels (`vault-mirror`, `narrative-mirror`,
|
|
361
|
+
* `export-hw-learnings`) to wire it (#1028 residue 2). Same core field set as
|
|
362
|
+
* the sibling channels (`channel`, `needle_count`, `records`, `hits`,
|
|
363
|
+
* `dry_run`), plus `session_id`/`semantic_session_id` via `sessionAttribution`
|
|
364
|
+
* — matching the `narrative-mirror` channel's shape, since this CLI (like
|
|
365
|
+
* `mirrorNarrative`) always resolves a concrete `repoRoot` to attribute
|
|
366
|
+
* against, unlike the `vault-mirror` CLI's 2-arg `emitEvent` call.
|
|
367
|
+
*
|
|
368
|
+
* `repoRoot` is REQUIRED here rather than left to `emitEvent`'s own
|
|
369
|
+
* cwd-derived default (#941/#1147) — a bare 2-arg call would attribute a run
|
|
370
|
+
* to whatever directory the process happens to sit in rather than to the repo
|
|
371
|
+
* whose `learnings.jsonl` was actually exported.
|
|
372
|
+
*
|
|
373
|
+
* Best-effort: never throws, never alters the export/promote result.
|
|
374
|
+
*
|
|
375
|
+
* @param {{ repoRoot: string, dryRun: boolean }} opts
|
|
376
|
+
* @returns {Promise<void>}
|
|
377
|
+
*/
|
|
378
|
+
async function emitMaskerTelemetry({ repoRoot, dryRun }) {
|
|
379
|
+
if (typeof repoRoot !== 'string' || repoRoot.length === 0) return;
|
|
380
|
+
try {
|
|
381
|
+
const stats = getExportMaskerStats();
|
|
382
|
+
await emitEvent(
|
|
383
|
+
'orchestrator.secret_masker.applied',
|
|
384
|
+
{
|
|
385
|
+
channel: 'export-hw-learnings',
|
|
386
|
+
needle_count: stats.needleCount,
|
|
387
|
+
records: stats.records,
|
|
388
|
+
hits: stats.hits,
|
|
389
|
+
dry_run: !!dryRun,
|
|
390
|
+
...sessionAttribution(repoRoot),
|
|
391
|
+
},
|
|
392
|
+
{ repoRoot },
|
|
393
|
+
);
|
|
394
|
+
} catch {
|
|
395
|
+
/* Best-effort telemetry — a broken ledger must never fail the export. */
|
|
396
|
+
}
|
|
326
397
|
}
|
|
327
398
|
|
|
328
399
|
/**
|
|
@@ -379,6 +450,11 @@ export function bucketCpuPct(pct) {
|
|
|
379
450
|
*/
|
|
380
451
|
export function anonymizeLearning(entry) {
|
|
381
452
|
const e = normalizeLearning(entry);
|
|
453
|
+
// #1028 residue 2: counted BEFORE the masking calls below, unconditionally —
|
|
454
|
+
// "records handed to the masker choke-point" must not depend on whether this
|
|
455
|
+
// particular entry's insight/evidence happened to contain a needle. Mirrors
|
|
456
|
+
// `_maskedRecords++` in `scripts/lib/vault-mirror/process.mjs`.
|
|
457
|
+
_maskedRecords++;
|
|
382
458
|
const out = {
|
|
383
459
|
...e,
|
|
384
460
|
// #1025: value-mask BEFORE form-anonymize — see the ORDER IS LOAD-BEARING
|
|
@@ -488,6 +564,11 @@ function parseArgs(argv) {
|
|
|
488
564
|
input: '.orchestrator/metrics/learnings.jsonl',
|
|
489
565
|
output: undefined, // resolved lazily below (default = vault-dir target)
|
|
490
566
|
generatedAt: new Date().toISOString(),
|
|
567
|
+
// #1028 residue 2: resolved explicitly HERE, at the CLI boundary, so the
|
|
568
|
+
// masker-telemetry emit in promoteHwLearnings/exportHwLearnings gets a
|
|
569
|
+
// real repoRoot — those library functions deliberately never default it
|
|
570
|
+
// themselves (see their opts.repoRoot doc for why).
|
|
571
|
+
repoRoot: findProjectRoot(),
|
|
491
572
|
};
|
|
492
573
|
for (let i = 0; i < argv.length; i++) {
|
|
493
574
|
const a = argv[i];
|
|
@@ -541,9 +622,18 @@ function parseArgs(argv) {
|
|
|
541
622
|
* @param {object} opts
|
|
542
623
|
* @param {string} opts.input — path to learnings.jsonl
|
|
543
624
|
* @param {boolean} opts.dryRun — if true, do not write any files
|
|
625
|
+
* @param {string} [opts.repoRoot] — repo whose ledger the masker-telemetry
|
|
626
|
+
* event (#1028 residue 2) is pinned to. EXPLICIT ONLY — never defaulted to
|
|
627
|
+
* `findProjectRoot()`/cwd inside this library function (#941/#1147: a
|
|
628
|
+
* silent cwd-derived default is exactly what let earlier callers, including
|
|
629
|
+
* plain test invocations, write into whichever repo the process happened to
|
|
630
|
+
* sit in). The CLI entrypoint below resolves and passes it explicitly;
|
|
631
|
+
* library callers that omit it simply get no masker-telemetry emit — see
|
|
632
|
+
* `emitMaskerTelemetry`'s own repoRoot guard.
|
|
544
633
|
* @returns {Promise<{promoted: number, skipped: number, flags: string[]}>}
|
|
545
634
|
*/
|
|
546
635
|
export async function promoteHwLearnings(opts) {
|
|
636
|
+
const repoRoot = opts.repoRoot;
|
|
547
637
|
const { entries, malformed } = await readLearnings(opts.input);
|
|
548
638
|
|
|
549
639
|
const hwPrivate = filterByScope(filterByType(entries, 'hardware-pattern'), 'private');
|
|
@@ -555,6 +645,10 @@ export async function promoteHwLearnings(opts) {
|
|
|
555
645
|
}
|
|
556
646
|
|
|
557
647
|
if (hwPrivate.length === 0) {
|
|
648
|
+
// #1028 residue 2: emitted here too — a run that anonymizes 0 entries
|
|
649
|
+
// still ran, and `getExportMaskerStats()` force-builds the masker so
|
|
650
|
+
// `needle_count` is real even though `_maskedRecords` stays 0.
|
|
651
|
+
await emitMaskerTelemetry({ repoRoot, dryRun: !!opts.dryRun });
|
|
558
652
|
return { promoted: 0, skipped: hwPublicExisting.length, flags };
|
|
559
653
|
}
|
|
560
654
|
|
|
@@ -595,10 +689,23 @@ export async function promoteHwLearnings(opts) {
|
|
|
595
689
|
await rewriteLearnings(opts.input, allEntries);
|
|
596
690
|
}
|
|
597
691
|
|
|
692
|
+
// #1028 residue 2: one masker-telemetry record per promote run.
|
|
693
|
+
await emitMaskerTelemetry({ repoRoot, dryRun: !!opts.dryRun });
|
|
694
|
+
|
|
598
695
|
return { promoted: promotedEntries.length, skipped: hwPublicExisting.length, flags };
|
|
599
696
|
}
|
|
600
697
|
|
|
698
|
+
/**
|
|
699
|
+
* @param {object} opts
|
|
700
|
+
* @param {string} opts.input — path to learnings.jsonl
|
|
701
|
+
* @param {string} opts.output — write target
|
|
702
|
+
* @param {boolean} opts.dryRun — if true, do not write any files
|
|
703
|
+
* @param {string} opts.generatedAt — ISO timestamp for the rendered doc
|
|
704
|
+
* @param {string} [opts.repoRoot] — see `promoteHwLearnings` opts.repoRoot doc.
|
|
705
|
+
* @returns {Promise<{markdown: string, count: number}>}
|
|
706
|
+
*/
|
|
601
707
|
export async function exportHwLearnings(opts) {
|
|
708
|
+
const repoRoot = opts.repoRoot;
|
|
602
709
|
const { entries } = await readLearnings(opts.input);
|
|
603
710
|
const hwPublic = filterByScope(filterByType(entries, 'hardware-pattern'), 'public');
|
|
604
711
|
const anonymized = hwPublic.map((e) => anonymizeLearning(e));
|
|
@@ -608,6 +715,11 @@ export async function exportHwLearnings(opts) {
|
|
|
608
715
|
await mkdir(path.dirname(opts.output), { recursive: true });
|
|
609
716
|
await writeFile(opts.output, md, 'utf8');
|
|
610
717
|
}
|
|
718
|
+
// #1028 residue 2: one masker-telemetry record per export run, whether or
|
|
719
|
+
// not any hardware-pattern entry was actually public (`hwPublic.length`
|
|
720
|
+
// can legitimately be 0 — `getExportMaskerStats()` still force-builds the
|
|
721
|
+
// masker so `needle_count` is a real measured value).
|
|
722
|
+
await emitMaskerTelemetry({ repoRoot, dryRun: !!opts.dryRun });
|
|
611
723
|
return { markdown: md, count: hwPublic.length };
|
|
612
724
|
}
|
|
613
725
|
|