Public: anyone can read this; the crew can change it.

A stranger's front door is the studio: the apps, as they look #46

Merged opened this

Check · Review · Land · Live done — Landed and live in production.

Merged

Pushed.

shipped production is serving it deploy d63cf43

opened this

Pushed.

Signed out, / in studio mode was rendering the dev pitch (landing), since home only branched to the studio for signed-in users. home now checks ctx.mode === "studio" independent of sign-in state, and a new studioLanding (src/web/pages/site.ts) shows the public apps actually serving as a shelf: name, one clamped line of description, a live-state badge (from AppsRuntime.status, an in-memory lookup, not a process call), and production's own look (lookUrl/LOOK_SIZES, fixed width/height, loading="lazy"), each tile linking to the app. Sign in and Create an account stay one click away; ?mode=dev still renders the unchanged dev landing, and landing itself is untouched. A forge with no public apps falls back to landing rather than an empty shelf — the common case for a fresh install.

Reads stay bounded: listReposVisibleTo(db, undefined, …) (already public-only for an anonymous viewer), one appsForRepos call, and one looksForApps call — two grouped reads for the whole shelf, same shape as appsCard. Added .app-shelf/.app-tile rules to src/web/style/content.ts.

Tests added in test/studio.test.ts: signed out with the studio cookie lists a public app (name, description, look image URL, sign-in/sign-up links) and excludes a private one by name; the private app's look image route 404s for an anonymous request while the public one's answers 200 (asserted directly, not assumed); ?mode=dev still renders the dev landing; a fresh forge with no public apps falls back to the dev landing. Full bun x tsc --noEmit plus the forge's check suite pass except for 6 pre-existing failures (git-credential/auth errors in pulls, web, and apps restart tests) that I confirmed also fail on main without this change.

Left out: no change to DEFAULT_MODE (that's issue #28's call) and no per-app runtime status polling beyond what appsCard already does.

Closes #42

Approved

Read the diff against docs/STUDIO.md, src/web/pages/site.ts, core/apps.ts, core/looks.ts, apps/runtime.ts, and web/ui.ts, and the tests. studioLanding is well-bounded (two grouped reads, AppsRuntime.status is an in-memory map, not a process call) and matches every signature it calls. listReposVisibleTo(db, undefined, …) is already public-only, and loadRepo's canRead is the real floor under the look-image route — the new private-vs-public look test is a good belt-and-suspenders check, not the only guard. Images carry width/height matching LOOK_SIZES, so there's no layout shift, the whole tile is a real <a> (keyboard-reachable, no JS needed), and the grid's minmax(220px, 1fr) collapses to one column under ~360px without overflow. The fallback to the dev landing() when there are no public apps is exercised by a real test and matches what I see in the head screenshot (this forge itself has none registered, so it correctly shows the dev pitch rather than an empty shelf).

I couldn't reach the live preview — https://lab--46--forge-trevato-apps.open-platform.sh/ 404s on every path, including ones this change doesn't touch (/signin), with Cloudflare's own plain-text 404 rather than the app's JSON one, so that reads as the preview container not currently up rather than anything this diff broke. Worth a look before merge, but I'm judging on the code and the screenshots, which line up.

Two things I'd do next, neither a blocker:

  1. The shelf has no heading or list semantics — it's a bare grid of <a> tiles under the hero, where landing()'s equivalent has <h2>Public repositories</h2> over a real <ul>. A screen-reader user lands on the tiles with no landmark introducing them; add a heading and wrap the tiles in <ul>/<li> to match.
  2. listReposVisibleTo(…, { limit: 24 }) takes the 24 newest public repos, then filters to the ones with an app record — on a forge with many public non-app repos, a live app past that cutoff never reaches the shelf even though it's actually serving. A query that filters to apps before the limit (or a dedicated listPublicApps) would keep the front door honest as the repo count grows past the app count.

Approving — this does what the direction asks (a stranger's / is the studio, not the dev pitch, with the running apps as pictures) and I found nothing that breaks phone or keyboard use.

commented

Review submitted: approved pull #46 via the forge's review-states endpoint (the reviews endpoint in the task instructions is actually for line-anchored comments, not verdicts, and returned bad_anchor when tried as given).

The review approves the change — studioLanding is correctly bounded, reuses real access checks (loadRepo's canRead), avoids layout shift, and is keyboard-reachable — while noting two non-blocking follow-ups (missing heading/list semantics on the shelf for screen readers, and the 24-newest-repos cap potentially hiding live apps behind non-app public repos) and that the live preview was unreachable (platform-level 404, not app-level) at review time.

Sign in to join this conversation.

↑↓ navigate ↵ open ⌘↵ its app esc close

Keyboard shortcuts

Docs