Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
75b9cb8
test: add RED durable retry cancellation regressions
tim8es Aug 29, 2026
a5957d8
chore: add one-time durable retry cancellation patcher
tim8es Aug 29, 2026
3804cf1
chore: add one-time durable retry cancellation green workflow
tim8es Aug 29, 2026
c86bbb2
feat: add durable retry cancellation
github-actions[bot] Aug 29, 2026
68f97ce
test: add one-time retry cancellation review hardening patcher
tim8es Aug 29, 2026
84b950a
test: strengthen retry cancellation race regressions
tim8es Aug 30, 2026
3148ee9
chore: add one-time retry cancellation review test workflow
tim8es Aug 30, 2026
05e8026
test: harden durable retry cancellation races
github-actions[bot] Aug 30, 2026
6ed5504
test: prepare deterministic cancel goal race regression
tim8es Aug 30, 2026
9386d6d
chore: add one-time cancel goal race regression workflow
tim8es Aug 30, 2026
9318feb
test: make cancel goal race regression deterministic
github-actions[bot] Aug 30, 2026
7e10490
test: prepare database-local cancel goal race
tim8es Aug 30, 2026
434dda6
chore: add one-time database-local cancel goal race workflow
tim8es Aug 30, 2026
00dde3b
test: make cancel goal race database-local
github-actions[bot] Aug 30, 2026
3f85fd3
test: prepare clean independent cancel race harness
tim8es Aug 30, 2026
cf6f38d
chore: add one-time clean cancel race harness workflow
tim8es Aug 30, 2026
b19b435
test: clean cancel goal race harness
github-actions[bot] Aug 30, 2026
f1411fd
test: prepare stale goal create task red
tim8es Aug 30, 2026
14904ba
chore: add one-time stale goal create task red workflow
tim8es Aug 30, 2026
cdaaf85
test: cover stale Goal CreateTask race
github-actions[bot] Aug 30, 2026
43b300a
feat: add D1 mutation batch guards
tim8es Aug 30, 2026
94426a6
feat: prepare D1 transaction guard fix
tim8es Aug 30, 2026
837d997
chore: add one-time D1 transaction guard workflow
tim8es Aug 30, 2026
6c19118
fix: make mutation guard migration repeatable
tim8es Aug 30, 2026
4603519
chore: rerun D1 transaction guard workflow
tim8es Aug 30, 2026
b8753b4
chore: retrigger D1 transaction guard workflow
tim8es Aug 30, 2026
fc0cf3e
chore: add final D1 transaction guard workflow
tim8es Aug 30, 2026
2a74dd1
fix: make durable lifecycle races transactional
github-actions[bot] Aug 30, 2026
9893b6e
test: prepare cancellation claim race regressions
tim8es Aug 30, 2026
b3b0dd9
chore: add one-time cancellation claim race RED workflow
tim8es Aug 30, 2026
7730c0b
test: cover cancellation recovery claim races
github-actions[bot] Aug 30, 2026
9e82a70
fix: prepare cancellation claim linearization
tim8es Aug 30, 2026
7eedfe7
chore: add one-time cancellation claim linearization workflow
tim8es Aug 30, 2026
2165860
fix: serialize cancellation with recovery claims
github-actions[bot] Aug 30, 2026
e15ae5a
docs: prepare retry cancellation reconciliation
tim8es Aug 30, 2026
e2e5cba
chore: add one-time retry cancellation docs workflow
tim8es Aug 30, 2026
681a5e6
docs: reconcile durable retry cancellation
github-actions[bot] Aug 30, 2026
a8a022e
chore: trigger final quality gate
tim8es Aug 30, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ The project is in `0.x` development and does not yet have a public product relea
- HTTP/application end-to-end regression covering `RegisterAgent -> StartSession -> CreateGoal -> CreateTask -> ClaimTask -> RecordCheckpoint -> RequestPermission(repository.write) -> RecordPermissionDecision(ALLOW) -> CompleteTask`, followed by HTTP verification of final Task, Goal, Lease, and checkpoint state.
- Durable HTTP end-to-end regressions covering restart after claim, restart after `HUMAN_REQUIRED`, response-loss receipt replay after application replacement, competing independent application claims, and fencing advancement after Lease expiry/recovery against the SQLite D1-like persistence harness.
- Durable `FailTask`, `BlockTask`, and `ResumeTask` composition with atomic Task/Lease/Checkpoint/receipt persistence where applicable, restart-safe immutable replay, persisted blocked/failed evidence, controller-authorized resume, and D1-like fault-injection rollback coverage.
- Durable `RetryTask`, `CancelTask`, and `CancelGoal` composition with restart-safe receipts, controller authority, task-only cancellation when no effective Lease exists, atomic Goal/Task/Lease cancellation, and database-level concurrency guards against stale Goal admission and recovery-claim races.

### Changed

Expand All @@ -58,6 +59,7 @@ The project is in `0.x` development and does not yet have a public product relea
- Admitted terminal semantic failures in the supported durable command loop now persist immutable `outcomeKind: error` command receipts and replay after restart instead of re-executing the command.
- Durable Session/Lease liveness composition now supports `HeartbeatSession`, `EndSession`, `RenewLease`, and `ReleaseLease` with atomic mutation receipts, restart-safe replay, stable renewal fencing, and recoverable released/revoked execution authority.
- Durable task-outcome persistence now revalidates execution/revision authority at commit time and stores failure/block transitions and their released Lease plus Checkpoint in one batch; `ResumeTask` recomputes dependency readiness and removes the blocking reason without granting a Lease.
- D1 mutation batches now use transaction-aborting guard rows for conditional mutation races. Task creation/retry revalidate an active parent Goal inside the database batch; Goal cancellation terminalizes the Goal only after its cancellable Tasks/Leases and only when no cancellable work remains; claim/cancellation share fencing-counter and Task-state predicates so neither can return success with execution authority beneath cancelled state.

### Verification

Expand All @@ -76,14 +78,15 @@ The project is in `0.x` development and does not yet have a public product relea
- Permanent Quality run `33274903333` passed the restart-safe durable HTTP E2E tree with **29/29 test files and 123/123 tests**, plus `pnpm test:coverage`. Overall coverage reported 85.3% statements, 73.3% branches, 96.15% functions, and 86.95% lines.
- Final correctness-review RED run `33275182068` failed exactly the two new terminal-error-receipt and recovery-discovery regressions while the previous 123 tests passed. Review-fix run `33275312677` then passed focused regressions, full `pnpm check`, and coverage with **30/30 test files and 125/125 tests**; overall coverage was 85.43% statements, 73.5% branches, 96.18% functions, and 87.07% lines.
- Durable task-outcome RED run `33278105807` preserved the previous 130 passing tests while the new FailTask/BlockTask regressions failed at the expected unsupported boundary. Review/atomicity run `33278493339` passed **32/32 test files and 133/133 tests**, plus coverage at 84.99% statements, 74.15% branches, 96.36% functions, and 86.73% lines, including a forced mid-batch rollback followed by successful exact retry.
- Durable retry/cancellation hardening run `33283962742` passed **33/33 test files and 143/143 tests**, full `pnpm check`, and coverage at 85.0% statements, 74.3% branches, 96.51% functions, and 86.71% lines after transaction-CAS, stale Goal admission, no-Lease cancellation, mid-batch rollback, false-receipt, and cancellation-versus-recovery claim regressions were made green.
- Frozen installation resolves `@mindrail/contracts 0.0.0 <- packages/contracts`, confirming the root runtime uses the workspace contract package.
- No new third-party runtime dependency was introduced for schema admission, protocol admission, bootstrap, transport, permission, persistence composition, rehydration, or durable query semantics.

### Known limitations

- `Quality` is not yet enforced as a required `main` merge gate; repository protection remains tracked separately in issue #3.
- The durable application composition is verified against the local SQLite D1-like test harness, not a deployed Cloudflare Worker/Durable Object/D1 environment.
- The durable dispatcher currently supports `RegisterAgent`, `StartSession`, `HeartbeatSession`, `EndSession`, `CreateGoal`, `CreateTask`, `ClaimTask`, `RenewLease`, `ReleaseLease`, `RecordCheckpoint`, `RequestPermission`, `RecordPermissionDecision`, `CompleteTask`, `FailTask`, `BlockTask`, and `ResumeTask`. `RetryTask`, `CancelTask`, and `CancelGoal` remain canonical runtime behavior but are explicitly unsupported by the durable composition until matching atomic persistence paths are added.
- The durable dispatcher supports the complete ADR-0005 v0.1 command surface. The remaining explicit durable application gaps are read-side: `ListGoals`, `ListGoalTasks`, and `GetTaskExecutionView`.
- Durable application queries `ListGoals`, `ListGoalTasks`, and `GetTaskExecutionView` remain explicitly unsupported.
- MindRail does not yet expose a verified deployed Cloudflare control-plane service, GitHub adapter, real Codex/ChatGPT integration, or unattended continuation of a real external agent across host/platform termination.
- The deterministic v0.1 permission policy is intentionally small and is not an IAM system, credential manager, arbitrary policy DSL, or model-based authority mechanism.
Expand Down
9 changes: 4 additions & 5 deletions docs/CURRENT_STATE.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,9 +27,9 @@ The following facts are supported by repository state and executed GitHub Action
- `ClaimTask` uses a deferred receipt snapshot so the returned/stored result is built only after the persistence layer allocates the authoritative fencing token. Executed regression coverage proves a replay returns the persisted Lease/fence rather than a speculative runtime token.
- `InMemoryControlPlane.rehydrate()` restores canonical Workspace/Goal/Task/Agent/Session/Lease/checkpoint/permission state plus durable per-Task fencing counters from a persistence snapshot. Rehydration validates record relationships, reconstructs effective Lease authority from canonical records and authoritative time, and fails closed on inconsistent state.
- `createDurableApplicationDispatcher(...)` composes the canonical runtime semantics with `DurableRuntimePersistence`. Each supported command loads authoritative durable state, rehydrates an ephemeral runtime, executes the existing semantics, and commits through explicit persistence methods. The dispatcher does not retain an in-memory fallback between requests.
- The durable command loop is executable for `RegisterAgent`, `StartSession`, `HeartbeatSession`, `EndSession`, `CreateGoal`, `CreateTask`, `ClaimTask`, `RenewLease`, `ReleaseLease`, `RecordCheckpoint`, `RequestPermission`, `RecordPermissionDecision`, `CompleteTask`, `FailTask`, `BlockTask`, and `ResumeTask`.
- The durable command loop is executable for the complete ADR-0005 v0.1 command surface: `RegisterAgent`, `StartSession`, `HeartbeatSession`, `EndSession`, `CreateGoal`, `CreateTask`, `ClaimTask`, `RenewLease`, `ReleaseLease`, `RecordCheckpoint`, `RequestPermission`, `RecordPermissionDecision`, `CompleteTask`, `FailTask`, `BlockTask`, `ResumeTask`, `RetryTask`, `CancelTask`, and `CancelGoal`.
- Durable Session/Lease liveness preserves the runtime authority model: heartbeat advances only Session liveness/revision, Lease renewal keeps the fencing token stable, release leaves the Task running/recoverable, and ending a Session revokes its still-effective active Leases without completing the Task.
- Durable task outcomes now preserve the same runtime semantics through persistence: `FailTask` and `BlockTask` atomically commit the Task transition, released Lease, terminal/blocked Checkpoint, and immutable command receipt; `ResumeTask` atomically commits the controller-authorized blocked-to-ready/pending Task transition and receipt without minting execution authority.
- Durable task outcomes now preserve the same runtime semantics through persistence: `FailTask` and `BlockTask` atomically commit the Task transition, released Lease, terminal/blocked Checkpoint, and immutable command receipt; `ResumeTask` atomically commits the controller-authorized blocked-to-ready/pending Task transition and receipt without minting execution authority. `RetryTask`, `CancelTask`, and `CancelGoal` also commit through explicit durable mutations with controller authority, immutable receipts, Goal/Task/Lease revision checks, database-enforced Goal-versus-Task admission ordering, and fencing-counter guards that prevent recovery claims from surviving cancellation races.
- Durable command replay first reads the persisted `(workspaceId, commandId)` receipt. Exact retries survive application/database-handle replacement, return `replayed: true`, preserve the immutable stored result/error snapshot, and reflect the current correlation id. Semantic command-id drift fails with `IDEMPOTENCY_CONFLICT`.
- Admitted terminal semantic failures on the supported durable command loop are also persisted as immutable error receipts, so an exact retry after restart replays the original terminal error instead of silently re-executing the command.
- Explicit durable read ports and application queries are implemented for `GetWorkspace`, `GetGoal`, `GetTask`, `GetLease`, `GetAgent`, `GetSession`, `GetPermissionRequest`, `ListTaskCheckpoints`, `ListPendingHumanPermissions`, `ListPermissionDecisions`, and advisory `ListClaimableTasks`. List queries use bounded deterministic cursor paging. `ListClaimableTasks` includes capability-compatible `ready` Tasks plus `running` Tasks whose prior Lease/Session authority is no longer effective at the authoritative server time; work acquisition still revalidates authority atomically at `ClaimTask`.
Expand All @@ -40,22 +40,21 @@ The following facts are supported by repository state and executed GitHub Action
- Permanent `Quality` run `33274903333` on the durable HTTP E2E tree passed formatting, lint, strict TypeScript, generated-contract drift checks, **29/29 test files and 123/123 tests**, and coverage. Reported overall coverage was 85.3% statements, 73.3% branches, 96.15% functions, and 86.95% lines.
- Final correctness review RED run `33275182068` demonstrated both remaining defects: the two new regressions failed because terminal semantic errors had no durable receipt and recovery work discovery omitted a `running` Task after its effective Lease expired, while the previous **123 tests passed**. Review-fix run `33275312677` then passed focused regressions, full `pnpm check`, and coverage with **30/30 test files and 125/125 tests**. Overall coverage was 85.43% statements, 73.5% branches, 96.18% functions, and 87.07% lines.
- Durable Session/Lease liveness RED Quality run `33276800987` passed formatting/lint/typecheck/contracts and the previous **125 tests**, while all four new HTTP E2E regressions failed exactly because `HeartbeatSession`, `EndSession`, `RenewLease`, and `ReleaseLease` returned `UNSUPPORTED_OPERATION`. GREEN run `33276973691` then passed the focused 4/4 liveness E2E tests, full `pnpm check` with **31/31 test files and 129/129 tests**, and coverage at 85.19% statements, 73.88% branches, 96.3% functions, and 86.83% lines.
- Durable task-outcome RED Quality run `33278105807` kept the previous **130 tests green** while both new outcome regressions failed on the expected `UNSUPPORTED_OPERATION` boundary. GREEN run `33278271723` passed full `pnpm check` and coverage after self-cleaning the one-time implementation harness. Review-hardening run `33278367867` then proved persisted FailTask Lease state, lost-response BlockTask replay, durable blocked Checkpoint storage, and complete persisted ResumeTask state. Atomicity run `33278493339` added D1-like mid-batch fault injection and passed **32/32 test files and 133/133 tests** plus coverage at 84.99% statements, 74.15% branches, 96.36% functions, and 86.73% lines; the injected failure rolls back Checkpoint, Task, Lease, and receipt together before an exact retry succeeds.
- Durable task-outcome RED Quality run `33278105807` kept the previous **130 tests green** while both new outcome regressions failed on the expected `UNSUPPORTED_OPERATION` boundary. GREEN run `33278271723` passed full `pnpm check` and coverage after self-cleaning the one-time implementation harness. Review-hardening run `33278367867` then proved persisted FailTask Lease state, lost-response BlockTask replay, durable blocked Checkpoint storage, and complete persisted ResumeTask state. Atomicity run `33278493339` added D1-like mid-batch fault injection and passed **32/32 test files and 133/133 tests** plus coverage at 84.99% statements, 74.15% branches, 96.36% functions, and 86.73% lines; the injected failure rolls back Checkpoint, Task, Lease, and receipt together before an exact retry succeeds. Durable retry/cancellation review hardening culminated in run `33283962742`, which passed **33/33 test files and 143/143 tests**, full `pnpm check`, and coverage at 85.0% statements, 74.3% branches, 96.51% functions, and 86.71% lines. The regressions cover lost-response replay, `CancelTask` without an effective Lease, `CancelGoal` mid-batch rollback, stale Goal task admission, false-success receipt prevention after a lost CAS, and recovery-`ClaimTask` races against both Task and Goal cancellation.
- Runtime Surface PR #20 merged with post-merge Quality PASS. Persistence PR #24 merged with post-merge Quality #248 PASS. HTTP/MCP Transport PR #25 merged at `e142c1399aed5de3d8df53ad876499583728a6b4`; permanent Quality #249 and post-merge Quality #250 both passed full quality and coverage gates.
- Permanent `Quality` CI remains least-privilege and uses pinned GitHub-owned action commits.

## Implemented but not yet fully deployed / externally integrated

- The durable application composition is verified locally against the SQLite D1-like harness used by persistence tests. This is executable restart/concurrency evidence for the application/persistence contract, but it is **not** evidence of a deployed Cloudflare Worker, Durable Object, or production D1 environment.
- The durable dispatcher still leaves `RetryTask`, `CancelTask`, and `CancelGoal` explicitly unsupported until matching atomic persistence mutations are added.
- Durable queries `ListGoals`, `ListGoalTasks`, and `GetTaskExecutionView` remain explicitly unsupported rather than inferred from retained application state.
- No deployed Cloudflare Worker/Durable Object service is claimed. Deployment configuration, environment provisioning, deployed-runtime restart verification, and real Cloudflare concurrency verification remain outstanding.
- The v0.1 permission policy is intentionally small, explicit, hard-coded, and versioned. It is not a policy DSL, IAM system, credential manager, model judge, or arbitrary-code policy runtime.
- `Quality` is executable on pull requests and `main`, but issue #3 still tracks repository-level enforcement as a required merge gate.

## Next implementation slices

- Complete durable persistence mutations for the remaining v0.1 lifecycle/cancellation commands without introducing a second state machine or generic CRUD authority.
- Audit and harden any remaining conditional durable mutations against the same database-CAS/receipt and Goal-level concurrency invariants before treating the local persistence composition as complete.
- Add the remaining bounded durable queries only where required by agent/human workflows.
- Add GitHub integration while keeping GitHub as an adapter/projection rather than canonical state authority.
- Add minimal real Codex, ChatGPT-compatible, generic MCP, and generic HTTP agent bootstrap/worker paths on top of the stable protocol/application boundary.
Expand Down
Loading