host: Phase 2 — middleware (auth+ACL+error) + guarded POST /feed, 43/43
Composable handler->handler layers over Dream's primitives, with auth and permission POLICY injected so the layer is policy-free and testable: - middleware.sx: host/wrap-errors (JSON 500 via dream-catch-with), host/require-auth (bearer->principal via dream-bearer-token, JSON 401, injected token resolver), host/require-permission (lib/acl acl/permit? gate, JSON 403, injected resource extractor), host/pipeline (first = outermost) - feed.sx: POST /feed via host/feed-write-routes — auth ∘ ACL(post,feed) ∘ wrap-errors over host/feed-create (parse JSON body -> feed/post -> 201; non-object -> 400). Created activity reads back via GET /feed. - middleware suite (9) + feed write tests (6 new); conformance preloads now include the Datalog engine + ACL subsystem + Dream auth/error. ACL works with string atoms (no symbol coercion). Mute/prefs layer and sxtp.sx deferred to the next tick. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -36,7 +36,8 @@ host — no `ocaml-on-sx` dependency.
|
||||
|
||||
## Status (rolling)
|
||||
|
||||
`bash lib/host/conformance.sh` → **28/28** (3 suites: handler, router, feed). Phase 1 DONE.
|
||||
`bash lib/host/conformance.sh` → **43/43** (4 suites: handler, middleware, router,
|
||||
feed). Phase 1 DONE; Phase 2 in progress (middleware + write endpoint DONE, SXTP next).
|
||||
|
||||
## Ground rules
|
||||
|
||||
@@ -84,9 +85,18 @@ lib/host/sxtp.sx subsystem APIs (feed/search/commerce/…
|
||||
- [x] `conformance.sh` (mirrors `lib/dream`'s runner) — 28/28
|
||||
|
||||
## Phase 2 — Middleware + SXTP
|
||||
- [ ] `middleware.sx` — composable auth/acl/mute/error layers
|
||||
- [ ] `sxtp.sx` — host↔subsystem wire format (align with existing spec)
|
||||
- [ ] migrate a write endpoint (auth + permission + action)
|
||||
- [x] `middleware.sx` — composable layers as `handler->handler`: `host/wrap-errors`
|
||||
(JSON 500), `host/require-auth` (bearer -> principal, JSON 401, INJECTED token
|
||||
resolver), `host/require-permission` (ACL `acl/permit?` gate, JSON 403,
|
||||
INJECTED resource extractor), `host/pipeline` (first = outermost). Reuses
|
||||
Dream's `dream-bearer-token` + `dream-catch-with`; calls lib/acl public API.
|
||||
Mute/prefs layer deferred (no blocker, add when a domain needs it).
|
||||
- [ ] `sxtp.sx` — host↔subsystem wire format (align with existing spec at
|
||||
`applications/sxtp/spec.sx`)
|
||||
- [x] migrate a write endpoint (auth + permission + action): `POST /feed`
|
||||
(`host/feed-write-routes resolve`) — auth ∘ ACL("post","feed") ∘ wrap-errors
|
||||
over `host/feed-create`, which parses the JSON body and `feed/post`s it (201);
|
||||
non-object body -> 400. Created activity is readable back via `GET /feed`.
|
||||
|
||||
## Phase 3 — Strangler migration ledger
|
||||
- [ ] enumerate Quart endpoints; track migrated vs proxied
|
||||
@@ -116,6 +126,16 @@ lib/host/sxtp.sx subsystem APIs (feed/search/commerce/…
|
||||
`hosts/` change (out of scope) — tracked under Blockers as the eventual
|
||||
live-wiring step. For now the host layer is exercised purely via conformance.
|
||||
|
||||
- **Phase 2 (middleware + write endpoint DONE, 43/43).** `lib/host/middleware.sx`
|
||||
+ a guarded `POST /feed`. Middleware is plain function composition over Dream's
|
||||
primitives; auth/permission *policy* is injected (token resolver, resource
|
||||
extractor) so the layer is policy-free and testable. ACL authorisation runs
|
||||
against lib/acl's public `acl/permit?` (string atoms work — no symbol coercion
|
||||
needed). The write path proves the auth ∘ permission ∘ action stack end-to-end:
|
||||
401 unauth, 403 unpermitted, 201 + readback on success, 400 on bad body.
|
||||
- **Remaining for Phase 2: `sxtp.sx`** — the host↔subsystem wire format. Align
|
||||
with the existing spec at `applications/sxtp/spec.sx`. This is the next tick.
|
||||
|
||||
## Blockers
|
||||
|
||||
- **Live wiring to the native OCaml HTTP server** (Phase 3/4): the prod server in
|
||||
|
||||
Reference in New Issue
Block a user