Skip to main content
← Back to list
01Issue
FeatureShippedExtensionsPublic
Assigneesskunk-ape

Relationships

#2806 gatorwalk-factory: studio model type and its local serve method

Opened by skunk-ape · 9/30/2026· Shipped 9/30/2026

Part of the gatorwalk-factory studio (gatorwalk-factory/ in swamp-extensions). Read gatorwalk-factory/README.md and DESIGN.md first. Design proposal (decisions recorded 2026-09-30): https://claude.ai/artifact/BNCKp7w3G3Q8VdmnCDDWHP. Prototype, with its source under source/ (read it with the Artifact tool): https://claude.ai/artifact/1wAxrpUqZ47FAjE4fU9idD. Both links are private to the maintainer.

Goal

A local server for the studio, started from swamp: swamp model create @swamp/gatorwalk-factory/studio studio once per repo, then swamp model method run studio serve. It serves the studio page on 127.0.0.1 and reads the lifecycle and scenario files that the repo's lifecycle holders name. It is its own model type, not a method on the holder (decided 2026-09-30), so one studio covers every lifecycle in the repo through a picker and never takes a holder's lock.

The studio views and simulates; it never writes (decided 2026-09-30: edits come from the agent). The agent edits lifecycles/<name>.yaml and its scenario files, and the page reloads them as they change.

Scope

  • The model type @swamp/gatorwalk-factory/studio (a string literal, like the others) with the method serve: an optional port input (default 0, a random port). It runs Deno.serve({ hostname: "127.0.0.1", signal: ctx.signal }), logs the URL, and blocks until Ctrl-C.
  • It finds lifecycle holders through the definition repository (HOLDER_TYPE) and resolves each holder's file as the holder does (#2803).
  • Routes. Every path is resolved on the server from a holder; a request names a holder, never a path. All routes are GET; anything else gets 405.
Route Does
GET /, /assets/* the page
GET /api/lifecycles holders, with the file each names
GET /api/lifecycles/<holder> text, digest, path
GET /api/lifecycles/<holder>/scenarios[/<name>] the same, for scenario files
GET /api/events server-sent events on Deno.watchFs changes, so the page reloads an agent's edit
  • Security:
    • Bind 127.0.0.1 only.
    • Host must be 127.0.0.1:<port> or localhost:<port> (DNS rebinding, which would otherwise let a hostile page read the files).
    • A request that carries Origin must carry the server's exact origin. No CORS headers are ever sent.
    • Scenario names must match NameSchema. The resolved real path must sit inside the holder's lifecycles/ directory.
    • No route writes a file or runs swamp, a shell or a method.
    • CSP default-src 'self'; fonts bundled.
    • No token or cookie: there is no write to protect, and the files are ones the local account can already read. If a write route is ever added, it needs the token, cookie and digest-checked write from the proposal first.
  • Build: UI source in gatorwalk-factory/studio/; deno task build:studio runs deno bundle --platform browser --minify into studio/dist/, which is committed. A verification command in verification/checks.yaml rebuilds it and fails on any diff. Shipping: additionalFiles at go-live. Until then there is no manifest (no_manifest_test.ts), so find dist/ relative to the model module in source mode.
  • The page in this issue is a minimal shell: a holder picker, the file's text (read-only), and reload on events. Design mode is its own issue.
  • DESIGN.md: a section "The studio server", with the security posture and why the studio is read-only.

Acceptance

  • Unit tests for each route and each refusal (bad Host, bad Origin, a non-GET method, a bad scenario name, a path escaping lifecycles/), against a temp repo.
  • An integration test starts serve through the CLI on a free port, loads /, changes the lifecycle file on disk, receives the event, and reads the new text.

Needs: #2803. Blocks: Design mode.

02Bog Flow
✓OPEN✓TRIAGED✓IN PROGRESS✓SHIPPED+ 1 MOREASSIGNED+ 5 MOREREVIEW+ 20 MOREPR_LINKED+ 2 MORESESSION_SUMMARIZED

Shipped

9/30/2026, 9:45:51 PM

Click a lifecycle step above to view its details.

03Sludge Pulse
skunk-ape assigned skunk-ape9/30/2026, 6:36:48 PM
Editable. Press Enter to edit.

system commented 9/30/2026, 3:48:16 PM

Classified automatically when this issue was filed.

  • Source: Extensions

If you feel this classification is incorrect, add a ripple to tell us so.

skunk-ape commented 9/30/2026, 4:04:47 PM

Re-scoped. Seth decided on 2026-09-30 that the studio views and simulates but never edits: "Edits should come from the agent... I just don't think we should go down the road of having users create or edit by hand." The agent writes lifecycles and scenarios as files, and the local page reloads them. The write path is gone: the PUT routes, the one-time token and cookie, digest-checked atomic writes, and saving drafts that fail the schema. All routes are GET, and anything else gets 405. Kept: the 127.0.0.1 binding, the Host check against DNS rebinding, the Origin check on any request that sends one, path confinement, file watch with SSE live reload, and the build, dist and freshness check. If a write route is ever added, the token, cookie and digest design has to come back first. The tests and acceptance now cover reads and live reload instead of saving.

Sign in to post a ripple.