Files
suaveplan/openspec/archive/2026-05-25-api-host/tasks.md
2026-05-27 23:29:53 +01:00

88 lines
5.8 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Tasks — `@suaveplan/api-host`
> Every checkbox MUST reflect work actually done in this change.
## 0. Pre-flight (non-negotiable)
- [x] 0.1 Confirm clean working tree (`git status` reports nothing) and no in-flight worktrees with uncommitted work
- [x] 0.2 Worktrees under `.claude/worktrees/` accounted for (agent-A/B/C all merged; agent-D = this change)
- [x] 0.3 `MANIFEST.md` matches package count
## 1. Spec authoring
- [x] 1.1 Read design doc `docs/superpowers/specs/2026-05-13-api-plugin-foundation-design.md` (§2.2, §4, §5, §6, §8, §12)
- [x] 1.2 Read umbrella `openspec/changes/api-plugin-foundation/proposal.md`
- [x] 1.3 Read `openspec/AGENTS.md` Sections 13 and 14
- [x] 1.4 Draft `proposal.md` from `openspec/templates/proposal.md`
- [x] 1.5 Draft `specs/api-host/spec.md` from `openspec/templates/spec-delta.md`
- [x] 1.6 Every requirement in the spec delta carries a `**Verified by:**` line naming concrete `it(...)` titles
## 2. Implementation
- [x] 2.1 Scaffold `packages/api-stack/api/api-host/` (Chunk A)
- [x] 2.2 `src/define-plugin/` — `definePlugin<Caps>(spec)` (Chunk A)
- [x] 2.3 `src/capability-registry/` (Chunk A)
- [x] 2.4 `src/lifecycle/` — `LifecycleDriver` (Chunk B)
- [x] 2.5 `src/hot-reload/` — `ReloadDriver` (Chunk B)
- [x] 2.6 `src/hot-reload/rollback-journal` via `@suaveplan/api-loader` (Chunk B)
- [x] 2.7 `src/plugin-ledger/` — `PluginLedger` + `HostMigrationRunner` (Chunk C)
- [x] 2.8 `src/admin-api/` — Hono sub-router; every §8.4 endpoint (Chunk C)
- [x] 2.9 `src/error-boundary/` — wraps every pipeline step; `SuaveplanError → statusMap`; `AbortError → 499`; default → 500 + log cause; envelope per `api-types/errors` (Chunk D)
- [x] 2.10 `src/request-pipeline/` — steps 1–11 from §6 in order; CSRF on cookie auth (non-GET/HEAD); streaming bypass; response-validation enforce/warn (Chunk D)
- [x] 2.11 `src/otel/` — `HostInstruments` (Chunk A); request-pipeline emits §12.3 metrics (Chunk D)
- [x] 2.12 `src/host/` — `createHost(config)`; `start()` / `stop()` / `fetch()`; `/internal/livez` + `/internal/readyz` (Chunk D)
- [x] 2.13 `src/error-codes/` — every `HOST_*` / `PLUGIN_*` / `RELOAD_*` / `CAPABILITY_*` / `ADMIN_*` / `LEDGER_*` code, plus Chunk D additions (`TENANT_NOT_RESOLVED`, `SESSION_REQUIRED`, `CSRF_TOKEN_INVALID`, `RBAC_DENIED`, `RATE_LIMIT_EXCEEDED`, `REQUEST_VALIDATION_FAILED`, `RESPONSE_VALIDATION_FAILED`, `IDEMPOTENCY_REPLAY`, `ROUTE_NOT_FOUND`, `HANDLER_THREW`, `CLIENT_ABORTED`)
- [x] 2.14 `src/testing/` — RESERVED placeholder (Chunk A)
- [x] 2.15 `src/index.ts` — explicit named re-exports per rule 10
- [x] 2.16 `package.json` `exports` — every subpath including `./error-boundary`, `./request-pipeline`, `./host`
## 3. Tests
- [x] 3.1 lifecycle (Chunk B)
- [x] 3.2 lifecycle-coverage (Chunk B)
- [x] 3.3 hot-reload (Chunk B)
- [x] 3.4 hot-reload-coverage (Chunk B)
- [x] 3.5 file-watcher (Chunk B)
- [x] 3.6 capability-registry (Chunk A)
- [x] 3.7 plugin-ledger (Chunk C)
- [x] 3.8 admin-api (Chunk C)
- [x] 3.9 admin-api disabled — covered in `src/host/host.test.ts::"adminPrefix: null disables admin surface"`
- [x] 3.10 `src/error-boundary/error-boundary.test.ts` — 18 tests covering manifest statusMap, default fallback, AbortError, ABORT_ERR variant, unknown throw, span recording, log cause chain, depth truncation (Chunk D)
- [x] 3.11 `src/request-pipeline/request-pipeline.test.ts` — 36 tests covering every §6 step in order, CSRF gating cookie auth, streaming bypass, idempotency replay, request/response Zod, handler throw, audit (Chunk D)
- [x] 3.12 response-validation enforce/warn covered in `request-pipeline.test.ts::"response Zod mismatch in enforce mode → 500"` and `"response Zod mismatch in warn mode → success"`
- [x] 3.13 otel (Chunk A) — every §12.3 counter exercised through the request-pipeline tests
- [x] 3.14 define-plugin generics (Chunk A)
- [x] 3.15 `src/host/host.test.ts` — empty host boots; `/internal/livez` → 200; `/internal/readyz` → 200 (Chunk D)
- [x] 3.16 Every `it(...)` carries `{ timeout: 5000 }`
## 4. Documentation
- [x] 4.1 Sibling `.md` for every implementation `.ts` (≥200 words, basic + advanced examples, full API reference)
- [x] 4.2 `README.md` updates in Chunks A/B/C; Chunk D adds `error-boundary`, `request-pipeline`, `host` modules
- [x] 4.3 CLAUDE.md package listing updated when shipped
## 5. Pre-archive verification (the 5-gate triple)
- [x] 5.1 `bunx biome check src/` — clean
- [x] 5.2 `bunx turbo lint typecheck test --filter=@suaveplan/api-host` — green (245 pass / 0 fail / 583 expect)
- [x] 5.3 `bun test --coverage` — 100% line coverage on every Chunk D module + every other src/ module
- [x] 5.4 `bunx turbo build --filter=@suaveplan/api-host` — green
- [x] 5.5 No `// biome-ignore` / `// @ts-ignore` introduced
## 6. Pre-archive 7-row checklist (AGENTS.md Section 13)
- [x] 6.1 Generics threaded — `definePlugin<Caps>`, `RequestContext<Caps>` flow into the pipeline
- [x] 6.2 Zod boundaries — admin-API bodies (Chunk C), host config + request body/params/query + response (Chunk D), ledger row shape (Chunk C)
- [x] 6.3 Every error code thrown — Chunk D error codes verified via request-pipeline + host tests
- [x] 6.4 Strict-mode behaviours both on and off — response validation `enforce`/`warn`, `blueGreen`/`503-window`
- [x] 6.5 OTel instruments exercised on real production code paths (counter + histogram emit on every pipeline success/failure)
- [x] 6.6 FSM dedup mutex tested (Chunk B)
- [x] 6.7 No retroactive tick — every box above reflects work done in this change
## 7. Archive
- [x] 7.1 Fold spec delta into `openspec/specs/api-host/spec.md`
- [x] 7.2 Move `openspec/changes/api-host/` → `openspec/archive/2026-05-25-api-host/`
- [x] 7.3 Tick Stage-2 row in umbrella `openspec/changes/api-plugin-foundation/`
- [x] 7.4 Refresh `STATUS.md`