Current section
Files
Jump to
Current section
Files
live_interaction_contracts
REPRODUCE.md
REPRODUCE.md
# Reproduction
The packaged way (recommended) — from the project (or a consumer) root:
mix live_interaction_contracts.test # harness + fuse + ledger
mix live_interaction_contracts.test --suite cursor
mix live_interaction_contracts.test --suite combobox
mix live_interaction_contracts.ledger
The raw way (how the spikes were developed) is below. Fixtures now live under `priv/`.
Prereqs: Elixir 1.20 / OTP 28, Node with Playwright + browsers installed
(`npx playwright install chromium firefox webkit`). All apps bind 127.0.0.1 only.
## Conformance harness (delegation ledger)
cd priv/harness
LV_SPEC=1.2.5 elixir app.exs # port 4123
node suite.mjs # -> harness/results.json
node ledger.mjs # -> ../delegation-ledger.{json,md}
## Multi-version drift check
cd priv/harness
PORT=4125 VERSIONS_OUT=versions-alt.json LV_SPEC="~> 1.1.0" elixir app.exs
PORT=4125 node suite.mjs # compare against results-1.2.5.json
# LV_SPEC also accepts: github:phoenixframework/phoenix_live_view#main | path:/abs/checkout
## Cursor rebind spike (client tier)
cd priv/cursor-spike
elixir app.exs # port 4126
node spike.mjs # -> cursor-spike/results.json
node focus3.mjs # aria-activedescendant vs roving focus
Kill a stuck server: kill $(lsof -nP -t -iTCP:<port> -sTCP:LISTEN)
## Combobox integration spike (Delegation × Cursor × Channel)
cd priv/combobox-spike
elixir app.exs # port 4127
node spike.mjs # -> combobox-spike/combobox-results.json
# deterministic async ordering via server query/release gate; guard flag toggles
# server-side monotonic guard (construction) vs client version-stamp (convention)
## CI fuse (local)
cd priv/harness
node ci-assert.mjs # exits non-zero on green regression / red-turned-green
node ledger.mjs # regenerates ../delegation-ledger.{json,md}
## CI (GitHub Actions)
.github/workflows/conformance.yml
# Tier 1 stable = blocking gate; Tier 2 main/edge = scheduled early-warning fuse.
# PR: reduced browser matrix (ONLY_BROWSER=chromium); release/schedule: full matrix.
## Consumer install (hex package dry-run — executed 2026-07-07, all green)
# 1. build + unpack the package (what hex would ship)
mix hex.build
tar -xf live_interaction_contracts-*.tar -C /tmp/hexpkg
tar -xzf /tmp/hexpkg/contents.tar.gz -C /tmp/lic_pkg
# 2. scratch consumer app depends on the UNPACKED PACKAGE (not the repo):
# {:phoenix, "~> 1.8"}, {:phoenix_live_view, "~> 1.2"},
# {:live_interaction_contracts, path: "/tmp/lic_pkg"}
# plus a module that imports and renders <.popover>.
mix deps.get && mix compile
# -> _build/dev/phoenix-colocated/live_interaction_contracts/index.js
# must list all five hooks (Popover/Menu/Tooltip/Select/Combobox) — zero manual wiring.
# 3. run the packaged conformance suite FROM the consumer app
# (proves priv fixtures ship complete; playwright comes from the
# package's own package.json)
(cd /tmp/lic_pkg && npm i)
mix live_interaction_contracts.test --suite tooltip # 8/8, all engines
# Real consumers install from Hex and use deps/live_interaction_contracts
# in place of /tmp/lic_pkg; everything else is identical.