@khoavu882/doflow 2.0.0-beta.5 → 2.0.1
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/README.md +16 -16
- package/bin/doflow.js +22 -12
- package/core/.antigravity-plugin/plugin.json +1 -2
- package/core/.claude-plugin/plugin.json +1 -1
- package/core/.codex-plugin/plugin.json +1 -1
- package/core/.plugin/plugin.json +1 -1
- package/core/harnesses/claude/hooks/lib.sh +43 -24
- package/core/harnesses/claude/hooks/mcp-tool-guard.sh +4 -1
- package/core/harnesses/claude/hooks/permission-audit.sh +3 -0
- package/core/harnesses/claude/hooks/post-compact.sh +35 -32
- package/core/harnesses/claude/hooks/post-edit-lint.sh +2 -0
- package/core/harnesses/claude/hooks/post-shell-observe.sh +48 -0
- package/core/harnesses/claude/hooks/post-tool-failure.sh +3 -0
- package/core/harnesses/claude/hooks/pre-compact.sh +23 -27
- package/core/harnesses/claude/hooks/pre-implement-gate.sh +4 -1
- package/core/harnesses/claude/hooks/session-end.sh +23 -10
- package/core/harnesses/claude/hooks/skill-config-audit.sh +3 -0
- package/core/harnesses/claude/settings/settings.json +26 -9
- package/core/harnesses/claude/statusline/doflow-statusline.sh +1 -0
- package/core/harnesses/codex/agents/core-implementer.toml +1 -0
- package/core/harnesses/codex/agents/delivery-lead.toml +10 -0
- package/core/harnesses/codex/agents/quality-guardian.toml +1 -1
- package/core/harnesses/codex/agents/research-writer.toml +1 -1
- package/core/harnesses/codex/agents/reviewer.toml +10 -0
- package/core/harnesses/codex/agents/spec-analyst.toml +1 -1
- package/core/harnesses/codex/agents/system-architect.toml +1 -1
- package/core/harnesses/codex/hooks/hooks.json +0 -10
- package/core/harnesses/codex/hooks/lib.sh +44 -25
- package/core/harnesses/codex/hooks/mcp-tool-guard.sh +4 -1
- package/core/harnesses/codex/hooks/post-edit-lint.impl.sh +3 -1
- package/core/harnesses/codex/hooks/pre-compact.impl.sh +29 -26
- package/core/harnesses/codex/hooks/pre-implement-gate.sh +4 -1
- package/core/harnesses/codex/hooks/session-end.impl.sh +23 -10
- package/core/harnesses/codex/hooks/subagent-audit.sh +1 -0
- package/core/harnesses/copilot/hooks/doflow-lib.sh +94 -0
- package/core/harnesses/copilot/hooks/doflow-mcp-tool-guard.sh +9 -0
- package/core/harnesses/copilot/hooks/doflow-pre-implement-gate.sh +9 -0
- package/core/harnesses/copilot/hooks/doflow-session-start.sh +9 -0
- package/core/harnesses/copilot/hooks/doflow-stop-check.sh +9 -0
- package/core/harnesses/copilot/hooks/doflow-subagent-start.sh +9 -0
- package/core/harnesses/copilot/hooks/doflow-subagent-stop.sh +9 -0
- package/core/harnesses/copilot/hooks/doflow.json +51 -0
- package/core/harnesses/kiro/agents/doflow.json +1 -11
- package/core/harnesses/kiro/hooks/doflow.json +0 -10
- package/core/harnesses/kiro/hooks/lib.sh +26 -6
- package/core/harnesses/kiro/hooks/mcp-tool-guard.sh +8 -3
- package/core/harnesses/kiro/hooks/pre-implement-gate.sh +8 -3
- package/core/harnesses/kiro/hooks/session-start.sh +1 -0
- package/core/harnesses/kiro/hooks/stop-check.sh +1 -0
- package/core/harnesses/pi/extensions/doflow-guard.js +11 -2
- package/core/harnesses/shared/hooks/ENVELOPE_MIGRATION.md +1 -2
- package/core/harnesses/shared/hooks/adapters/antigravity.js +1 -1
- package/core/harnesses/shared/hooks/bridge/bridge.sh +126 -23
- package/core/harnesses/shared/hooks/bridge/envelope.jq +87 -18
- package/core/harnesses/shared/hooks/bridge/observe-model.sh +75 -0
- package/core/harnesses/shared/hooks/bridge/respond.sh +16 -2
- package/core/harnesses/shared/hooks/policies/capture-failure.sh +49 -16
- package/core/harnesses/shared/hooks/policies/compact-text.sh +46 -0
- package/core/harnesses/shared/hooks/policies/contract.sh +3 -0
- package/core/harnesses/shared/hooks/policies/deny-json.sh +20 -7
- package/core/harnesses/shared/hooks/policies/emission-rules.sh +37 -0
- package/core/harnesses/shared/hooks/policies/emission.jq +209 -0
- package/core/harnesses/shared/hooks/policies/emission.sh +383 -0
- package/core/harnesses/shared/hooks/policies/identity.sh +177 -0
- package/core/harnesses/shared/hooks/policies/lib.sh +63 -40
- package/core/harnesses/shared/hooks/policies/mcp-policy.conf +1 -1
- package/core/harnesses/shared/hooks/policies/mcp-tool-guard.sh +7 -8
- package/core/harnesses/shared/hooks/policies/pre-implementation-gate.sh +132 -57
- package/core/harnesses/shared/hooks/policies/session-context.sh +30 -1
- package/core/harnesses/shared/hooks/policies/stop-check.sh +27 -15
- package/core/harnesses/shared/hooks/policies/subagent-audit.sh +6 -3
- package/core/harnesses/shared/hooks/policies/summary-store.sh +347 -0
- package/core/harnesses/shared/hooks/policies/user-prompt-submit.sh +60 -155
- package/core/harnesses/shared/hooks/stream-hook-runner.js +58 -20
- package/core/harnesses/shared/locator/doflow-run +2 -3
- package/core/registry/advice.json +3 -3
- package/core/registry/assets.json +55 -82
- package/core/registry/capabilities.json +12 -0
- package/core/registry/contracts.json +58 -31
- package/core/registry/contribution-points.json +35 -0
- package/core/registry/gates.json +32 -0
- package/core/registry/guidance-caps.json +40 -0
- package/core/registry/harnesses.json +1445 -366
- package/core/registry/intake.json +53 -0
- package/core/registry/lifecycle.json +599 -996
- package/core/registry/mcp.json +5 -1
- package/core/registry/models.json +7 -1
- package/core/registry/package-templates/README.md +19 -0
- package/core/registry/package-templates/agent/files/agent.md +9 -0
- package/core/registry/package-templates/agent/template.json +4 -0
- package/core/registry/package-templates/capability-provider/files/provider.json +9 -0
- package/core/registry/package-templates/capability-provider/template.json +11 -0
- package/core/registry/package-templates/debate-preset/files/preset.json +26 -0
- package/core/registry/package-templates/debate-preset/template.json +4 -0
- package/core/registry/package-templates/intake-category/files/category.json +8 -0
- package/core/registry/package-templates/intake-category/template.json +4 -0
- package/core/registry/package-templates/review-preset/files/preset.json +30 -0
- package/core/registry/package-templates/review-preset/template.json +4 -0
- package/core/registry/package-templates/skill/files/SKILL.md +8 -0
- package/core/registry/package-templates/skill/template.json +4 -0
- package/core/registry/package-templates/worker/files/worker.json +92 -0
- package/core/registry/package-templates/worker/template.json +11 -0
- package/core/registry/packages/doflow/doflow-package.json +15 -0
- package/core/registry/packages/doflow/presets/debate-3.json +26 -0
- package/core/registry/protocols.json +61 -0
- package/core/registry/routes.json +17 -0
- package/core/registry/rules.json +431 -0
- package/core/registry/settings.json +272 -0
- package/core/registry/storage.json +687 -31
- package/core/registry/telemetry.json +236 -0
- package/core/registry/transcripts.json +142 -0
- package/core/registry/verification.json +76 -6
- package/core/registry/workflows.json +55 -0
- package/core/shared/agent-specs/core-implementer.md +3 -0
- package/core/shared/agent-specs/delivery-lead.md +68 -0
- package/core/shared/agent-specs/quality-guardian.md +5 -1
- package/core/shared/agent-specs/research-writer.md +10 -3
- package/core/shared/agent-specs/reviewer.md +53 -0
- package/core/shared/agent-specs/spec-analyst.md +5 -6
- package/core/shared/agent-specs/system-architect.md +5 -1
- package/core/shared/guidance/DOFLOW_CORE.md +1 -5
- package/core/shared/guidance/modes/MODE_DeepResearch.md +1 -1
- package/core/shared/guidance/modes/MODE_Orchestration.md +4 -3
- package/core/shared/guidance/modes/MODE_Task_Management.md +14 -14
- package/core/shared/guidance/pointers/codex.md +1 -4
- package/core/shared/guidance/references/ARTIFACT_FORMAT.md +30 -16
- package/core/shared/guidance/references/ARTIFACT_VOICE.md +3 -2
- package/core/shared/guidance/references/CONSTITUTION_BASE.md +17 -15
- package/core/shared/guidance/references/DIAGRAM_GUIDE.md +1 -1
- package/core/shared/guidance/references/DOFLOW_CHAIN.md +17 -19
- package/core/shared/guidance/references/EVIDENCE_LEDGER.md +7 -8
- package/core/shared/guidance/references/MODEL_SELECTION.md +5 -3
- package/core/shared/guidance/references/ORCHESTRATION.md +3 -2
- package/core/shared/guidance/references/WORKFLOW_HANDOFF.md +19 -1
- package/core/shared/guidance/rules/RULES.md +45 -0
- package/core/shared/scripts/doflow/bash/do-args.sh +37 -0
- package/core/shared/scripts/doflow/bash/do-exec-paths.sh +4 -0
- package/core/shared/scripts/doflow/bash/do-git-state.sh +15 -4
- package/core/shared/scripts/doflow/bash/do-parallel-check.sh +4 -0
- package/core/shared/scripts/doflow/bash/do-paths.sh +40 -2
- package/core/shared/scripts/doflow/bash/do-prereqs.sh +2 -1
- package/core/shared/scripts/doflow/bash/do-review-package.sh +4 -0
- package/core/shared/scripts/doflow/bash/do-task-brief.sh +58 -16
- package/core/shared/scripts/doflow/bash/render-audit.sh +26 -2
- package/core/shared/scripts/doflow/bash/render-diagrams.sh +1 -0
- package/core/shared/scripts/doflow/bash/render-puml.sh +2 -1
- package/core/shared/scripts/doflow/bash/validate-artifacts.sh +49 -5
- package/core/shared/scripts/doflow/bin/doflow-run +152 -34
- package/core/shared/skills/do/SKILL.md +14 -12
- package/core/shared/skills/do/references/advice_calls.md +26 -0
- package/core/shared/skills/do/references/pm_routing.md +1 -2
- package/core/shared/skills/do/references/program_mode.md +31 -0
- package/core/shared/skills/do-brainstorm/SKILL.md +45 -97
- package/core/shared/skills/do-brainstorm/references/handoff_branches.md +36 -0
- package/core/shared/skills/do-brainstorm/references/intent_seed.md +21 -0
- package/core/shared/skills/do-brainstorm/references/round_log.md +17 -0
- package/core/shared/skills/do-code-review/SKILL.md +48 -148
- package/core/shared/skills/do-code-review/content-types/markdown.md +24 -2
- package/core/shared/skills/do-code-review/references/tools.md +90 -0
- package/core/shared/skills/do-code-review/scripts/doc_quality_checker.py +549 -7
- package/core/shared/skills/do-design/SKILL.md +23 -20
- package/core/shared/skills/do-diagnose/SKILL.md +18 -6
- package/core/shared/skills/do-document/SKILL.md +12 -1
- package/core/shared/skills/do-document/references/deep_research.md +1 -2
- package/core/shared/skills/do-document/references/embedded-research.md +19 -7
- package/core/shared/skills/do-document/references/implementation-flow.md +5 -6
- package/core/shared/skills/do-execute-plan/SKILL.md +19 -60
- package/core/shared/skills/do-execute-plan/references/handoff_record.md +7 -2
- package/core/shared/skills/do-execute-plan/references/parallel_dispatch.md +13 -0
- package/core/shared/skills/do-execute-plan/references/readiness_gate.md +26 -1
- package/core/shared/skills/do-execute-plan/references/run_position.md +16 -2
- package/core/shared/skills/do-execute-plan/references/scaffold.md +17 -9
- package/core/shared/skills/do-execute-plan/references/state_checkpoint.md +11 -0
- package/core/shared/skills/do-execute-plan/references/task_attempts.md +78 -24
- package/core/shared/skills/do-flow/SKILL.md +10 -11
- package/core/shared/skills/do-flow/references/task_classes.md +5 -5
- package/core/shared/skills/do-git/SKILL.md +4 -0
- package/core/shared/skills/do-implement/SKILL.md +13 -14
- package/core/shared/skills/do-plan/SKILL.md +34 -20
- package/core/shared/skills/do-test/SKILL.md +7 -4
- package/core/shared/templates/doflow/constitution-template.md +9 -3
- package/core/shared/templates/doflow/data-model-template.md +1 -1
- package/core/shared/templates/doflow/design-template.md +113 -16
- package/core/shared/templates/doflow/plan-template.md +11 -10
- package/core/shared/templates/doflow/question-log-template.md +14 -2
- package/core/shared/templates/doflow/requirement-template.md +1 -1
- package/core/shared/workflows/do-flow-chain.md +2 -0
- package/core/worker-evidence/antigravity/checks.json +14 -0
- package/core/worker-evidence/codex/2026-10-18-cli-check.json +107 -0
- package/core/worker-evidence/codex/2026-10-18-live-run-edit.json +73 -0
- package/core/worker-evidence/codex/2026-10-18-live-run-read-only.json +62 -0
- package/core/worker-evidence/codex/2026-10-24-cli-check.json +126 -0
- package/core/worker-evidence/codex/checks.json +38 -0
- package/package.json +10 -6
- package/src/adapters/antigravity/index.js +143 -66
- package/src/adapters/claude/index.js +46 -5
- package/src/adapters/codex/agents.js +25 -15
- package/src/adapters/codex/hooks.js +39 -3
- package/src/adapters/codex/index.js +61 -13
- package/src/adapters/codex/native-projection.js +6 -2
- package/src/adapters/copilot/index.js +58 -23
- package/src/adapters/copy-tree.js +291 -46
- package/src/adapters/guidance-manifest.js +71 -0
- package/src/adapters/guidance-pointer.js +19 -0
- package/src/adapters/hook-commands.js +6 -10
- package/src/adapters/index.js +1 -0
- package/src/adapters/kiro/index.js +23 -12
- package/src/adapters/opencode/index.js +8 -8
- package/src/adapters/pi/hooks.js +2 -1
- package/src/adapters/pi/index.js +14 -7
- package/src/adapters/resolve-source.js +26 -2
- package/src/cli/commands/install.js +2 -1
- package/src/cli/commands/reconcile.js +53 -9
- package/src/cli/commands/remove.js +2 -2
- package/src/cli/commands/rollback.js +6 -3
- package/src/cli/commands/self-update.js +18 -9
- package/src/cli/commands/status.js +22 -3
- package/src/cli/commands/ui.js +99 -0
- package/src/cli/commands/update.js +2 -1
- package/src/cli/index.js +337 -32
- package/src/cli/runtime-commands.js +220 -60
- package/src/cli/shared.js +0 -2
- package/src/helper/git.js +1 -1
- package/src/helper/guardrails.js +1 -1
- package/src/helper/marker-merge.js +31 -13
- package/src/helper/package-ids.js +37 -0
- package/src/helper/semver.js +94 -0
- package/src/install/backup.js +105 -15
- package/src/install/context.js +1 -1
- package/src/install/targets.js +31 -16
- package/src/lifecycle/coverage.js +4 -16
- package/src/lifecycle/hook-tier.js +160 -0
- package/src/lifecycle/index.js +412 -78
- package/src/lifecycle/retired-harnesses.js +318 -0
- package/src/lifecycle/view.js +35 -15
- package/src/registry/index.js +551 -26
- package/src/registry/worker-ids.js +45 -0
- package/src/release/build-package.js +0 -3
- package/src/release/docs-blocks.js +472 -0
- package/src/release/preflight.js +425 -0
- package/src/release/rehearse.js +401 -0
- package/src/release/release-workflow.js +733 -0
- package/src/release/sync-plugin-versions.js +43 -7
- package/src/runtime/advice/bench-gate.js +25 -0
- package/src/runtime/advice/cli.js +59 -16
- package/src/runtime/advice/client.js +32 -9
- package/src/runtime/advice/config.js +98 -133
- package/src/runtime/advice/doctor.js +1 -1
- package/src/runtime/advice/elevation.js +97 -0
- package/src/runtime/advice/endpoint-guard.js +9 -3
- package/src/runtime/advice/mode.js +37 -0
- package/src/runtime/advice/record.js +18 -5
- package/src/runtime/advice/registry.js +4 -1
- package/src/runtime/advice/shadow-config.js +229 -0
- package/src/runtime/advice/shadow-dispatcher.js +276 -0
- package/src/runtime/brief-rules.js +81 -0
- package/src/runtime/brief-tools.js +111 -34
- package/src/runtime/candidate.js +20 -11
- package/src/runtime/capabilities/executor.js +450 -0
- package/src/runtime/capabilities/loopback.js +41 -0
- package/src/runtime/capabilities/sanitizer.js +88 -0
- package/src/runtime/capability-router.js +135 -3
- package/src/runtime/checkouts.js +73 -11
- package/src/runtime/claims.js +13 -7
- package/src/runtime/cli.js +196 -19
- package/src/runtime/config-home.js +42 -0
- package/src/runtime/context/arbitrate.js +767 -0
- package/src/runtime/context/delivery-store.js +4 -6
- package/src/runtime/context/emission-rules.js +118 -0
- package/src/runtime/context/identity.js +227 -0
- package/src/runtime/context/pointer.js +67 -12
- package/src/runtime/context/primary-command.js +117 -0
- package/src/runtime/context/primary.js +344 -0
- package/src/runtime/context/summary-store.js +655 -0
- package/src/runtime/context-pack.js +158 -79
- package/src/runtime/decision-register.js +13 -4
- package/src/runtime/dispatch/admission.js +392 -0
- package/src/runtime/dispatch/attempt-end.js +274 -0
- package/src/runtime/dispatch/command.js +628 -0
- package/src/runtime/dispatch/controls.js +904 -0
- package/src/runtime/dispatch/envelope.js +276 -0
- package/src/runtime/dispatch/grants.js +310 -0
- package/src/runtime/dispatch/integrate.js +617 -0
- package/src/runtime/dispatch/loop.js +1835 -0
- package/src/runtime/dispatch/store.js +352 -0
- package/src/runtime/dispatch/verify-run.js +201 -0
- package/src/runtime/evidence-ledger.js +52 -7
- package/src/runtime/failure/capture.js +3 -1
- package/src/runtime/failure/cli.js +25 -9
- package/src/runtime/failure/home.js +57 -30
- package/src/runtime/failure/store.js +7 -2
- package/src/runtime/feature-pointer.js +174 -0
- package/src/runtime/feature-resolve.js +13 -2
- package/src/runtime/fleet/command.js +77 -0
- package/src/runtime/fleet/projects.js +178 -0
- package/src/runtime/fleet/tree.js +383 -0
- package/src/runtime/freshness.js +33 -3
- package/src/runtime/git-memo.js +46 -0
- package/src/runtime/guidance/ablation.js +427 -0
- package/src/runtime/health.js +624 -18
- package/src/runtime/history-compactor.js +13 -3
- package/src/runtime/implementation-gate.js +281 -26
- package/src/runtime/intake/engine.js +677 -0
- package/src/runtime/intake/index.js +136 -0
- package/src/runtime/intake/manifest.js +140 -0
- package/src/runtime/intake/taxonomy.js +206 -0
- package/src/runtime/inventory/coverage.js +1 -1
- package/src/runtime/inventory/index.js +1 -1
- package/src/runtime/inventory/precedence.js +2 -2
- package/src/runtime/inventory/siblings.js +6 -4
- package/src/runtime/knowledge/code-corpus.js +277 -0
- package/src/runtime/knowledge/code-lexical.js +130 -0
- package/src/runtime/knowledge/code-retrieval.js +307 -0
- package/src/runtime/knowledge/code-validation.js +106 -0
- package/src/runtime/knowledge/gp3-gate.js +74 -0
- package/src/runtime/knowledge/graph-adapter.js +288 -0
- package/src/runtime/knowledge/graph-fallback.js +394 -0
- package/src/runtime/knowledge/hybrid.js +136 -8
- package/src/runtime/knowledge/retrieval.js +34 -1
- package/src/runtime/knowledge/rtk-compress.js +77 -0
- package/src/runtime/knowledge/semble-bridge.py +106 -0
- package/src/runtime/knowledge/semble-lifecycle.js +114 -0
- package/src/runtime/knowledge/semble-provider.js +365 -0
- package/src/runtime/lifecycle/cli.js +88 -10
- package/src/runtime/lifecycle/event-store.js +8 -6
- package/src/runtime/lifecycle/followup.js +38 -7
- package/src/runtime/lifecycle/overview.js +26 -2
- package/src/runtime/lifecycle/report-store.js +8 -10
- package/src/runtime/lifecycle/retention.js +95 -31
- package/src/runtime/lifecycle/root.js +9 -1
- package/src/runtime/lifecycle/status.js +34 -17
- package/src/runtime/lifecycle/store-upkeep.js +56 -7
- package/src/runtime/mask.js +134 -7
- package/src/runtime/mcp-consultations.js +40 -6
- package/src/runtime/model-router.js +79 -7
- package/src/runtime/models/catalogue.js +191 -0
- package/src/runtime/models/command.js +153 -0
- package/src/runtime/off-words.js +12 -0
- package/src/runtime/outcome.js +2 -2
- package/src/runtime/packages/command.js +1009 -0
- package/src/runtime/packages/contributions.js +116 -0
- package/src/runtime/packages/digest.js +132 -0
- package/src/runtime/packages/fetch.js +182 -0
- package/src/runtime/packages/grants.js +192 -0
- package/src/runtime/packages/index-file.js +134 -0
- package/src/runtime/packages/instruction.js +90 -0
- package/src/runtime/packages/manifest.js +331 -0
- package/src/runtime/packages/points.js +487 -0
- package/src/runtime/packages/programs.js +216 -0
- package/src/runtime/packages/scaffold.js +277 -0
- package/src/runtime/packages/source.js +90 -0
- package/src/runtime/packages/state.js +164 -0
- package/src/runtime/packages/store.js +449 -0
- package/src/runtime/packages/tar.js +106 -0
- package/src/runtime/packages/view.js +406 -0
- package/src/runtime/plan-check.js +59 -0
- package/src/runtime/plan-content.js +324 -0
- package/src/runtime/policy-init.js +118 -0
- package/src/runtime/profiles/doctor.js +96 -0
- package/src/runtime/profiles/resolve.js +244 -0
- package/src/runtime/profiles/rollback.js +254 -0
- package/src/runtime/profiles/sampler.js +41 -0
- package/src/runtime/readiness-record.js +16 -11
- package/src/runtime/readiness.js +46 -5
- package/src/runtime/research-request.js +50 -25
- package/src/runtime/retrieval-plan.js +10 -30
- package/src/runtime/retrieval-record.js +75 -5
- package/src/runtime/review/command.js +246 -0
- package/src/runtime/review/dominance.js +68 -0
- package/src/runtime/review/findings.js +434 -0
- package/src/runtime/review/identity.js +255 -0
- package/src/runtime/review/protocol-command.js +109 -0
- package/src/runtime/review/protocols.js +405 -0
- package/src/runtime/review/resolve-protocol.js +302 -0
- package/src/runtime/review/start.js +530 -0
- package/src/runtime/roadmap/attendance.js +137 -0
- package/src/runtime/roadmap/facts.js +479 -0
- package/src/runtime/roadmap/gates.js +273 -0
- package/src/runtime/roadmap/loop.js +1719 -0
- package/src/runtime/roadmap/merge.js +390 -0
- package/src/runtime/roadmap/rows.js +1122 -0
- package/src/runtime/roadmap/seed.js +1063 -0
- package/src/runtime/roadmap/worktree-cleanup.js +147 -0
- package/src/runtime/rules-report.js +336 -0
- package/src/runtime/scaffold/artifacts.js +60 -9
- package/src/runtime/scaffold/generate.js +21 -9
- package/src/runtime/settings/autopilot.js +106 -0
- package/src/runtime/settings/cli.js +280 -0
- package/src/runtime/settings/config-write.js +314 -0
- package/src/runtime/settings/files.js +271 -0
- package/src/runtime/settings/legacy.js +154 -0
- package/src/runtime/settings/lexical.js +56 -0
- package/src/runtime/settings/prepared-run.js +269 -0
- package/src/runtime/settings/project-layers.js +118 -0
- package/src/runtime/settings/refs.js +288 -0
- package/src/runtime/settings/registry.js +553 -0
- package/src/runtime/settings/resolve.js +713 -0
- package/src/runtime/settings/shared.js +37 -0
- package/src/runtime/settings/worker-billing.js +107 -0
- package/src/runtime/settings/write.js +269 -0
- package/src/runtime/slot-command.js +78 -0
- package/src/runtime/slots.js +671 -0
- package/src/runtime/source-version.js +1 -0
- package/src/runtime/state-root.js +217 -0
- package/src/runtime/storage/cli.js +12 -5
- package/src/runtime/storage/engine.js +9 -2
- package/src/runtime/storage/registry.js +14 -1
- package/src/runtime/storage/roots.js +66 -16
- package/src/runtime/storage/rules.js +82 -10
- package/src/runtime/storage/upkeep.js +10 -2
- package/src/runtime/storage/work-status.js +245 -26
- package/src/runtime/task-attempts.js +589 -69
- package/src/runtime/task-classifier.js +85 -14
- package/src/runtime/task-graph.js +373 -0
- package/src/runtime/task-run.js +778 -0
- package/src/runtime/task-scope.js +176 -55
- package/src/runtime/task-sources.js +147 -0
- package/src/runtime/task-state.js +373 -64
- package/src/runtime/team/admission.js +301 -0
- package/src/runtime/team/envelope.js +324 -0
- package/src/runtime/team/review-guard.js +156 -0
- package/src/runtime/trace/analyze.js +427 -0
- package/src/runtime/trace/baseline.js +770 -0
- package/src/runtime/trace/ledger.js +63 -140
- package/src/runtime/trace/otlp-export.js +568 -0
- package/src/runtime/trace/otlp-map.js +481 -0
- package/src/runtime/trace/spans.js +745 -0
- package/src/runtime/trace/telemetry.js +225 -0
- package/src/runtime/trace/views.js +1 -0
- package/src/runtime/transcripts/command.js +98 -0
- package/src/runtime/transcripts/cursor.js +326 -0
- package/src/runtime/transcripts/read.js +126 -0
- package/src/runtime/transcripts/readers/claude-jsonl.js +74 -0
- package/src/runtime/transcripts/readers/codex-rollout.js +70 -0
- package/src/runtime/transcripts/readers/copilot-events.js +90 -0
- package/src/runtime/transcripts/readers/kiro-jsonl.js +77 -0
- package/src/runtime/transcripts/readers/pi-jsonl.js +59 -0
- package/src/runtime/transcripts/registry.js +161 -0
- package/src/runtime/transcripts/stats.js +161 -0
- package/src/runtime/verb-view.js +267 -0
- package/src/runtime/verification/check-key.js +628 -0
- package/src/runtime/verification/contract-runner.js +546 -11
- package/src/runtime/verification/engine.js +499 -54
- package/src/runtime/verification/impact.js +617 -0
- package/src/runtime/verification/inflight.js +205 -0
- package/src/runtime/verification/registry.js +176 -0
- package/src/runtime/verification/reuse.js +184 -0
- package/src/runtime/verification/telemetry-emit.js +254 -0
- package/src/runtime/verification/test-selection.js +67 -7
- package/src/runtime/worker/active.js +90 -0
- package/src/runtime/worker/cancel.js +222 -0
- package/src/runtime/worker/catalogue.js +122 -0
- package/src/runtime/worker/command.js +677 -0
- package/src/runtime/worker/evidence.js +288 -0
- package/src/runtime/worker/launch.js +256 -0
- package/src/runtime/worker/models.js +137 -0
- package/src/runtime/worker/parsers.js +218 -0
- package/src/runtime/worker/probes/index.js +706 -0
- package/src/runtime/worker/process-tree.js +415 -0
- package/src/runtime/worker/quota.js +43 -0
- package/src/runtime/worker/readiness.js +713 -0
- package/src/runtime/worker/run-store.js +166 -0
- package/src/runtime/worker/supervisor.js +541 -0
- package/src/runtime/worker/worktree-check.js +252 -0
- package/src/runtime/workflow-engine.js +5 -1
- package/src/runtime/workflow-orchestrator.js +610 -67
- package/src/runtime/worktree.js +149 -22
- package/src/state/index.js +1 -1
- package/src/state/lockfile.js +64 -10
- package/src/state/run-lock.js +1 -1
- package/types/node-commonjs.d.ts +106 -7
- package/core/harnesses/claude/hooks/pre-bash-guard.sh +0 -10
- package/core/harnesses/codex/hooks/pre-bash-guard.sh +0 -10
- package/core/harnesses/gemini/hooks/hooks.json +0 -77
- package/core/harnesses/gemini/hooks/lib.sh +0 -302
- package/core/harnesses/gemini/hooks/mcp-tool-guard.sh +0 -10
- package/core/harnesses/gemini/hooks/post-edit-lint.sh +0 -39
- package/core/harnesses/gemini/hooks/pre-bash-guard.sh +0 -10
- package/core/harnesses/gemini/hooks/pre-compact.sh +0 -38
- package/core/harnesses/gemini/hooks/pre-implement-gate.sh +0 -10
- package/core/harnesses/gemini/hooks/session-end.impl.sh +0 -89
- package/core/harnesses/gemini/hooks/session-end.sh +0 -5
- package/core/harnesses/gemini/hooks/session-start.sh +0 -7
- package/core/harnesses/gemini/settings/adapter-defaults.json +0 -4
- package/core/harnesses/kiro/hooks/pre-bash-guard.sh +0 -24
- package/core/harnesses/shared/hooks/policies/blocked-patterns.conf +0 -91
- package/core/harnesses/shared/hooks/policies/pre-bash-guard.sh +0 -378
- package/core/shared/guidance/FLAGS.md +0 -25
- package/core/shared/guidance/rules/RULE_01_SAFETY.md +0 -25
- package/core/shared/guidance/rules/RULE_02_WORKFLOW.md +0 -23
- package/core/shared/guidance/rules/RULE_03_QUALITY.md +0 -14
- package/core/shared/guidance/rules/RULE_04_QUESTIONS.md +0 -46
- package/src/adapters/gemini/hooks.js +0 -251
- package/src/adapters/gemini/index.js +0 -429
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
{
|
|
2
|
+
"binary": "codex",
|
|
3
|
+
"checks": [
|
|
4
|
+
{
|
|
5
|
+
"argv": [
|
|
6
|
+
"exec",
|
|
7
|
+
"--help"
|
|
8
|
+
],
|
|
9
|
+
"establishes": [
|
|
10
|
+
"runnableProbe",
|
|
11
|
+
"oneShot"
|
|
12
|
+
],
|
|
13
|
+
"exit": 0,
|
|
14
|
+
"expect": [
|
|
15
|
+
"^Usage: codex exec \\[OPTIONS\\] \\[PROMPT\\]",
|
|
16
|
+
"instructions are read from stdin"
|
|
17
|
+
],
|
|
18
|
+
"id": "exec-one-shot",
|
|
19
|
+
"matched": [
|
|
20
|
+
"Usage: codex exec [OPTIONS] [PROMPT]",
|
|
21
|
+
" instructions are read from stdin. If stdin is piped and a prompt is also provided, stdin"
|
|
22
|
+
],
|
|
23
|
+
"result": "pass"
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
"argv": [
|
|
27
|
+
"exec",
|
|
28
|
+
"--help"
|
|
29
|
+
],
|
|
30
|
+
"establishes": [
|
|
31
|
+
"structuredOutput"
|
|
32
|
+
],
|
|
33
|
+
"exit": 0,
|
|
34
|
+
"expect": [
|
|
35
|
+
"^\\s+--json$",
|
|
36
|
+
"Print events to stdout as JSONL",
|
|
37
|
+
"-o, --output-last-message"
|
|
38
|
+
],
|
|
39
|
+
"id": "exec-json",
|
|
40
|
+
"matched": [
|
|
41
|
+
" --json",
|
|
42
|
+
" Print events to stdout as JSONL",
|
|
43
|
+
" -o, --output-last-message <FILE>"
|
|
44
|
+
],
|
|
45
|
+
"result": "pass"
|
|
46
|
+
},
|
|
47
|
+
{
|
|
48
|
+
"argv": [
|
|
49
|
+
"exec",
|
|
50
|
+
"--help"
|
|
51
|
+
],
|
|
52
|
+
"establishes": [
|
|
53
|
+
"readOnly",
|
|
54
|
+
"isolatedEdit"
|
|
55
|
+
],
|
|
56
|
+
"exit": 0,
|
|
57
|
+
"expect": [
|
|
58
|
+
"-s, --sandbox <SANDBOX_MODE>",
|
|
59
|
+
"read-only, workspace-write"
|
|
60
|
+
],
|
|
61
|
+
"id": "exec-sandbox",
|
|
62
|
+
"matched": [
|
|
63
|
+
" -s, --sandbox <SANDBOX_MODE>",
|
|
64
|
+
" [possible values: read-only, workspace-write, danger-full-access]"
|
|
65
|
+
],
|
|
66
|
+
"result": "pass"
|
|
67
|
+
},
|
|
68
|
+
{
|
|
69
|
+
"argv": [
|
|
70
|
+
"features",
|
|
71
|
+
"list",
|
|
72
|
+
"--disable",
|
|
73
|
+
"multi_agent",
|
|
74
|
+
"--disable",
|
|
75
|
+
"multi_agent_v2"
|
|
76
|
+
],
|
|
77
|
+
"establishes": [
|
|
78
|
+
"spawnDenial"
|
|
79
|
+
],
|
|
80
|
+
"exit": 0,
|
|
81
|
+
"expect": [
|
|
82
|
+
"^multi_agent\\s+\\S+\\s+false$",
|
|
83
|
+
"^multi_agent_v2\\s+\\S+\\s+false$"
|
|
84
|
+
],
|
|
85
|
+
"id": "spawn-denial",
|
|
86
|
+
"matched": [
|
|
87
|
+
"multi_agent stable false",
|
|
88
|
+
"multi_agent_v2 stable false"
|
|
89
|
+
],
|
|
90
|
+
"result": "pass"
|
|
91
|
+
},
|
|
92
|
+
{
|
|
93
|
+
"argv": [
|
|
94
|
+
"exec",
|
|
95
|
+
"--help"
|
|
96
|
+
],
|
|
97
|
+
"establishes": [
|
|
98
|
+
"model"
|
|
99
|
+
],
|
|
100
|
+
"exit": 0,
|
|
101
|
+
"expect": [
|
|
102
|
+
"^\\s+-m, --model <MODEL>$"
|
|
103
|
+
],
|
|
104
|
+
"id": "exec-model",
|
|
105
|
+
"matched": [
|
|
106
|
+
" -m, --model <MODEL>"
|
|
107
|
+
],
|
|
108
|
+
"result": "pass"
|
|
109
|
+
}
|
|
110
|
+
],
|
|
111
|
+
"cliVersion": "codex-cli 0.164.0",
|
|
112
|
+
"establishes": [
|
|
113
|
+
"isolatedEdit",
|
|
114
|
+
"model",
|
|
115
|
+
"oneShot",
|
|
116
|
+
"readOnly",
|
|
117
|
+
"runnableProbe",
|
|
118
|
+
"spawnDenial",
|
|
119
|
+
"structuredOutput"
|
|
120
|
+
],
|
|
121
|
+
"harness": "codex",
|
|
122
|
+
"kind": "cli-check",
|
|
123
|
+
"recordedAt": "2026-10-24T10:45:22.229Z",
|
|
124
|
+
"run": null,
|
|
125
|
+
"schema": "doflow-worker-evidence-v1"
|
|
126
|
+
}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
{
|
|
2
|
+
"schema": "doflow-worker-checks-v1",
|
|
3
|
+
"harness": "codex",
|
|
4
|
+
"binary": "codex",
|
|
5
|
+
"version": { "argv": ["--version"], "expect": "^codex-cli \\d+\\.\\d+\\.\\d+" },
|
|
6
|
+
"checks": [
|
|
7
|
+
{
|
|
8
|
+
"id": "exec-one-shot",
|
|
9
|
+
"argv": ["exec", "--help"],
|
|
10
|
+
"expect": ["^Usage: codex exec \\[OPTIONS\\] \\[PROMPT\\]", "instructions are read from stdin"],
|
|
11
|
+
"establishes": ["runnableProbe", "oneShot"]
|
|
12
|
+
},
|
|
13
|
+
{
|
|
14
|
+
"id": "exec-json",
|
|
15
|
+
"argv": ["exec", "--help"],
|
|
16
|
+
"expect": ["^\\s+--json$", "Print events to stdout as JSONL", "-o, --output-last-message"],
|
|
17
|
+
"establishes": ["structuredOutput"]
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
"id": "exec-sandbox",
|
|
21
|
+
"argv": ["exec", "--help"],
|
|
22
|
+
"expect": ["-s, --sandbox <SANDBOX_MODE>", "read-only, workspace-write"],
|
|
23
|
+
"establishes": ["readOnly", "isolatedEdit"]
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
"id": "spawn-denial",
|
|
27
|
+
"argv": ["features", "list", "--disable", "multi_agent", "--disable", "multi_agent_v2"],
|
|
28
|
+
"expect": ["^multi_agent\\s+\\S+\\s+false$", "^multi_agent_v2\\s+\\S+\\s+false$"],
|
|
29
|
+
"establishes": ["spawnDenial"]
|
|
30
|
+
},
|
|
31
|
+
{
|
|
32
|
+
"id": "exec-model",
|
|
33
|
+
"argv": ["exec", "--help"],
|
|
34
|
+
"expect": ["^\\s+-m, --model <MODEL>$"],
|
|
35
|
+
"establishes": ["model"]
|
|
36
|
+
}
|
|
37
|
+
]
|
|
38
|
+
}
|
package/package.json
CHANGED
|
@@ -1,11 +1,10 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@khoavu882/doflow",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.1",
|
|
4
4
|
"description": "DoFlow config installer — npx CLI for the registry-driven multi-harness install/update/remove lifecycle",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"claude-code",
|
|
7
7
|
"codex",
|
|
8
|
-
"gemini",
|
|
9
8
|
"opencode",
|
|
10
9
|
"ai-coding-agent",
|
|
11
10
|
"skills",
|
|
@@ -26,16 +25,21 @@
|
|
|
26
25
|
"doflow": "bin/doflow.js"
|
|
27
26
|
},
|
|
28
27
|
"engines": {
|
|
29
|
-
"node": "
|
|
28
|
+
"node": ">=24.22.1"
|
|
30
29
|
},
|
|
31
30
|
"scripts": {
|
|
32
|
-
"test": "node --test \"test/**/*.test.js\"",
|
|
31
|
+
"test": "node --test \"test/**/*.test.js\" \"test/**/*.test.ts\"",
|
|
32
|
+
"test:fast": "node test/helper/fast-tier.ts",
|
|
33
33
|
"typecheck": "npx -y -p typescript@5.7.2 tsc -p tsconfig.json",
|
|
34
34
|
"build:package": "node src/release/build-package.js .pack",
|
|
35
|
-
"bench": "node bench/runner.
|
|
35
|
+
"bench": "node bench/runner.ts",
|
|
36
36
|
"drift": "node scripts/check-format-drift.js",
|
|
37
|
+
"emission-rules": "node src/runtime/context/emission-rules.js --check",
|
|
37
38
|
"release-notes": "node src/release/changelog-section.js",
|
|
38
|
-
"
|
|
39
|
+
"docs:blocks": "node src/release/docs-blocks.js --check",
|
|
40
|
+
"release:preflight": "node src/release/preflight.js",
|
|
41
|
+
"release:rehearse": "node src/release/rehearse.js",
|
|
42
|
+
"version": "node src/release/sync-plugin-versions.js && git add core/.codex-plugin/plugin.json core/.claude-plugin/plugin.json core/.plugin/plugin.json core/registry/packages/doflow/doflow-package.json core/registry/contribution-points.json"
|
|
39
43
|
},
|
|
40
44
|
"files": [
|
|
41
45
|
"bin/",
|
|
@@ -4,9 +4,11 @@
|
|
|
4
4
|
|
|
5
5
|
// Antigravity CLI adapter (#8). Scope follows the surfaces verified against Antigravity's own
|
|
6
6
|
// docs (antigravity.google/docs/cli/*):
|
|
7
|
-
// instructions — marker-managed section in
|
|
8
|
-
//
|
|
9
|
-
// one
|
|
7
|
+
// instructions — marker-managed section in project AGENTS.md and global ~/.gemini/GEMINI.md (left
|
|
8
|
+
// alone while another live harness declares it); a retired harness's span there is taken over in
|
|
9
|
+
// one write (row 127 IC-007), a person-edited file kept until --force. See instructionTarget.
|
|
10
|
+
// rules — the core set (DOFLOW_CORE.md and the files it imports), flat, in project .agents/rules
|
|
11
|
+
// only; the full guidance tree stays in .doflow/guidance.
|
|
10
12
|
// skills — folder-form copy-tree into project .agents/skills or user ~/.gemini/config/skills.
|
|
11
13
|
// agents — copy-tree into project .agents/agents or user ~/.gemini/config/agents.
|
|
12
14
|
// mcp — entries of the mcpServers object in .agents/mcp_config.json (workspace) or
|
|
@@ -20,9 +22,10 @@ const fs = require('node:fs');
|
|
|
20
22
|
const os = require('node:os');
|
|
21
23
|
const path = require('node:path');
|
|
22
24
|
|
|
23
|
-
const { MARKER_START, MARKER_END } = require('../../helper/marker-merge.js');
|
|
24
|
-
const { planTree, applyTree, removeTree, verifyTree, copyTreeAssets, ledgerFileResources, ledgerSiblingFingerprints, siblingReplacedNotices, fingerprint, readJson, sourceDirFor } = require('../copy-tree.js');
|
|
25
|
+
const { MARKER_START, MARKER_END, removeMarkedSection } = require('../../helper/marker-merge.js');
|
|
26
|
+
const { planTree, applyTree, removeTree, verifyTree, resolveTransform, copyTreeAssets, ledgerFileResources, ledgerSiblingFingerprints, siblingReplacedNotices, fingerprint, readJson, sourceDirFor } = require('../copy-tree.js');
|
|
25
27
|
const { declaredHarnessPaths, resolveHarnessPaths } = require('../../helper/harness-paths.js');
|
|
28
|
+
const { renderGuidancePointer } = require('../guidance-pointer.js');
|
|
26
29
|
const { readMcpFiles, planMcpEntries, verifyMcpEntries, ownedMcpIds, writeMcpEntries } = require('../mcp-entries.js');
|
|
27
30
|
|
|
28
31
|
const HARNESS = 'antigravity';
|
|
@@ -136,8 +139,8 @@ function sha256File(fsImpl , file ) {
|
|
|
136
139
|
|
|
137
140
|
/** Native paths per scope, resolved from the declaration in core/registry/harnesses.json
|
|
138
141
|
* ("paths"): project customization lives at <root>/.agents, global config at ~/.gemini/config
|
|
139
|
-
* (the shared-customization root); instructions
|
|
140
|
-
* rule is declared
|
|
142
|
+
* (the shared-customization root); instructions are AGENTS.md in the project and ~/.gemini/GEMINI.md
|
|
143
|
+
* globally; the hook surfaces are project-only, so no user rule is declared and they resolve to null. */
|
|
141
144
|
function resolveNativePaths(declaredPaths , { scope, scopeRoot, homeDir } = {}) {
|
|
142
145
|
if (scope !== 'project' && scope !== 'global') throw new Error(`Unsupported Antigravity scope '${scope}'`);
|
|
143
146
|
const resolved = resolveHarnessPaths(declaredPaths, { scope, scopeRoot, homeDir });
|
|
@@ -212,16 +215,25 @@ function render({ content = '' } = {}) {
|
|
|
212
215
|
return `${MARKER_START}\n${String(content).trimEnd()}\n${MARKER_END}\n`;
|
|
213
216
|
}
|
|
214
217
|
|
|
215
|
-
|
|
218
|
+
const INSTRUCTIONS_IDENTITY = `doflow:${HARNESS}:instructions:managed-section`;
|
|
219
|
+
/** The short start marker the retired harness wrote into ~/.gemini/GEMINI.md (row 127). It is read
|
|
220
|
+
* only in a file this adapter is taking over, never written: the span it opens is replaced with ours. */
|
|
221
|
+
const PREDECESSOR_MARKER_START = '<!-- doflow:start -->';
|
|
222
|
+
|
|
223
|
+
/** The file's content with `rendered` as its DoFlow span: created, appended to a file with none, or
|
|
224
|
+
* replacing the span in place. `predecessor` also accepts the retired harness's start marker, for a
|
|
225
|
+
* file being taken over. `name` is the file's name in the conflict. */
|
|
226
|
+
function managedInstruction(existing , rendered , { name = 'AGENTS.md', predecessor = false } = {}) {
|
|
216
227
|
if (existing === null) return { ok: true, operation: 'create', content: rendered };
|
|
217
|
-
|
|
228
|
+
let start = existing.indexOf(MARKER_START);
|
|
229
|
+
if (start === -1 && predecessor) start = existing.indexOf(PREDECESSOR_MARKER_START);
|
|
218
230
|
const end = existing.indexOf(MARKER_END);
|
|
219
231
|
if (start === -1 && end === -1) {
|
|
220
232
|
const separator = existing === '' || existing.endsWith('\n') ? '\n' : '\n\n';
|
|
221
233
|
const content = `${existing}${separator}${rendered}`;
|
|
222
234
|
return { ok: true, operation: 'merge', content };
|
|
223
235
|
}
|
|
224
|
-
if (start === -1 || end === -1 || end < start) return { ok: false, conflict:
|
|
236
|
+
if (start === -1 || end === -1 || end < start) return { ok: false, conflict: `${name} has malformed DoFlow managed-section markers` };
|
|
225
237
|
const content = `${existing.slice(0, start)}${rendered}${existing.slice(end + MARKER_END.length).replace(/^\n?/, '')}`;
|
|
226
238
|
return { ok: true, operation: content === existing ? 'none' : 'merge', content };
|
|
227
239
|
}
|
|
@@ -279,7 +291,7 @@ function planTrees({ assets, paths, scope, neutralResources, removing, repoRoot,
|
|
|
279
291
|
for (const { asset, destDir } of targets) {
|
|
280
292
|
const sourceDir = sourceDirFor(asset, { repoRoot }, fsImpl, HARNESS);
|
|
281
293
|
const previousResources = ledgerFileResources(neutralResources, HARNESS, asset.id);
|
|
282
|
-
const result = planTree({ sourceDir, destDir, previousResources, siblingFingerprints: ledgerSiblingFingerprints(neutralResources, HARNESS), operation: removing ? 'remove' : 'apply', fsImpl, layout: asset.layout, keepModified: !removing,
|
|
294
|
+
const result = planTree({ sourceDir, destDir, previousResources, siblingFingerprints: ledgerSiblingFingerprints(neutralResources, HARNESS), operation: removing ? 'remove' : 'apply', fsImpl, layout: asset.layout, transform: asset.transform, select: asset.select, keepModified: !removing,
|
|
283
295
|
// Forwarded so the CLI's --force reaches planTree's conflict check; omitting it let
|
|
284
296
|
// planTree's own `force = false` default stand in silently. Gated on `!removing` for the
|
|
285
297
|
// reason codex/index.ts states in full: force heals drift on apply, but a hand-edited file
|
|
@@ -297,6 +309,7 @@ function planTrees({ assets, paths, scope, neutralResources, removing, repoRoot,
|
|
|
297
309
|
ownershipIdentity: `doflow:${HARNESS}:copy-tree:${asset.id}:${change.relPath}`,
|
|
298
310
|
kind: 'copy-tree-file', identity: change.relPath,
|
|
299
311
|
afterFingerprint: change.fingerprint, fingerprint: change.fingerprint, sourceVersion: 'registry-v1',
|
|
312
|
+
transformName: asset.transform || null,
|
|
300
313
|
...(change.kept ? { retained: true, retainedFor: [] } : {}),
|
|
301
314
|
projection: { renderer: 'copy-tree' },
|
|
302
315
|
});
|
|
@@ -315,7 +328,8 @@ function runTreeChanges(changes , mode ) {
|
|
|
315
328
|
.filter((c ) => c.projection?.renderer === 'copy-tree' || c.kind === 'copy-tree-file')
|
|
316
329
|
.map((c ) => ({ relPath: c.identity ?? c.relPath, target: c.target,
|
|
317
330
|
source: c._text ? undefined : c.source, operation: c.operation,
|
|
318
|
-
fingerprint: c.fingerprint, pruneGuard: c.pruneGuard,
|
|
331
|
+
fingerprint: c.fingerprint, pruneGuard: c.pruneGuard, transformName: c.transformName || null,
|
|
332
|
+
...(c._text ? { _text: c._text } : {}) }));
|
|
319
333
|
// Content-managed tree files (hook scripts): write rendered text with +x, not a byte copy.
|
|
320
334
|
for (const t of treeChanges) {
|
|
321
335
|
if (t._text === undefined) continue;
|
|
@@ -330,58 +344,100 @@ function runTreeChanges(changes , mode ) {
|
|
|
330
344
|
const plain = treeChanges.filter((t ) => t._text === undefined);
|
|
331
345
|
const writes = plain.filter((c ) => c.operation !== 'remove');
|
|
332
346
|
const removals = plain.filter((c ) => c.operation === 'remove');
|
|
333
|
-
|
|
347
|
+
// A projection that declares a transform (the rules' always_on header) is re-derived from the
|
|
348
|
+
// source at write time, so each change is applied under its own transform.
|
|
349
|
+
const byTransform = new Map ();
|
|
350
|
+
for (const change of writes) byTransform.set(change.transformName, [...(byTransform.get(change.transformName) || []), change]);
|
|
351
|
+
let applied = 0;
|
|
352
|
+
for (const [transformName, group] of byTransform) {
|
|
353
|
+
applied += applyTree({ changes: group, transform: transformName ? resolveTransform(transformName) : undefined }).applied;
|
|
354
|
+
}
|
|
334
355
|
const removed = removals.length ? removeTree({ changes: removals }).removed : 0;
|
|
335
356
|
return { applied, removed };
|
|
336
357
|
})(),
|
|
337
358
|
};
|
|
338
|
-
const writes = treeChanges.filter((c ) => c.operation !== 'remove');
|
|
339
|
-
const removals = treeChanges.filter((c ) => c.operation === 'remove');
|
|
340
|
-
const applied = writes.length ? applyTree({ changes: writes }).applied : 0;
|
|
341
|
-
const removed = removals.length ? removeTree({ changes: removals }).removed : 0;
|
|
342
|
-
return { applied, removed };
|
|
343
359
|
}
|
|
344
360
|
|
|
345
361
|
// ---- instructions component ----
|
|
346
362
|
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
363
|
+
/** The instruction file this run manages, or null: project AGENTS.md as ever; the global GEMINI.md
|
|
364
|
+
* only when the pointer asset is selected and no other live harness in `registry` declares that same
|
|
365
|
+
* file (until the harness that owned it retires, its adapter keeps it and this one stays out). */
|
|
366
|
+
function instructionTarget({ paths, assets, registry } ) {
|
|
367
|
+
if (!paths.instruction) return null;
|
|
368
|
+
if (scopeOf(paths) === 'project') return paths.instruction;
|
|
369
|
+
if (!(assets ?? []).some((asset ) => asset.id === POINTER_ASSET_ID)) return null;
|
|
370
|
+
const declaredBy = (harness ) => {
|
|
371
|
+
if (harness?.id === HARNESS || !harness?.paths?.instruction) return false;
|
|
372
|
+
try { return resolveHarnessPaths({ instruction: harness.paths.instruction }, { scope: 'global', scopeRoot: paths.root, homeDir: paths.root }).instruction === paths.instruction; } catch { return false; }
|
|
373
|
+
};
|
|
374
|
+
return (registry?.harnesses ?? []).some(declaredBy) ? null : paths.instruction;
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
/** How this run stands to a section it took over (IC-007): the lifecycle's handover verdict for the
|
|
378
|
+
* file, this harness's own row on it, and whether a person-edited file stays as it is (`retained`:
|
|
379
|
+
* edited before the handover, or kept since, and no --force). `predecessor` lets the retired
|
|
380
|
+
* harness's span count as the section to replace; `keptRow` is a row recorded as kept. A handover
|
|
381
|
+
* file whose DoFlow span already is this harness's render was written by DoFlow itself (a run that
|
|
382
|
+
* threw after that write and before its ledger write), so it does not count as edited. */
|
|
383
|
+
function instructionState({ target, context, resources, paths, fsImpl = fs } ) {
|
|
384
|
+
const handover = (context.handovers ?? []).find((item ) => item.target === target) ?? null;
|
|
385
|
+
const ownRow = (resources ?? []).find((row ) => row.harness === HARNESS && row.target === target && row.ownershipIdentity === INSTRUCTIONS_IDENTITY) ?? null;
|
|
386
|
+
const ownWrite = () => {
|
|
387
|
+
const rendered = renderedInstruction(paths, fsImpl);
|
|
388
|
+
if (rendered === null || !fsImpl.existsSync(target)) return false;
|
|
389
|
+
const outcome = managedInstruction(fsImpl.readFileSync(target, 'utf8'), rendered);
|
|
390
|
+
return outcome.ok && outcome.operation === 'none';
|
|
391
|
+
};
|
|
392
|
+
const edited = (handover?.edited === true && !ownWrite()) || ownRow?.retainedEdit === true;
|
|
393
|
+
return { predecessor: Boolean(handover) || ownRow?.retainedEdit === true, retained: edited && context.force !== true,
|
|
394
|
+
keptRow: ownRow?.retainedEdit === true };
|
|
395
|
+
}
|
|
396
|
+
|
|
397
|
+
function instructionsChange(target , fields ) {
|
|
398
|
+
return { assetId: POINTER_ASSET_ID, target, ownershipIdentity: INSTRUCTIONS_IDENTITY,
|
|
399
|
+
kind: 'instructions-section', identity: path.basename(target), projection: { renderer: 'antigravity-instructions' }, ...fields };
|
|
400
|
+
}
|
|
401
|
+
|
|
402
|
+
function planInstructions({ paths, target, removing, state, fsImpl = fs } ) {
|
|
403
|
+
const none = { changes: [], conflicts: [], notices: [] };
|
|
404
|
+
if (!target) return none;
|
|
350
405
|
if (removing) {
|
|
351
406
|
// Removal must strip the section DoFlow owns while leaving foreign bytes untouched — same
|
|
352
407
|
// contract as the other AGENTS-style adapters.
|
|
353
|
-
if (!fsImpl.existsSync(
|
|
354
|
-
const text = fsImpl.readFileSync(
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
ownershipIdentity: `doflow:${HARNESS}:instructions:managed-section`,
|
|
360
|
-
kind: 'instructions-section', identity: 'AGENTS.md',
|
|
361
|
-
projection: { renderer: 'antigravity-instructions' },
|
|
362
|
-
}],
|
|
363
|
-
conflicts: [],
|
|
364
|
-
};
|
|
408
|
+
if (!fsImpl.existsSync(target)) return none;
|
|
409
|
+
const text = fsImpl.readFileSync(target, 'utf8');
|
|
410
|
+
// A kept edited file with no span left still carries this harness's row: the remove change
|
|
411
|
+
// releases the row, and apply finds no span to strip, so the person's file is not touched.
|
|
412
|
+
if (!text.includes(MARKER_START) && !state.keptRow) return none;
|
|
413
|
+
return { ...none, changes: [instructionsChange(target, { operation: 'remove' })] };
|
|
365
414
|
}
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
if (
|
|
415
|
+
if (state.retained) {
|
|
416
|
+
const shown = scopeOf(paths) === 'global' ? `~/${path.relative(paths.root, target)}` : path.relative(paths.root, target);
|
|
417
|
+
return { ...none, notices: [`kept ${shown}: changed before handover; --force replaces the DoFlow section`] };
|
|
418
|
+
}
|
|
419
|
+
const rendered = renderedInstruction(paths, fsImpl);
|
|
420
|
+
if (rendered === null) return none;
|
|
421
|
+
const existing = fsImpl.existsSync(target) ? fsImpl.readFileSync(target, 'utf8') : null;
|
|
422
|
+
const outcome = managedInstruction(existing, rendered, { name: path.basename(target), predecessor: state.predecessor });
|
|
423
|
+
if (!outcome.ok) return { ...none, conflicts: [outcome.conflict] };
|
|
424
|
+
if (outcome.operation === 'none') return none;
|
|
372
425
|
return {
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
kind: 'instructions-section', identity: 'AGENTS.md',
|
|
426
|
+
...none,
|
|
427
|
+
changes: [instructionsChange(target, {
|
|
428
|
+
operation: existing === null ? 'create' : 'update',
|
|
377
429
|
afterFingerprint: fingerprint(outcome.content), sourceVersion: 'registry-v1',
|
|
378
|
-
projection: { renderer: 'antigravity-instructions' },
|
|
379
430
|
_content: outcome.content,
|
|
380
|
-
}],
|
|
381
|
-
conflicts: [],
|
|
431
|
+
})],
|
|
382
432
|
};
|
|
383
433
|
}
|
|
384
434
|
|
|
435
|
+
/** This scope's DoFlow section: the shared pointer rendered for the scope, inside the markers. */
|
|
436
|
+
function renderedInstruction(paths , fsImpl ) {
|
|
437
|
+
const sourceText = pointerBody(fsImpl);
|
|
438
|
+
return sourceText ? render({ content: renderGuidancePointer(sourceText, { scope: scopeOf(paths), scopeRoot: paths.root }) }) : null;
|
|
439
|
+
}
|
|
440
|
+
|
|
385
441
|
function pointerBody(fsImpl ) {
|
|
386
442
|
// The shared pointer prose ships once; read it through the same repo-relative anchor the other
|
|
387
443
|
// AGENTS-style adapters use.
|
|
@@ -432,13 +488,18 @@ function plan(options = {}, impl = {}) {
|
|
|
432
488
|
const selectedServers = Array.isArray(options.mcp) ? options.mcp : [];
|
|
433
489
|
const discovery = options.discovery ?? discover(options, impl);
|
|
434
490
|
|
|
435
|
-
const
|
|
491
|
+
const instructionFile = instructionTarget({ paths, assets: options.assets, registry: options.registry });
|
|
492
|
+
const instructions = planInstructions({ paths, target: instructionFile, removing, fsImpl,
|
|
493
|
+
state: instructionState({ target: instructionFile, context, resources: neutralResources, paths, fsImpl }) });
|
|
436
494
|
const trees = planTrees({ assets: options.assets, paths, scope, neutralResources, removing, repoRoot: context.repoRoot, force: context.force === true, fsImpl });
|
|
437
495
|
const mcp = planMcpEntries({
|
|
438
496
|
...mcpEntriesInput({ paths, mcp: selectedServers, mcpAdoptable: options.mcpAdoptable, resources: neutralResources }),
|
|
439
497
|
files: discovery.mcpSnapshot, removing,
|
|
440
498
|
});
|
|
441
|
-
|
|
499
|
+
// Hook tiers (maint-hooks): outside `hooks.harnesses` this plan carries no hook change; the lifecycle
|
|
500
|
+
// plans the removal of what an earlier run wrote, from the ledger, against the full registry.
|
|
501
|
+
const hooksPlan = context.hooksOff === true && !removing ? { changes: [], conflicts: [] }
|
|
502
|
+
: planHooks({ paths, scope, neutralResources, removing, repoRoot: context.repoRoot, fsImpl });
|
|
442
503
|
|
|
443
504
|
const changes = [...instructions.changes, ...trees.changes, ...mcp.changes, ...hooksPlan.changes];
|
|
444
505
|
const conflicts = [...instructions.conflicts, ...trees.conflicts, ...mcp.conflicts, ...hooksPlan.conflicts];
|
|
@@ -447,7 +508,7 @@ function plan(options = {}, impl = {}) {
|
|
|
447
508
|
conflicts,
|
|
448
509
|
prerequisites: [],
|
|
449
510
|
requiredNativeResources: changes,
|
|
450
|
-
notices: [...trees.notices, ...mcp.notices],
|
|
511
|
+
notices: [...instructions.notices, ...trees.notices, ...mcp.notices],
|
|
451
512
|
};
|
|
452
513
|
}
|
|
453
514
|
|
|
@@ -485,14 +546,26 @@ function apply(options = {}, impl = {}) {
|
|
|
485
546
|
|
|
486
547
|
for (const change of changes.filter((c ) => c.projection?.renderer === 'antigravity-instructions')) {
|
|
487
548
|
if (change.operation === 'remove') {
|
|
488
|
-
// pi precedent: strip only the managed span; the file survives even when nothing remains.
|
|
489
549
|
if (!fsImpl.existsSync(change.target)) continue;
|
|
550
|
+
// The global file is the person's: the span goes with the one newline put before it, so their
|
|
551
|
+
// bytes come back exactly (and a file that held only the span goes with it). A kept file taken
|
|
552
|
+
// over from the retired harness may still hold that harness's span, under its short marker.
|
|
553
|
+
if ((options.scope ?? 'project') === 'global') { removeMarkedSection(change.target, { startMarkers: [MARKER_START, PREDECESSOR_MARKER_START] }); continue; }
|
|
554
|
+
// pi precedent: strip only the managed span; the file survives even when nothing remains.
|
|
490
555
|
const next = strippedInstruction(fsImpl.readFileSync(change.target, 'utf8'));
|
|
491
556
|
if (next !== null) fsImpl.writeFileSync(change.target, next, 'utf8');
|
|
492
557
|
continue;
|
|
493
558
|
}
|
|
559
|
+
// One rename onto the file: no reader, and no failure, ever sees it without its DoFlow span.
|
|
494
560
|
fsImpl.mkdirSync(path.dirname(change.target), { recursive: true });
|
|
495
|
-
|
|
561
|
+
const tmp = `${change.target}.${process.pid}.tmp`;
|
|
562
|
+
try {
|
|
563
|
+
fsImpl.writeFileSync(tmp, change._content ?? render({ content: '' }), 'utf8');
|
|
564
|
+
fsImpl.renameSync(tmp, change.target);
|
|
565
|
+
} catch (error) {
|
|
566
|
+
fsImpl.rmSync(tmp, { force: true });
|
|
567
|
+
throw error;
|
|
568
|
+
}
|
|
496
569
|
}
|
|
497
570
|
for (const change of changes.filter((c ) => c.projection?.renderer === 'antigravity-hooks')) {
|
|
498
571
|
if (change.kind === 'copy-tree-file') continue; // handled by runTreeChanges below
|
|
@@ -594,24 +667,28 @@ function verify(options = {}, impl = {}) {
|
|
|
594
667
|
const statuses = [];
|
|
595
668
|
const resources = [];
|
|
596
669
|
|
|
597
|
-
const
|
|
598
|
-
|
|
599
|
-
const
|
|
600
|
-
|
|
670
|
+
const instructionFile = instructionTarget({ paths, assets: options.assets, registry: options.registry });
|
|
671
|
+
const state = instructionState({ target: instructionFile, context, resources: ledgerResources(options), paths, fsImpl });
|
|
672
|
+
const instruction = instructionFile && fsImpl.existsSync(instructionFile)
|
|
673
|
+
? fsImpl.readFileSync(instructionFile, 'utf8') : null;
|
|
674
|
+
const managed = instruction !== null && instruction.includes(MARKER_END)
|
|
675
|
+
&& (instruction.includes(MARKER_START) || (state.predecessor && instruction.includes(PREDECESSOR_MARKER_START)));
|
|
676
|
+
// A kept, person-edited file (IC-007) is owned as it is now, markers or not: an edit can drop the
|
|
677
|
+
// span, and without its row the next run would see no owner and append the section unasked.
|
|
678
|
+
const kept = !removing && state.retained && instruction !== null;
|
|
679
|
+
if (instructionFile) {
|
|
601
680
|
// Removal verification asks "did our section go away?"; install/update asks "is it managed?".
|
|
602
681
|
statuses.push({
|
|
603
682
|
assetId: POINTER_ASSET_ID, capability: 'instructions',
|
|
604
|
-
status: removing ? (managed ? 'retained' : 'absent') : (managed ? 'managed' : 'missing'),
|
|
605
|
-
target:
|
|
683
|
+
status: removing ? (managed ? 'retained' : 'absent') : (managed ? 'managed' : (kept ? 'retained' : 'missing')),
|
|
684
|
+
target: instructionFile,
|
|
606
685
|
});
|
|
607
|
-
if (
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
ownershipIdentity: `doflow:${HARNESS}:instructions:managed-section`,
|
|
611
|
-
kind: 'instructions-section', identity: 'AGENTS.md',
|
|
686
|
+
if (!removing && (managed || kept)) {
|
|
687
|
+
// Recorded with the file as it is now; a kept one is flagged so later runs keep it until --force.
|
|
688
|
+
resources.push(instructionsChange(instructionFile, {
|
|
612
689
|
fingerprint: fingerprint(instruction), sourceVersion: 'registry-v1',
|
|
613
|
-
|
|
614
|
-
});
|
|
690
|
+
...(state.retained ? { retainedEdit: true } : {}),
|
|
691
|
+
}));
|
|
615
692
|
}
|
|
616
693
|
}
|
|
617
694
|
|
|
@@ -619,7 +696,7 @@ function verify(options = {}, impl = {}) {
|
|
|
619
696
|
const destDir = treeDestFor(asset, paths, scope);
|
|
620
697
|
if (!destDir) continue;
|
|
621
698
|
const sourceDir = sourceDirFor(asset, { repoRoot: context.repoRoot }, fsImpl, HARNESS);
|
|
622
|
-
const result = verifyTree({ sourceDir, destDir, fsImpl, layout: asset.layout, plannedWrites: context.plannedWrites });
|
|
699
|
+
const result = verifyTree({ sourceDir, destDir, fsImpl, layout: asset.layout, transform: asset.transform, select: asset.select, plannedWrites: context.plannedWrites });
|
|
623
700
|
conflictsToStatuses(result.conflicts, asset.id, statuses);
|
|
624
701
|
for (const resource of result.resources) {
|
|
625
702
|
resources.push({
|
|
@@ -642,7 +719,7 @@ function verify(options = {}, impl = {}) {
|
|
|
642
719
|
resources.push(...mcp.resources);
|
|
643
720
|
|
|
644
721
|
// Hooks projection (project scope): the shims' bytes and the registered groups.
|
|
645
|
-
if (scope === 'project') {
|
|
722
|
+
if (scope === 'project' && context.hooksOff !== true) {
|
|
646
723
|
const hooks = verifyHooks({ options, paths, context, fsImpl });
|
|
647
724
|
statuses.push(...hooks.statuses);
|
|
648
725
|
resources.push(...hooks.resources);
|