githubnext/chopinPublic

Let's compose rich plans together

Test the frontend with a browser, and run it on every push #6

MergedKrzysztof-Cieslakmerged 3 commits intomainfromrefs/pull/6/head
  1. KC

    Six adapters in this codebase could not be tested and could not have been: measured table rails, a pointer drag, a caret painted for somebody else, a wash in `CSS.highlights`. `bun test` has no DOM and should not grow one — happy-dom returns zero for every rectangle, so a rail drawn in the right place and one drawn on top of itself pass the same assertion.

    Three commits: the suite, the MCP server that drives the same browser by hand, and CI.

    ## The suite

    40 tests in Chromium against the built client, 10 seconds, fully parallel.

    | File | Covers | | --- | --- | | `smoke` | `?as=` joins without the form, key stripped from the URL, `/` → `/r/main`, three panes, an empty room settles | | `editing` | keystroke to `plan.mdx`, reload, `# ` becomes a heading, a dropped socket locks the plan and reconnecting unlocks it | | `collab` | convergence both ways, the roster, a named peer caret, no self-caret | | `table` | rails on both axes, header-is-furniture, keyboard move, a real pointer drag with drop indicator, remove, alignment cycle, row limit | | `toolbar` | slash menu opens/filters/escapes, `and/or` does not trigger it, exactly one bubble, bold and heading reach the file, `javascript:` refused | | `sidecar` | questionnaire answer/refuse/cancel, thread quote as a link, reply, two-click accept, dismiss |

    A room exists because somebody opened its URL, so isolation costs a name rather than a fixture. Two servers, started by the suite: 8788, and 8789 with `DEV_QUESTIONS`/`DEV_COMMENTS` on — those are read on every room open, so one server would put a questionnaire in every other suite's room.

    `bun test` is untouched: still 500 pass in 18s, and it never sees these files.

    ## Things that had to be found the hard way

    Each of these is now an entry in `agents.md`, because each looked like working code.

    - **Bun's runner claims `.spec.` as well as `.test.`** — the conventional Playwright name enrols every one of these in the unit run, which cannot import them. Hence `*.e2e.ts`. - **Playwright's web servers start before `globalSetup`.** A dist check there is unreachable: verified by deleting `dist` and getting 60s of polling and a timeout naming a URL. The guard is top-level in the config now, and fails instantly with a sentence. - **`globalTeardown` runs while the servers are still up.** The snapshot sink debounces 500ms, so it wrote rooms back *after* the wipe — the tree ended up mostly empty and never quite. Cleanup moved to the way in, which is exact, and leaves a failed run's plan beside the trace that failed on it. - **`context.setOffline` leaves an established socket alone.** The offline test asserted nothing until it became `page.routeWebSocket`. - **`"Remove row 4"` contains `"Move row 4"`.** Accessible names match as substrings, so the obvious grip locator is a strict-mode violation every time. - **`data-plan-related` never runs in Chromium.** The wash is `CSS.highlights`; asserting on the attribute asserts on the fallback path.

    ## MCP

    `@playwright/mcp` pinned by version, run through `bunx`, so nothing enters `bun.lock`. Every release of it depends on a prerelease `playwright`, and a devDependency would put an alpha and a second `playwright-core` in the lockfile of a project that ships neither. `--browser chrome` avoids a redundant 180MB download.

    Probed over stdio before committing: 24 tools, navigates, and it drove the questionnaire end to end — answered both tabs, submitted, and both halves of the two-phase resolution landed (`state.json` says `answered`, `plan.mdx` carries `<Answer value="Anchors, Export" />`).

    ## CI

    Two jobs on `ubuntu-latest`, push to `main` and every PR, superseded runs cancelled.

    - `checks` — `bun run ci`, `bun run types`, `bun test` - `browser` — `playwright install --with-deps chromium`, `bun run e2e`

    Separate because they fail for unrelated reasons and only one is slow; a missing blank line should not wait behind Vite. Caches keyed on what decides their contents: dprint on the config naming its wasm plugins, Playwright on its own version rather than the lockfile. Failures upload the report and traces.

    ## Verification

    Replayed in a clean `/tmp` checkout from `git ls-files` — no `node_modules`, no build:

    ``` bun install --frozen-lockfile 1.78s, 1028 packages bun run ci 0 bun run types 0 bun test 0 500 pass playwright install --with-deps 0 CI=true bun run e2e 0 40 passed ```

    The first commit was then checked out into its own worktree and put through all five again, so the series is green at every point, not just at the tip. Confirmed the linux-x64 binaries for `tsgo`, `dprint` and `oxlint` are all in the lockfile.

    ## Worth pushing back on

    - **Ubuntu only.** This is developed on macOS and nothing verifies that path in CI. A matrix is a two-line change. - **`bun run ci` still means `dprint check && oxlint`**, not "what CI runs". I left the name alone rather than redefine a script you may use as a pre-commit check; the workflow lists the four commands explicitly. - **`@types/bun` moved to the root** because the catalog copies are nested per workspace and `e2e` is not one. Making it a workspace purely to be typechecked seemed the heavier answer.

  2. Krzysztof-Cieslakmerged 31bbb859d2303 months ago on GitHub

  3. Krzysztof-Cieslakclosed3 months ago on GitHub

  4. Krzysztof-Cieslakhead-ref-deleted3 months ago on GitHub