cloving 1.3.0 → 1.5.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/README.md +329 -215
- package/dist/src/agent-harness-shell.d.ts +2 -1
- package/dist/src/agent-harness-shell.js +8 -5
- package/dist/src/authority/command-wait-checks.d.ts +8 -0
- package/dist/src/authority/command-wait-checks.js +88 -0
- package/dist/src/authority/command-wait-results.d.ts +15 -0
- package/dist/src/authority/command-wait-results.js +73 -0
- package/dist/src/authority/command-wait-view.d.ts +21 -0
- package/dist/src/authority/command-wait-view.js +34 -0
- package/dist/src/authority/command-waits.d.ts +39 -0
- package/dist/src/authority/command-waits.js +97 -0
- package/dist/src/authority/commands.js +22 -1
- package/dist/src/authority/dispatch-decision.d.ts +8 -0
- package/dist/src/authority/dispatch-decision.js +26 -1
- package/dist/src/authority/effect-requests.js +6 -3
- package/dist/src/authority/effect-results.js +4 -2
- package/dist/src/authority/history-state.d.ts +2 -0
- package/dist/src/authority/history-state.js +13 -1
- package/dist/src/authority/instants.d.ts +1 -0
- package/dist/src/authority/instants.js +21 -0
- package/dist/src/authority/reduction-state.d.ts +2 -0
- package/dist/src/authority/reduction-state.js +5 -0
- package/dist/src/authority/reduction.js +24 -0
- package/dist/src/authority/status-input.d.ts +2 -0
- package/dist/src/authority/status.d.ts +2 -0
- package/dist/src/authority/status.js +1 -0
- package/dist/src/authority/stop-sequence.d.ts +1 -0
- package/dist/src/authority/stop-sequence.js +2 -1
- package/dist/src/authority/transitions.d.ts +6 -4
- package/dist/src/authority/transitions.js +7 -0
- package/dist/src/broker/actor/authority-health.d.ts +9 -0
- package/dist/src/broker/actor/authority-health.js +24 -0
- package/dist/src/broker/actor/authority-queries.d.ts +2 -1
- package/dist/src/broker/actor/authority-queries.js +14 -5
- package/dist/src/broker/actor/authority-receipts.js +1 -1
- package/dist/src/broker/actor/authority-runtime.d.ts +4 -2
- package/dist/src/broker/actor/authority-runtime.js +29 -20
- package/dist/src/broker/actor/authority-session.d.ts +6 -19
- package/dist/src/broker/actor/authority-session.js +66 -88
- package/dist/src/broker/actor/authority-settings.d.ts +2 -1
- package/dist/src/broker/actor/authority-settings.js +6 -3
- package/dist/src/broker/actor/authority-upgrades.d.ts +23 -2
- package/dist/src/broker/actor/authority-upgrades.js +8 -2
- package/dist/src/broker/actor/authority-watchdog.d.ts +6 -2
- package/dist/src/broker/actor/authority-watchdog.js +31 -9
- package/dist/src/broker/actor/authority.js +3 -1
- package/dist/src/broker/actor/delivery-intents.js +2 -0
- package/dist/src/broker/actor/effect-delivery.d.ts +1 -1
- package/dist/src/broker/actor/effect-delivery.js +15 -2
- package/dist/src/broker/actor/effect-plan.js +11 -2
- package/dist/src/broker/actor/effect-queries.d.ts +4 -0
- package/dist/src/broker/actor/effect-queries.js +9 -1
- package/dist/src/broker/actor/effect-turn.js +2 -0
- package/dist/src/broker/actor/projection-memory.d.ts +43 -0
- package/dist/src/broker/actor/projection-memory.js +207 -0
- package/dist/src/broker/actor/runtime-parts.d.ts +5 -0
- package/dist/src/broker/actor/runtime-parts.js +8 -3
- package/dist/src/broker/actor/stop-plan.js +9 -3
- package/dist/src/broker/actor/stop-turn.d.ts +2 -0
- package/dist/src/broker/actor/stop-turn.js +24 -11
- package/dist/src/broker/actor/turn-draft.d.ts +1 -0
- package/dist/src/broker/actor/turn-draft.js +4 -0
- package/dist/src/broker/actor/turn-state.js +5 -1
- package/dist/src/broker/authority-admission.js +60 -0
- package/dist/src/broker/authority-restore.d.ts +2 -0
- package/dist/src/broker/authority-restore.js +35 -1
- package/dist/src/broker/command-wait-restore.d.ts +31 -0
- package/dist/src/broker/command-wait-restore.js +86 -0
- package/dist/src/broker/decision-restore.d.ts +1 -1
- package/dist/src/broker/decision-restore.js +1 -0
- package/dist/src/broker/effect-upgrade.d.ts +3 -0
- package/dist/src/broker/effect-upgrade.js +11 -2
- package/dist/src/cli/arguments.d.ts +13 -0
- package/dist/src/cli/arguments.js +43 -3
- package/dist/src/cli/chat-stores.d.ts +2 -0
- package/dist/src/cli/chat-stores.js +113 -0
- package/dist/src/cli/client.d.ts +7 -2
- package/dist/src/cli/client.js +13 -7
- package/dist/src/cli/command-requests.d.ts +46 -0
- package/dist/src/cli/command-requests.js +84 -0
- package/dist/src/cli/command-waits.d.ts +9 -0
- package/dist/src/cli/command-waits.js +51 -0
- package/dist/src/cli/commands.js +70 -88
- package/dist/src/cli/config-file.d.ts +2 -2
- package/dist/src/cli/config-file.js +4 -2
- package/dist/src/cli/config-notice.js +5 -2
- package/dist/src/cli/doctor-retention.d.ts +2 -0
- package/dist/src/cli/doctor-retention.js +93 -0
- package/dist/src/cli/doctor-workflows.d.ts +5 -2
- package/dist/src/cli/doctor-workflows.js +12 -7
- package/dist/src/cli/doctor.js +11 -9
- package/dist/src/cli/harness-probes.d.ts +2 -0
- package/dist/src/cli/harness-probes.js +1 -1
- package/dist/src/cli/harness-processes.d.ts +6 -0
- package/dist/src/cli/harness-processes.js +36 -0
- package/dist/src/cli/init-command.d.ts +9 -0
- package/dist/src/cli/init-command.js +52 -0
- package/dist/src/cli/init-prompt-command.d.ts +10 -0
- package/dist/src/cli/init-prompt-command.js +145 -0
- package/dist/src/cli/init-prompt.d.ts +35 -0
- package/dist/src/cli/init-prompt.js +74 -0
- package/dist/src/cli/init-selection.d.ts +13 -0
- package/dist/src/cli/init-selection.js +75 -0
- package/dist/src/cli/main.d.ts +2 -0
- package/dist/src/cli/main.js +37 -7
- package/dist/src/cli/mcp-server.d.ts +1 -0
- package/dist/src/cli/mcp-server.js +156 -0
- package/dist/src/cli/mcp-tools.d.ts +15 -0
- package/dist/src/cli/mcp-tools.js +242 -0
- package/dist/src/cli/queue-arguments.d.ts +15 -0
- package/dist/src/cli/queue-arguments.js +31 -0
- package/dist/src/cli/queue-render.d.ts +3 -0
- package/dist/src/cli/queue-render.js +26 -0
- package/dist/src/cli/reload-render.d.ts +2 -0
- package/dist/src/cli/reload-render.js +12 -0
- package/dist/src/cli/render.d.ts +1 -1
- package/dist/src/cli/render.js +54 -38
- package/dist/src/cli/report-ci-jobs.d.ts +23 -0
- package/dist/src/cli/report-ci-jobs.js +103 -0
- package/dist/src/cli/report-ci-usage.d.ts +9 -0
- package/dist/src/cli/report-ci-usage.js +185 -0
- package/dist/src/cli/report-ci.d.ts +13 -0
- package/dist/src/cli/report-ci.js +74 -0
- package/dist/src/cli/report-closures.d.ts +6 -0
- package/dist/src/cli/report-closures.js +97 -0
- package/dist/src/cli/report-flow.d.ts +7 -0
- package/dist/src/cli/report-flow.js +122 -0
- package/dist/src/cli/report-github-reader.d.ts +29 -0
- package/dist/src/cli/report-github-reader.js +157 -0
- package/dist/src/cli/report-github.d.ts +15 -8
- package/dist/src/cli/report-github.js +131 -150
- package/dist/src/cli/report-operator.d.ts +3 -0
- package/dist/src/cli/report-operator.js +40 -0
- package/dist/src/cli/report-ready.d.ts +3 -0
- package/dist/src/cli/report-ready.js +96 -0
- package/dist/src/cli/report-text.d.ts +9 -0
- package/dist/src/cli/report-text.js +33 -0
- package/dist/src/cli/report.d.ts +1 -0
- package/dist/src/cli/report.js +104 -27
- package/dist/src/cli/runtime-arguments.d.ts +18 -3
- package/dist/src/cli/runtime-arguments.js +29 -20
- package/dist/src/cli/schedule-arguments.d.ts +14 -0
- package/dist/src/cli/schedule-arguments.js +26 -0
- package/dist/src/cli/schedule-render.d.ts +22 -0
- package/dist/src/cli/schedule-render.js +73 -0
- package/dist/src/cli/terminal-text.d.ts +3 -0
- package/dist/src/cli/terminal-text.js +28 -0
- package/dist/src/cli/toolchain.d.ts +1 -0
- package/dist/src/cli/toolchain.js +1 -0
- package/dist/src/cli/usage-render.d.ts +1 -0
- package/dist/src/cli/usage-render.js +28 -1
- package/dist/src/cli/usage.d.ts +2 -2
- package/dist/src/cli/usage.js +89 -11
- package/dist/src/cli/watch-actions.js +2 -2
- package/dist/src/cli/watch-api-document.d.ts +430 -0
- package/dist/src/cli/watch-api-document.js +291 -0
- package/dist/src/cli/watch-api-run.d.ts +56 -0
- package/dist/src/cli/watch-api-run.js +112 -0
- package/dist/src/cli/watch-api.d.ts +17 -0
- package/dist/src/cli/watch-api.js +230 -0
- package/dist/src/cli/watch-board-view.js +19 -2
- package/dist/src/cli/watch-board.d.ts +4 -2
- package/dist/src/cli/watch-board.js +53 -43
- package/dist/src/cli/watch-card-forms.d.ts +1 -1
- package/dist/src/cli/watch-card-forms.js +11 -10
- package/dist/src/cli/watch-client.d.ts +1 -1
- package/dist/src/cli/watch-client.js +2 -11
- package/dist/src/cli/watch-header-view.d.ts +1 -5
- package/dist/src/cli/watch-header-view.js +17 -21
- package/dist/src/cli/watch-model.d.ts +5 -1
- package/dist/src/cli/watch-model.js +20 -11
- package/dist/src/cli/watch-page.js +15 -15
- package/dist/src/cli/watch-phases.d.ts +12 -3
- package/dist/src/cli/watch-phases.js +68 -11
- package/dist/src/cli/watch-pr-board.js +1 -1
- package/dist/src/cli/watch-pr-command.d.ts +1 -0
- package/dist/src/cli/watch-pull-request.js +18 -8
- package/dist/src/cli/watch-reads.d.ts +3 -0
- package/dist/src/cli/watch-reads.js +22 -20
- package/dist/src/cli/watch-render.d.ts +15 -0
- package/dist/src/cli/watch-run-input.d.ts +0 -1
- package/dist/src/cli/watch-run-input.js +0 -13
- package/dist/src/cli/watch-server.js +24 -10
- package/dist/src/cli/watch-view.d.ts +0 -3
- package/dist/src/cli/watch-view.js +13 -13
- package/dist/src/cli.js +73 -12
- package/dist/src/command-wait.d.ts +4 -0
- package/dist/src/command-wait.js +45 -0
- package/dist/src/configuration-change.d.ts +7 -0
- package/dist/src/configuration-change.js +14 -0
- package/dist/src/configuration-display.js +2 -0
- package/dist/src/configuration-schema.d.ts +14 -0
- package/dist/src/configuration-schema.js +6 -2
- package/dist/src/daemon/attachment-file.d.ts +6 -0
- package/dist/src/daemon/attachment-file.js +86 -0
- package/dist/src/daemon/attachments.d.ts +14 -0
- package/dist/src/daemon/attachments.js +17 -0
- package/dist/src/daemon/claude-recovery.d.ts +50 -0
- package/dist/src/daemon/claude-recovery.js +208 -0
- package/dist/src/daemon/claude-stream.d.ts +27 -0
- package/dist/src/daemon/claude-stream.js +63 -0
- package/dist/src/daemon/claude-turn.d.ts +11 -25
- package/dist/src/daemon/claude-turn.js +64 -81
- package/dist/src/daemon/claude-worker.d.ts +5 -4
- package/dist/src/daemon/claude-worker.js +127 -126
- package/dist/src/daemon/daemon-adapters.d.ts +9 -0
- package/dist/src/daemon/daemon-adapters.js +33 -5
- package/dist/src/daemon/daemon-loops.d.ts +5 -1
- package/dist/src/daemon/daemon-loops.js +18 -10
- package/dist/src/daemon/daemon.js +80 -61
- package/dist/src/daemon/github-attach.d.ts +2 -0
- package/dist/src/daemon/github-attach.js +222 -0
- package/dist/src/daemon/github-calls.js +1 -1
- package/dist/src/daemon/github-ci-filters.d.ts +6 -0
- package/dist/src/daemon/github-ci-filters.js +138 -0
- package/dist/src/daemon/github-ci-workflows.d.ts +10 -0
- package/dist/src/daemon/github-ci-workflows.js +148 -0
- package/dist/src/daemon/github-ci.js +22 -4
- package/dist/src/daemon/github-issue-methods.d.ts +2 -0
- package/dist/src/daemon/github-issue-methods.js +37 -2
- package/dist/src/daemon/github-merge-call.d.ts +2 -1
- package/dist/src/daemon/github-merge-call.js +10 -3
- package/dist/src/daemon/github-merge.js +52 -24
- package/dist/src/daemon/github-methods.js +18 -4
- package/dist/src/daemon/github-operation.d.ts +4 -0
- package/dist/src/daemon/github-operation.js +6 -0
- package/dist/src/daemon/github-worker.d.ts +4 -0
- package/dist/src/daemon/github-worker.js +6 -0
- package/dist/src/daemon/issue-queue.d.ts +4 -1
- package/dist/src/daemon/issue-queue.js +76 -78
- package/dist/src/daemon/merge-turns.d.ts +10 -0
- package/dist/src/daemon/merge-turns.js +37 -0
- package/dist/src/daemon/notify-events.d.ts +6 -0
- package/dist/src/daemon/notify-events.js +84 -0
- package/dist/src/daemon/notify-journal.js +1 -1
- package/dist/src/daemon/notify-message.d.ts +4 -1
- package/dist/src/daemon/notify-message.js +36 -0
- package/dist/src/daemon/notify.d.ts +1 -1
- package/dist/src/daemon/notify.js +5 -77
- package/dist/src/daemon/operation-journal.d.ts +1 -0
- package/dist/src/daemon/queue-control.d.ts +13 -0
- package/dist/src/daemon/queue-control.js +86 -0
- package/dist/src/daemon/queue-journal.d.ts +20 -0
- package/dist/src/daemon/queue-journal.js +89 -0
- package/dist/src/daemon/queue-status.d.ts +9 -3
- package/dist/src/daemon/queue-status.js +17 -4
- package/dist/src/daemon/record-archive.d.ts +19 -0
- package/dist/src/daemon/record-archive.js +82 -0
- package/dist/src/daemon/record-sweep.d.ts +24 -0
- package/dist/src/daemon/record-sweep.js +147 -0
- package/dist/src/daemon/resume-index-lock.d.ts +13 -0
- package/dist/src/daemon/resume-index-lock.js +160 -0
- package/dist/src/daemon/resume-worktree.d.ts +7 -0
- package/dist/src/daemon/resume-worktree.js +29 -0
- package/dist/src/daemon/retrying-turn.d.ts +2 -12
- package/dist/src/daemon/retrying-turn.js +98 -172
- package/dist/src/daemon/schedule-control.d.ts +26 -0
- package/dist/src/daemon/schedule-control.js +110 -0
- package/dist/src/daemon/schedule-journal.d.ts +2 -15
- package/dist/src/daemon/schedule-journal.js +67 -4
- package/dist/src/daemon/settings-reload.d.ts +26 -0
- package/dist/src/daemon/settings-reload.js +82 -0
- package/dist/src/daemon/ticket-registration.d.ts +2 -7
- package/dist/src/daemon/ticket-registration.js +15 -81
- package/dist/src/daemon/turn-attempt-journal.d.ts +38 -0
- package/dist/src/daemon/turn-attempt-journal.js +136 -0
- package/dist/src/daemon/turn-attempts.d.ts +47 -0
- package/dist/src/daemon/turn-attempts.js +166 -0
- package/dist/src/daemon/turn-details.d.ts +4 -0
- package/dist/src/daemon/turn-details.js +33 -0
- package/dist/src/daemon/turn-report.d.ts +8 -1
- package/dist/src/daemon/turn-report.js +39 -0
- package/dist/src/daemon/work-tree.d.ts +9 -0
- package/dist/src/daemon/work-tree.js +20 -0
- package/dist/src/daemon/worker-profile.d.ts +9 -0
- package/dist/src/daemon/worker-profile.js +44 -0
- package/dist/src/daemon/workflow-generations.d.ts +7 -4
- package/dist/src/daemon/workflow-generations.js +22 -14
- package/dist/src/daemon/workflow-reload.d.ts +41 -0
- package/dist/src/daemon/workflow-reload.js +244 -0
- package/dist/src/daemon/workflow-replay.d.ts +2 -1
- package/dist/src/daemon/workflow-replay.js +7 -3
- package/dist/src/daemon/workflow-schedules.d.ts +3 -0
- package/dist/src/daemon/workflow-schedules.js +98 -45
- package/dist/src/daemon/worktree-processes.d.ts +9 -0
- package/dist/src/daemon/worktree-processes.js +151 -0
- package/dist/src/doctor-report.d.ts +4 -6
- package/dist/src/doctor-report.js +8 -13
- package/dist/src/harness-start.d.ts +15 -0
- package/dist/src/harness-start.js +37 -0
- package/dist/src/host/command-wait.d.ts +38 -0
- package/dist/src/host/command-wait.js +115 -0
- package/dist/src/host/start-delivery.d.ts +5 -7
- package/dist/src/host/start-delivery.js +3 -15
- package/dist/src/host/step-bridge-host.d.ts +2 -0
- package/dist/src/host/step-bridge-host.js +21 -0
- package/dist/src/operation-identity.d.ts +1 -0
- package/dist/src/operation-identity.js +4 -0
- package/dist/src/private-config.schema.json +71 -0
- package/dist/src/project-config.schema.json +40 -0
- package/dist/src/project-settings.d.ts +16 -2
- package/dist/src/project-settings.js +35 -1
- package/dist/src/queue-spend.d.ts +4 -0
- package/dist/src/queue-spend.js +21 -0
- package/dist/src/queue-state.d.ts +26 -0
- package/dist/src/queue-state.js +34 -0
- package/dist/src/record-retention.d.ts +46 -0
- package/dist/src/record-retention.js +81 -0
- package/dist/src/relay/relay-service.d.ts +3 -0
- package/dist/src/relay/relay-service.js +5 -3
- package/dist/src/report-ci.d.ts +164 -0
- package/dist/src/report-ci.js +32 -0
- package/dist/src/report-effects.d.ts +15 -0
- package/dist/src/report-effects.js +212 -0
- package/dist/src/report-flow-types.d.ts +38 -0
- package/dist/src/report-flow-types.js +7 -0
- package/dist/src/report-flow.d.ts +43 -0
- package/dist/src/report-flow.js +193 -0
- package/dist/src/report-operator.d.ts +67 -0
- package/dist/src/report-operator.js +25 -0
- package/dist/src/report-quality.d.ts +221 -0
- package/dist/src/report-quality.js +94 -0
- package/dist/src/report-ready.d.ts +23 -0
- package/dist/src/report-ready.js +117 -0
- package/dist/src/report-statistics.d.ts +2 -1
- package/dist/src/report-statistics.js +40 -4
- package/dist/src/report.d.ts +588 -47
- package/dist/src/report.js +156 -41
- package/dist/src/schedule-progress.d.ts +33 -0
- package/dist/src/schedule-progress.js +45 -0
- package/dist/src/service/active-tickets.js +11 -6
- package/dist/src/service/command-waits.d.ts +34 -0
- package/dist/src/service/command-waits.js +86 -0
- package/dist/src/service/dispatcher.d.ts +4 -0
- package/dist/src/service/dispatcher.js +33 -0
- package/dist/src/service/expiry.js +2 -0
- package/dist/src/service/gateway.js +3 -1
- package/dist/src/service/queue-handlers.d.ts +4 -0
- package/dist/src/service/queue-handlers.js +32 -0
- package/dist/src/service/queue-spend.d.ts +6 -0
- package/dist/src/service/queue-spend.js +68 -0
- package/dist/src/service/registry.d.ts +28 -2
- package/dist/src/service/registry.js +48 -0
- package/dist/src/service/replies.d.ts +22 -8
- package/dist/src/service/replies.js +16 -2
- package/dist/src/service/run-handlers.js +37 -12
- package/dist/src/service/run-metadata.d.ts +15 -1
- package/dist/src/service/run-metadata.js +93 -8
- package/dist/src/service/service.d.ts +11 -3
- package/dist/src/service/service.js +22 -37
- package/dist/src/service/submission-handler.js +18 -4
- package/dist/src/service/worker-port.js +9 -1
- package/dist/src/service/worker-totals.d.ts +6 -0
- package/dist/src/service/worker-totals.js +8 -1
- package/dist/src/service/workflow-reload.d.ts +35 -0
- package/dist/src/service/workflow-reload.js +52 -0
- package/dist/src/step-bridge.d.ts +20 -0
- package/dist/src/steps/command-wait.d.ts +12 -0
- package/dist/src/steps/command-wait.js +26 -0
- package/dist/src/steps/open-decision-wait.d.ts +2 -0
- package/dist/src/steps/{decision-gate.js → open-decision-wait.js} +0 -7
- package/dist/src/steps/review-by-person.js +4 -1
- package/dist/src/steps/wait-for-command.d.ts +3 -0
- package/dist/src/steps/wait-for-command.js +17 -0
- package/dist/src/steps/wait-for-decision.js +1 -1
- package/dist/src/storage/command-wait-rows.d.ts +30 -0
- package/dist/src/storage/command-wait-rows.js +96 -0
- package/dist/src/storage/decision-snapshots.d.ts +8 -2
- package/dist/src/storage/decision-snapshots.js +16 -8
- package/dist/src/storage/domain-changes.d.ts +3 -1
- package/dist/src/storage/domain-changes.js +4 -0
- package/dist/src/storage/domain-schema.d.ts +16 -1
- package/dist/src/storage/domain-schema.js +35 -4
- package/dist/src/storage/effect-schema.d.ts +2 -0
- package/dist/src/storage/effect-schema.js +9 -0
- package/dist/src/storage/projection-changes.d.ts +12 -0
- package/dist/src/storage/projection-changes.js +194 -0
- package/dist/src/storage/projection-lookups.d.ts +7 -0
- package/dist/src/storage/projection-lookups.js +30 -0
- package/dist/src/testing-requests.d.ts +15 -0
- package/dist/src/testing-requests.js +93 -0
- package/dist/src/testing.d.ts +4 -10
- package/dist/src/testing.js +33 -86
- package/dist/src/worker-usage.d.ts +1 -0
- package/dist/src/worker-usage.js +3 -0
- package/dist/src/workflow-candidate.d.ts +1 -0
- package/dist/src/workflow-candidate.js +12 -1
- package/dist/src/workflow-contracts.d.ts +1 -0
- package/dist/src/workflow-contracts.js +9 -2
- package/dist/src/workflow-declaration.d.ts +1 -0
- package/dist/src/workflow-declaration.js +3 -0
- package/dist/src/workflow-discovery.d.ts +2 -13
- package/dist/src/workflow-discovery.js +1 -13
- package/dist/src/workflow-refusals.js +0 -1
- package/dist/src/workflows.d.ts +1 -1
- package/dist/src/workflows.js +1 -1
- package/dist/tools/compile-workflows.js +3 -0
- package/dist/tools/project-configuration.d.ts +7 -2
- package/dist/tools/project-configuration.js +30 -1
- package/dist/tools/red-green-command.d.ts +1 -0
- package/dist/tools/red-green-command.js +174 -0
- package/dist/tools/red-green-process.d.ts +10 -0
- package/dist/tools/red-green-process.js +59 -0
- package/dist/tools/self-host-processes.d.ts +2 -0
- package/dist/tools/self-host-processes.js +69 -26
- package/dist/tools/self-host-project.d.ts +2 -0
- package/dist/tools/self-host-project.js +30 -77
- package/dist/tools/self-host-runtime.js +1 -1
- package/dist/tools/self-host.js +76 -34
- package/dist/tools/template-command.d.ts +1 -0
- package/dist/tools/template-command.js +160 -0
- package/dist/tools/template-copy.d.ts +11 -0
- package/dist/tools/template-copy.js +130 -0
- package/dist/tools/template-files.d.ts +17 -0
- package/dist/tools/template-files.js +74 -0
- package/dist/tools/workflow-bundles.js +1 -0
- package/dist/tools/workflow-candidate-counts.js +2 -2
- package/dist/tools/workflow-candidate-program.d.ts +4 -2
- package/dist/tools/workflow-candidate-program.js +30 -11
- package/dist/tools/workflow-candidate-shape.d.ts +3 -0
- package/dist/tools/workflow-candidate-shape.js +90 -0
- package/dist/tools/workflow-candidate-source.d.ts +1 -0
- package/dist/tools/workflow-candidate-source.js +26 -4
- package/dist/tools/workflow-candidate-syntax.d.ts +2 -2
- package/dist/tools/workflow-candidate-syntax.js +24 -94
- package/dist/tools/workflow-command.js +1 -2
- package/dist/tools/workflow-folders.d.ts +2 -3
- package/dist/tools/workflow-folders.js +1 -1
- package/package.json +17 -9
- package/templates/develop/README.md +93 -4
- package/templates/develop/develop/flow-tests.ts +38 -1
- package/templates/develop/develop/interruption-tests.ts +157 -0
- package/templates/develop/develop/local.ts +1 -0
- package/templates/develop/develop/option-tests.ts +138 -9
- package/templates/develop/develop/pull.ts +5 -1
- package/templates/develop/develop/red-green.ts +55 -0
- package/templates/develop/develop/refusal-tests.ts +77 -0
- package/templates/develop/develop/report.ts +31 -11
- package/templates/develop/develop/round.ts +1 -0
- package/templates/develop/develop/scenarios.ts +27 -0
- package/templates/develop/develop/turn.ts +28 -7
- package/templates/develop/develop.declaration.json +1 -1
- package/templates/develop/develop.test.ts +4 -0
- package/templates/develop/template.json +29 -2
- package/templates/idea-to-issue/README.md +27 -0
- package/templates/idea-to-issue/idea-to-issue/effects.ts +52 -0
- package/templates/idea-to-issue/idea-to-issue/leave.ts +10 -0
- package/templates/idea-to-issue/idea-to-issue/next.ts +29 -0
- package/templates/idea-to-issue/idea-to-issue/post-person.ts +18 -0
- package/templates/idea-to-issue/idea-to-issue/post.ts +50 -0
- package/templates/idea-to-issue/idea-to-issue/queue.ts +27 -0
- package/templates/idea-to-issue/idea-to-issue/review.ts +42 -0
- package/templates/idea-to-issue/idea-to-issue/scenarios.ts +50 -0
- package/templates/idea-to-issue/idea-to-issue/turn.ts +40 -0
- package/templates/idea-to-issue/idea-to-issue.declaration.json +16 -0
- package/templates/idea-to-issue/idea-to-issue.test.ts +79 -0
- package/templates/idea-to-issue/idea-to-issue.ts +49 -0
- package/templates/idea-to-issue/template.json +81 -0
- package/templates/review-day/README.md +97 -0
- package/templates/review-day/review-day/critique.ts +58 -0
- package/templates/review-day/review-day/decision.ts +29 -0
- package/templates/review-day/review-day/facts.ts +69 -0
- package/templates/review-day/review-day/label.ts +29 -0
- package/templates/review-day/review-day/next.ts +28 -0
- package/templates/review-day/review-day/post.ts +27 -0
- package/templates/review-day/review-day/report.ts +98 -0
- package/templates/review-day/review-day/rules.ts +12 -0
- package/templates/review-day/review-day/scenarios.ts +76 -0
- package/templates/review-day/review-day/turn.ts +73 -0
- package/templates/review-day/review-day.declaration.json +16 -0
- package/templates/review-day/review-day.test.ts +362 -0
- package/templates/review-day/review-day.ts +37 -0
- package/templates/review-day/template.json +56 -0
- package/dist/src/cli/watch-start-view.d.ts +0 -18
- package/dist/src/cli/watch-start-view.js +0 -77
- package/dist/src/steps/decision-gate.d.ts +0 -3
- package/dist/workflows/develop-prd.d.ts +0 -7
- package/dist/workflows/develop-prd.js +0 -165
- package/dist/workflows/develop-ticket.d.ts +0 -9
- package/dist/workflows/develop-ticket.js +0 -207
- package/dist/workflows/issue-labels.d.ts +0 -16
- package/dist/workflows/issue-labels.js +0 -70
- package/dist/workflows/ticket-prompts.d.ts +0 -35
- package/dist/workflows/ticket-prompts.js +0 -147
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { scheduledText } from "./schedule-render.js";
|
|
2
|
+
import { CommandWaits, effectBudgetText } from "./command-waits.js";
|
|
1
3
|
import { Header, Queue } from "./watch-header-view.js";
|
|
2
4
|
export { clove, Header } from "./watch-header-view.js";
|
|
3
5
|
import { priceText, usageText, totalsSuffix } from "./usage-render.js";
|
|
@@ -8,7 +10,6 @@ import { boardWorkflow, watchHash, watchLocation } from "./watch-navigation.js";
|
|
|
8
10
|
import { Decision, Events, Turn, PullRequest } from "./watch-turn.js";
|
|
9
11
|
import { Commands } from "./command-effects.js";
|
|
10
12
|
export { PullRequest } from "./watch-turn.js";
|
|
11
|
-
import { StartRun } from "./watch-start-view.js";
|
|
12
13
|
export function BannerDetail(props) {
|
|
13
14
|
const { run, now } = props;
|
|
14
15
|
const turn = run.turns.at(-1);
|
|
@@ -88,9 +89,7 @@ export function Review(props) {
|
|
|
88
89
|
export function Run(props) {
|
|
89
90
|
const { run, now, copying } = props;
|
|
90
91
|
const turn = run.turns.at(-1);
|
|
91
|
-
const budget = run.spent
|
|
92
|
-
? ""
|
|
93
|
-
: ` · ${String(run.spent)} of ${String(run.limit)} effect units`;
|
|
92
|
+
const budget = effectBudgetText(run.spent, run.limit);
|
|
94
93
|
const none = "No agent turn for this run.";
|
|
95
94
|
const turns = run.turns.length === 0
|
|
96
95
|
? element("p", { class: "meta", children: none })
|
|
@@ -103,13 +102,17 @@ export function Run(props) {
|
|
|
103
102
|
}),
|
|
104
103
|
]);
|
|
105
104
|
const foot = [
|
|
106
|
-
`${run.workflowId} · ${run.runId}${budget}`,
|
|
105
|
+
`${run.workflowId} · ${run.runId}${budget === "" ? "" : ` · ${budget}`}`,
|
|
107
106
|
element("br", {}),
|
|
108
107
|
`${run.code}: ${run.detail}`,
|
|
109
108
|
];
|
|
110
109
|
return [
|
|
111
110
|
component(Banner, { run, now }),
|
|
111
|
+
run.scheduled === undefined
|
|
112
|
+
? null
|
|
113
|
+
: element("p", { class: "meta", children: scheduledText(run.scheduled) }),
|
|
112
114
|
component(HandoffLinks, { run }),
|
|
115
|
+
component(CommandWaits, { waits: run.commandWaits ?? [] }),
|
|
113
116
|
element("section", {
|
|
114
117
|
class: "run-usage",
|
|
115
118
|
children: [
|
|
@@ -181,21 +184,18 @@ export function Page(props) {
|
|
|
181
184
|
return component(BoardPage, { ...props, model, workflowId, down });
|
|
182
185
|
}
|
|
183
186
|
export function BoardPage(props) {
|
|
184
|
-
const { model, workflowId, down, now, stale
|
|
187
|
+
const { model, workflowId, down, now, stale } = props;
|
|
185
188
|
const workflow = model.workflows.find((item) => item.workflowId === workflowId);
|
|
186
|
-
const start = props.start ?? { shown: false, onToggle: () => undefined };
|
|
187
189
|
return element("div", {
|
|
188
190
|
class: "board-page",
|
|
189
191
|
children: [
|
|
190
|
-
component(Header, { model, stale,
|
|
192
|
+
component(Header, { model, stale, phone: props.phone, now }),
|
|
191
193
|
component(Queue, { model }),
|
|
192
194
|
down,
|
|
195
|
+
model.schedules !== undefined && "status" in model.schedules
|
|
196
|
+
? element("p", { class: "meta", children: "Schedules: unavailable" })
|
|
197
|
+
: null,
|
|
193
198
|
component(RefusedWorkflows, { model }),
|
|
194
|
-
component(StartRun, {
|
|
195
|
-
workflows: model.workflows,
|
|
196
|
-
copying,
|
|
197
|
-
shown: start.shown,
|
|
198
|
-
}),
|
|
199
199
|
component(WorkflowList, {
|
|
200
200
|
workflows: model.workflows,
|
|
201
201
|
selected: workflowId,
|
package/dist/src/cli.js
CHANGED
|
@@ -1,8 +1,10 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import { createProbeRunner } from "./cli/probe-command.js";
|
|
3
|
+
import { terminateHarness } from "./cli/harness-processes.js";
|
|
3
4
|
import { settingsEnvironment } from "./cli/project-settings.js";
|
|
5
|
+
import { constants as systemConstants } from "node:os";
|
|
4
6
|
import { addAbortListener } from "node:events";
|
|
5
|
-
import { execFile, execFileSync, spawn } from "node:child_process";
|
|
7
|
+
import { execFile, execFileSync, spawn, } from "node:child_process";
|
|
6
8
|
import { existsSync, realpathSync } from "node:fs";
|
|
7
9
|
import { parseArgs } from "node:util";
|
|
8
10
|
import { delimiter, dirname, extname, join, resolve } from "node:path";
|
|
@@ -30,7 +32,7 @@ const watchCommand = async (request) => {
|
|
|
30
32
|
cwd: request.directory,
|
|
31
33
|
signal: request.signal,
|
|
32
34
|
killSignal: "SIGKILL",
|
|
33
|
-
maxBuffer: 1024 * 1024,
|
|
35
|
+
maxBuffer: request.outputBytes ?? 1024 * 1024,
|
|
34
36
|
encoding: "utf8",
|
|
35
37
|
}, (error, stdout) => {
|
|
36
38
|
const code = error === null ? 0 : error.code;
|
|
@@ -58,6 +60,52 @@ const watchCommand = async (request) => {
|
|
|
58
60
|
listener[Symbol.dispose]();
|
|
59
61
|
}
|
|
60
62
|
};
|
|
63
|
+
function spawnedHarness(request) {
|
|
64
|
+
try {
|
|
65
|
+
return spawn(request.executable, request.arguments, {
|
|
66
|
+
cwd: request.directory,
|
|
67
|
+
env: request.environment,
|
|
68
|
+
stdio: "inherit",
|
|
69
|
+
});
|
|
70
|
+
}
|
|
71
|
+
catch {
|
|
72
|
+
return undefined;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
function startHarness(request) {
|
|
76
|
+
return new Promise((settle) => {
|
|
77
|
+
const interrupt = () => undefined;
|
|
78
|
+
const terminate = () => {
|
|
79
|
+
terminateHarness(child?.pid, {
|
|
80
|
+
snapshot: () => execFileSync("/bin/ps", ["-axo", "pid=,ppid="], {
|
|
81
|
+
encoding: "utf8",
|
|
82
|
+
timeout: 1000,
|
|
83
|
+
}),
|
|
84
|
+
kill: (identifier, signal) => process.kill(identifier, signal),
|
|
85
|
+
});
|
|
86
|
+
};
|
|
87
|
+
const cleanup = () => {
|
|
88
|
+
process.off("SIGINT", interrupt);
|
|
89
|
+
process.off("SIGTERM", terminate);
|
|
90
|
+
};
|
|
91
|
+
process.on("SIGINT", interrupt);
|
|
92
|
+
process.on("SIGTERM", terminate);
|
|
93
|
+
const child = spawnedHarness(request);
|
|
94
|
+
if (child === undefined) {
|
|
95
|
+
cleanup();
|
|
96
|
+
settle(null);
|
|
97
|
+
return;
|
|
98
|
+
}
|
|
99
|
+
child.once("error", () => {
|
|
100
|
+
cleanup();
|
|
101
|
+
settle(null);
|
|
102
|
+
});
|
|
103
|
+
child.once("close", (status, signal) => {
|
|
104
|
+
cleanup();
|
|
105
|
+
settle(status ?? (signal === null ? 1 : 128 + systemConstants.signals[signal]));
|
|
106
|
+
});
|
|
107
|
+
});
|
|
108
|
+
}
|
|
61
109
|
function startArguments(input) {
|
|
62
110
|
const { runtime, repository, argumentsList } = input;
|
|
63
111
|
const located = [
|
|
@@ -81,13 +129,6 @@ function startArguments(input) {
|
|
|
81
129
|
}
|
|
82
130
|
function toolProcess(input) {
|
|
83
131
|
const program = join(import.meta.dirname, "..", "tools", `${input.tool}${extname(import.meta.filename)}`);
|
|
84
|
-
const child = spawn(process.execPath, [program, ...input.argumentsList], {
|
|
85
|
-
stdio: "inherit",
|
|
86
|
-
env: {
|
|
87
|
-
...process.env,
|
|
88
|
-
PATH: [dirname(process.execPath), process.env["PATH"]].join(delimiter),
|
|
89
|
-
},
|
|
90
|
-
});
|
|
91
132
|
let stopping = false;
|
|
92
133
|
const interrupt = () => {
|
|
93
134
|
stopping = true;
|
|
@@ -99,11 +140,25 @@ function toolProcess(input) {
|
|
|
99
140
|
};
|
|
100
141
|
process.on("SIGINT", interrupt);
|
|
101
142
|
process.on("SIGTERM", terminate);
|
|
143
|
+
const child = spawn(process.execPath, [program, ...input.argumentsList], {
|
|
144
|
+
detached: input.tool === "red-green-command",
|
|
145
|
+
stdio: input.tool === "red-green-command"
|
|
146
|
+
? ["inherit", "inherit", "inherit", "ipc"]
|
|
147
|
+
: "inherit",
|
|
148
|
+
env: {
|
|
149
|
+
...process.env,
|
|
150
|
+
PATH: [dirname(process.execPath), process.env["PATH"]].join(delimiter),
|
|
151
|
+
},
|
|
152
|
+
});
|
|
102
153
|
return new Promise((settle) => {
|
|
103
154
|
child.once("close", (status) => {
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
155
|
+
setImmediate(() => {
|
|
156
|
+
setImmediate(() => {
|
|
157
|
+
process.off("SIGINT", interrupt);
|
|
158
|
+
process.off("SIGTERM", terminate);
|
|
159
|
+
settle(stopping && status === 75 ? 0 : (status ?? 1));
|
|
160
|
+
});
|
|
161
|
+
});
|
|
107
162
|
});
|
|
108
163
|
});
|
|
109
164
|
}
|
|
@@ -160,6 +215,11 @@ else if (command === "templates")
|
|
|
160
215
|
tool: "template-command",
|
|
161
216
|
argumentsList: options,
|
|
162
217
|
});
|
|
218
|
+
else if (command === "red-green")
|
|
219
|
+
process.exitCode = await toolProcess({
|
|
220
|
+
tool: "red-green-command",
|
|
221
|
+
argumentsList: options,
|
|
222
|
+
});
|
|
163
223
|
else if (command === "start")
|
|
164
224
|
process.exitCode = await start();
|
|
165
225
|
else {
|
|
@@ -174,6 +234,7 @@ else {
|
|
|
174
234
|
await main(process.argv.slice(2), {
|
|
175
235
|
repository,
|
|
176
236
|
environment,
|
|
237
|
+
startHarness,
|
|
177
238
|
doctorProbe: createProbeRunner({
|
|
178
239
|
spawn: (input) => spawn(input.executable, input.arguments, input.options),
|
|
179
240
|
kill: (identifier, signal) => process.kill(identifier, signal),
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { HandoffValue, CommandWaitRequest } from "./step-bridge.ts";
|
|
2
|
+
export type { CommandWaitRequest, CommandWaitOutcome, CommandWaitProgress, } from "./step-bridge.ts";
|
|
3
|
+
export declare function isCommandWaitRequest(value: unknown): value is CommandWaitRequest;
|
|
4
|
+
export declare function commandWaitValue(value: unknown, ancestors?: ReadonlySet<unknown>): value is HandoffValue;
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
export function isCommandWaitRequest(value) {
|
|
2
|
+
if (!dataFields(value, ["name", "input"]))
|
|
3
|
+
return false;
|
|
4
|
+
const name = Reflect.get(value, "name");
|
|
5
|
+
return (typeof name === "string" &&
|
|
6
|
+
name.length > 0 &&
|
|
7
|
+
commandWaitValue(Reflect.get(value, "input")));
|
|
8
|
+
}
|
|
9
|
+
function dataFields(value, keys) {
|
|
10
|
+
if (value === null || typeof value !== "object" || Array.isArray(value))
|
|
11
|
+
return false;
|
|
12
|
+
return (Reflect.ownKeys(value).length === keys.length &&
|
|
13
|
+
keys.every((key) => {
|
|
14
|
+
const field = Object.getOwnPropertyDescriptor(value, key);
|
|
15
|
+
return field?.enumerable === true && Object.hasOwn(field, "value");
|
|
16
|
+
}));
|
|
17
|
+
}
|
|
18
|
+
export function commandWaitValue(value, ancestors = new Set()) {
|
|
19
|
+
if (value === null || typeof value === "string" || typeof value === "boolean")
|
|
20
|
+
return true;
|
|
21
|
+
if (typeof value === "number")
|
|
22
|
+
return Number.isFinite(value);
|
|
23
|
+
if (typeof value !== "object" || ancestors.has(value))
|
|
24
|
+
return false;
|
|
25
|
+
return commandWaitObject(value, ancestors);
|
|
26
|
+
}
|
|
27
|
+
function commandWaitObject(value, ancestors) {
|
|
28
|
+
const prototype = Object.getPrototypeOf(value);
|
|
29
|
+
const expectedPrototype = Object.getPrototypeOf(Array.isArray(value) ? [] : {});
|
|
30
|
+
if (prototype !== expectedPrototype && prototype !== null)
|
|
31
|
+
return false;
|
|
32
|
+
const keys = Array.isArray(value)
|
|
33
|
+
? Array.from({ length: value.length }, (_, index) => String(index))
|
|
34
|
+
: Object.keys(value);
|
|
35
|
+
const ownKeys = Reflect.ownKeys(value).filter((key) => !Array.isArray(value) || key !== "length");
|
|
36
|
+
if (keys.length !== ownKeys.length)
|
|
37
|
+
return false;
|
|
38
|
+
const seen = new Set([...ancestors, value]);
|
|
39
|
+
return keys.every((key) => {
|
|
40
|
+
const field = Object.getOwnPropertyDescriptor(value, key);
|
|
41
|
+
return (field?.enumerable === true &&
|
|
42
|
+
Object.hasOwn(field, "value") &&
|
|
43
|
+
commandWaitValue(field.value, seen));
|
|
44
|
+
});
|
|
45
|
+
}
|
|
@@ -1,9 +1,16 @@
|
|
|
1
|
+
import { type Configuration } from "./configuration-schema.ts";
|
|
1
2
|
export interface SettingChange {
|
|
2
3
|
readonly field: string;
|
|
3
4
|
readonly action: "set" | "unset";
|
|
4
5
|
readonly value?: string;
|
|
5
6
|
readonly scope: "project" | "private";
|
|
6
7
|
}
|
|
8
|
+
export type HarnessSelection = Required<Pick<NonNullable<Configuration["harness"]>, "name" | "kind" | "path">>;
|
|
9
|
+
export interface HarnessChange {
|
|
10
|
+
readonly harness: HarnessSelection;
|
|
11
|
+
readonly scope: "private";
|
|
12
|
+
}
|
|
13
|
+
export declare function selectedHarnessConfiguration(contents: string | undefined, selection: HarnessSelection): string;
|
|
7
14
|
export type JsonValue = null | boolean | number | string | readonly JsonValue[] | {
|
|
8
15
|
readonly [name: string]: JsonValue;
|
|
9
16
|
};
|
|
@@ -1,6 +1,20 @@
|
|
|
1
1
|
import { configuration, settingScope, validateSetting, } from "./configuration-schema.js";
|
|
2
2
|
import { configurationValues, parseConfiguration } from "./project-settings.js";
|
|
3
3
|
import { record } from "./protocol.js";
|
|
4
|
+
export function selectedHarnessConfiguration(contents, selection) {
|
|
5
|
+
const previous = parseConfiguration(contents, "private");
|
|
6
|
+
const harness = previous.harness;
|
|
7
|
+
const same = harness?.name === selection.name &&
|
|
8
|
+
harness.kind === selection.kind &&
|
|
9
|
+
harness.path === selection.path;
|
|
10
|
+
const next = {
|
|
11
|
+
version: 1,
|
|
12
|
+
...previous,
|
|
13
|
+
harness: { ...(same ? harness : {}), ...selection },
|
|
14
|
+
};
|
|
15
|
+
configuration(next, "private");
|
|
16
|
+
return JSON.stringify(next, null, 2) + "\n";
|
|
17
|
+
}
|
|
4
18
|
function isJsonValue(value) {
|
|
5
19
|
if (value === null || typeof value === "boolean" || typeof value === "string")
|
|
6
20
|
return true;
|
|
@@ -1,10 +1,18 @@
|
|
|
1
1
|
import type { TurnProfiles } from "./turn-profile.ts";
|
|
2
2
|
import type { TokenPrices } from "./token-prices.ts";
|
|
3
|
+
export interface RedGreenSettings {
|
|
4
|
+
readonly test: readonly string[];
|
|
5
|
+
readonly testFiles: readonly string[];
|
|
6
|
+
readonly prepare?: readonly string[];
|
|
7
|
+
readonly assertionPattern?: string;
|
|
8
|
+
readonly skipPattern?: string;
|
|
9
|
+
}
|
|
3
10
|
export interface Configuration {
|
|
4
11
|
readonly version: 1;
|
|
5
12
|
readonly checks?: {
|
|
6
13
|
readonly beforeMerge?: readonly string[];
|
|
7
14
|
readonly required?: readonly string[];
|
|
15
|
+
readonly redGreen?: RedGreenSettings;
|
|
8
16
|
};
|
|
9
17
|
readonly tickets?: {
|
|
10
18
|
readonly command?: readonly string[];
|
|
@@ -13,6 +21,7 @@ export interface Configuration {
|
|
|
13
21
|
readonly queue?: {
|
|
14
22
|
readonly everySeconds?: number;
|
|
15
23
|
readonly lanes?: number;
|
|
24
|
+
readonly dailySpendLimitUsd?: number;
|
|
16
25
|
};
|
|
17
26
|
readonly harness?: {
|
|
18
27
|
readonly name?: string;
|
|
@@ -42,6 +51,11 @@ export interface Configuration {
|
|
|
42
51
|
readonly workflows?: {
|
|
43
52
|
readonly folder?: string;
|
|
44
53
|
};
|
|
54
|
+
readonly retention?: {
|
|
55
|
+
readonly days?: number | null;
|
|
56
|
+
readonly action?: "archive" | "delete";
|
|
57
|
+
readonly archiveFolder?: string | null;
|
|
58
|
+
};
|
|
45
59
|
}
|
|
46
60
|
export declare function configuration(value: unknown, scope: "project" | "private"): Configuration;
|
|
47
61
|
export declare function settingScope(field: string): "project" | "private";
|
|
@@ -88,12 +88,16 @@ function validate(value, checked) {
|
|
|
88
88
|
scalar(value, checked);
|
|
89
89
|
if (schema.type === "object")
|
|
90
90
|
validateObject(value, checked);
|
|
91
|
-
if (schema.type
|
|
92
|
-
|
|
91
|
+
if (schema.type === "array")
|
|
92
|
+
validateArray(value, checked);
|
|
93
|
+
}
|
|
94
|
+
function validateArray(value, { schema, field }) {
|
|
93
95
|
if (!Array.isArray(value))
|
|
94
96
|
invalid(field);
|
|
95
97
|
if (schema.maxItems !== undefined && value.length > schema.maxItems)
|
|
96
98
|
invalid(field);
|
|
99
|
+
if (schema.minItems !== undefined && value.length < schema.minItems)
|
|
100
|
+
invalid(field);
|
|
97
101
|
if (schema.items === undefined)
|
|
98
102
|
return;
|
|
99
103
|
for (const [index, item] of value.entries())
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import { type FileHandle } from "node:fs/promises";
|
|
2
|
+
export declare function openedAttachment(place: {
|
|
3
|
+
readonly folder: string;
|
|
4
|
+
readonly name: string;
|
|
5
|
+
}): Promise<FileHandle>;
|
|
6
|
+
export declare function copiedAttachment(handle: FileHandle, copy: string): Promise<void>;
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
import { constants } from "node:fs";
|
|
2
|
+
import { lstat, open, rm } from "node:fs/promises";
|
|
3
|
+
import { dirname, join } from "node:path";
|
|
4
|
+
const maximumBytes = 104_857_600;
|
|
5
|
+
const chunkBytes = 1_048_576;
|
|
6
|
+
const pngSignature = Buffer.from([
|
|
7
|
+
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a,
|
|
8
|
+
]);
|
|
9
|
+
const webmSignature = Buffer.from([0x1a, 0x45, 0xdf, 0xa3]);
|
|
10
|
+
const signatures = new Map([
|
|
11
|
+
["mp4", (head) => head.subarray(4, 8).toString("latin1") === "ftyp"],
|
|
12
|
+
["webm", (head) => head.subarray(0, 4).equals(webmSignature)],
|
|
13
|
+
["png", (head) => head.subarray(0, 8).equals(pngSignature)],
|
|
14
|
+
]);
|
|
15
|
+
function listedStatus(path) {
|
|
16
|
+
return lstat(path).catch(() => undefined);
|
|
17
|
+
}
|
|
18
|
+
async function realFolder(path) {
|
|
19
|
+
const status = await listedStatus(path);
|
|
20
|
+
return (status !== undefined && status.isDirectory() && !status.isSymbolicLink());
|
|
21
|
+
}
|
|
22
|
+
async function realFolders(folder) {
|
|
23
|
+
return (await realFolder(dirname(folder))) && (await realFolder(folder));
|
|
24
|
+
}
|
|
25
|
+
function sameFile(opened, listed) {
|
|
26
|
+
return (listed !== undefined &&
|
|
27
|
+
listed.isFile() &&
|
|
28
|
+
listed.ino === opened.ino &&
|
|
29
|
+
listed.dev === opened.dev);
|
|
30
|
+
}
|
|
31
|
+
async function signed(handle, name) {
|
|
32
|
+
const head = Buffer.alloc(8);
|
|
33
|
+
const { bytesRead } = await handle.read(head, 0, 8, 0);
|
|
34
|
+
const check = signatures.get(name.slice(name.lastIndexOf(".") + 1));
|
|
35
|
+
return bytesRead === 8 && check !== undefined && check(head);
|
|
36
|
+
}
|
|
37
|
+
async function checkedHandle(handle, place) {
|
|
38
|
+
const opened = await handle.stat();
|
|
39
|
+
const listed = await listedStatus(join(place.folder, place.name));
|
|
40
|
+
if (!opened.isFile() || opened.nlink !== 1 || !sameFile(opened, listed))
|
|
41
|
+
throw new Error("attachment-not-available");
|
|
42
|
+
if (!(await realFolders(place.folder)))
|
|
43
|
+
throw new Error("attachment-not-available");
|
|
44
|
+
if (opened.size > maximumBytes)
|
|
45
|
+
throw new Error("attachment-too-large");
|
|
46
|
+
if (!(await signed(handle, place.name)))
|
|
47
|
+
throw new Error("attachment-not-available");
|
|
48
|
+
}
|
|
49
|
+
export async function openedAttachment(place) {
|
|
50
|
+
if (!(await realFolders(place.folder)))
|
|
51
|
+
throw new Error("attachment-not-available");
|
|
52
|
+
const handle = await open(join(place.folder, place.name), constants.O_RDONLY | constants.O_NOFOLLOW | constants.O_NONBLOCK).catch(() => undefined);
|
|
53
|
+
if (handle === undefined)
|
|
54
|
+
throw new Error("attachment-not-available");
|
|
55
|
+
try {
|
|
56
|
+
await checkedHandle(handle, place);
|
|
57
|
+
return handle;
|
|
58
|
+
}
|
|
59
|
+
catch (error) {
|
|
60
|
+
await handle.close();
|
|
61
|
+
throw error;
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
async function copiedChunks(source, target) {
|
|
65
|
+
const chunk = Buffer.alloc(chunkBytes);
|
|
66
|
+
let position = 0;
|
|
67
|
+
for (;;) {
|
|
68
|
+
const { bytesRead } = await source.read(chunk, 0, chunkBytes, position);
|
|
69
|
+
if (bytesRead === 0)
|
|
70
|
+
return;
|
|
71
|
+
position += bytesRead;
|
|
72
|
+
if (position > maximumBytes)
|
|
73
|
+
throw new Error("attachment-too-large");
|
|
74
|
+
await target.write(chunk, 0, bytesRead);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
export async function copiedAttachment(handle, copy) {
|
|
78
|
+
await rm(copy, { force: true });
|
|
79
|
+
const target = await open(copy, "wx");
|
|
80
|
+
try {
|
|
81
|
+
await copiedChunks(handle, target);
|
|
82
|
+
}
|
|
83
|
+
finally {
|
|
84
|
+
await target.close();
|
|
85
|
+
}
|
|
86
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export declare function attachmentFolder(place: {
|
|
2
|
+
readonly worktrees: string;
|
|
3
|
+
readonly target: string;
|
|
4
|
+
}): string;
|
|
5
|
+
export declare function attachmentEnvironment(settings: {
|
|
6
|
+
readonly worktrees: string;
|
|
7
|
+
}, start: {
|
|
8
|
+
readonly intent: {
|
|
9
|
+
readonly target: string;
|
|
10
|
+
};
|
|
11
|
+
readonly profile: {
|
|
12
|
+
readonly env?: Readonly<Record<string, string>>;
|
|
13
|
+
};
|
|
14
|
+
}): Promise<Readonly<Record<string, string>>>;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { mkdir } from "node:fs/promises";
|
|
2
|
+
import { dirname, join } from "node:path";
|
|
3
|
+
import { treeName } from "./work-tree.js";
|
|
4
|
+
export function attachmentFolder(place) {
|
|
5
|
+
return join(dirname(place.worktrees), "attachments", treeName(place.target));
|
|
6
|
+
}
|
|
7
|
+
export async function attachmentEnvironment(settings, start) {
|
|
8
|
+
const attachments = attachmentFolder({
|
|
9
|
+
worktrees: settings.worktrees,
|
|
10
|
+
target: start.intent.target,
|
|
11
|
+
});
|
|
12
|
+
await mkdir(attachments, { recursive: true });
|
|
13
|
+
return {
|
|
14
|
+
...(start.profile.env ?? {}),
|
|
15
|
+
CLOVING_ATTACHMENTS_DIRECTORY: attachments,
|
|
16
|
+
};
|
|
17
|
+
}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import type { TurnEnd } from "./claude-turn.ts";
|
|
2
|
+
import { type Located, type WorkerReport } from "./operation-journal.ts";
|
|
3
|
+
import type { WorkTree } from "./work-tree.ts";
|
|
4
|
+
import { type WorkerProfiles } from "./worker-profile.ts";
|
|
5
|
+
import type { AdapterOutcome, DeliveryIntent, ProtectedIntent } from "../broker/actor/delivery-intents.ts";
|
|
6
|
+
export interface TurnResume {
|
|
7
|
+
readonly startedAt: string;
|
|
8
|
+
readonly turnStartCommit: string | null;
|
|
9
|
+
readonly sessionId: string;
|
|
10
|
+
readonly ends: readonly TurnEnd[];
|
|
11
|
+
}
|
|
12
|
+
export declare const resumePrompt = "This turn stopped because the Cloving daemon restarted. Continue the task from the point where it stopped. Run again each command or subagent that did not end. End with the result line that the task asks for.";
|
|
13
|
+
export declare function turnIntent(intent: DeliveryIntent): intent is ProtectedIntent;
|
|
14
|
+
export declare function resumableHarness(harness: unknown): boolean;
|
|
15
|
+
export declare function resumedCommand(request: {
|
|
16
|
+
readonly worker: string | undefined;
|
|
17
|
+
readonly command: readonly string[];
|
|
18
|
+
readonly sessionId: string;
|
|
19
|
+
}): readonly string[] | undefined;
|
|
20
|
+
export declare function recordedField(value: unknown, name: string): unknown;
|
|
21
|
+
export declare function processAlive(processId: unknown): boolean;
|
|
22
|
+
export declare function uncertainProcess(started: unknown): Promise<boolean>;
|
|
23
|
+
export declare function recordedTree(started: unknown): WorkTree | undefined;
|
|
24
|
+
export declare function resumePlan(settings: WorkerProfiles & {
|
|
25
|
+
readonly stopMilliseconds?: number;
|
|
26
|
+
}, request: {
|
|
27
|
+
readonly folder: string;
|
|
28
|
+
readonly started: unknown;
|
|
29
|
+
readonly intent: ProtectedIntent;
|
|
30
|
+
readonly signal: AbortSignal;
|
|
31
|
+
}): Promise<"worktree-index-unknown" | "worktree-index-locked" | "claude-turn-interrupted" | {
|
|
32
|
+
resume: TurnResume;
|
|
33
|
+
tree: WorkTree;
|
|
34
|
+
profile: import("../turn-profile.ts").TurnProfile;
|
|
35
|
+
harness: {
|
|
36
|
+
readonly worker: string;
|
|
37
|
+
readonly command: readonly string[];
|
|
38
|
+
readonly shell?: string;
|
|
39
|
+
readonly output?: "text";
|
|
40
|
+
};
|
|
41
|
+
}>;
|
|
42
|
+
export declare function readResume(folder: string, started: unknown): Promise<TurnResume | undefined>;
|
|
43
|
+
export declare function recordedHarness(journal: string, operationId: string): Promise<string | undefined>;
|
|
44
|
+
export declare function interruptedReply(place: Located, reason: string): Promise<AdapterOutcome>;
|
|
45
|
+
export declare function recoverTurn(operation: {
|
|
46
|
+
readonly intent: ProtectedIntent;
|
|
47
|
+
readonly journal: string;
|
|
48
|
+
readonly report: (report: WorkerReport) => Promise<unknown>;
|
|
49
|
+
readonly signal: AbortSignal;
|
|
50
|
+
}, reconcile: () => Promise<AdapterOutcome>): Promise<void>;
|