diff --git a/README.md b/README.md index 55c8323..ca5bcbd 100644 --- a/README.md +++ b/README.md @@ -270,3 +270,83 @@ cp .env.example .env # edit with your keys # Requires PostgreSQL with pgvector node server.js ``` + +--- + +## Testing + +Two layers, both zero-config after the initial setup. + +### Unit tests — pure dose math (Node built-in) + +```bash +npm test +``` + +Runs `node --test test/` against `public/js/calc-math.js` — pure functions for +APLS / Best Guess weight, Parkland, Holliday-Segar 4-2-1, PRAM, Westley, +epi (anaphylaxis vs arrest vs NRP, different concentrations), RSI drugs, +min SBP, ETT sizing, Lund-Browder TBSA. **36 assertions, no dependencies.** + +### End-to-end tests — Playwright smoke suite + +Runs a headless Chromium against the live app. **128 tests** covering every +calculator tab, every Bedside sub-pill + widget, auth-gated pages (encounter, +well visit, charts, vaccines, catch-up, learning hub, dictation, settings, +FAQ), at **both desktop and mobile (Pixel 5) viewports**. + +```bash +# First-time setup: spin up the auth-less test container (port 3553) +docker compose -f docker-compose.yml -f docker-compose.e2e.yml up -d pediatric-scribe-e2e + +# Then run the full suite (runs inside an official Playwright container) +npm run e2e +``` + +The runner script (`scripts/e2e.sh`) uses `mcr.microsoft.com/playwright` so you +don't need Node or browsers on the host. + +**Test environment:** + +- `pediatric-ai-scribe` (port 3552) — your normal app +- `pediatric-ai-scribe-e2e` (port 3553) — identical image, but with + `TURNSTILE_SECRET_KEY=""` and `SMTP_HOST=""` so Playwright can log in + without a bot challenge. Shares the same Postgres + pgdata volume. +- Test user: `e2e-user@ped-ai.test` (auto-verified on first register) +- Harness page: `public/e2e-harness.html` loads the calculators component + without the auth wall for smoke tests that don't need a logged-in session. + +**Viewing failures** — Playwright writes `e2e/test-results//` +with: + +- `test-failed-1.png` — screenshot at the point of failure +- `trace.zip` — full action trace (replay with `npx playwright show-trace`) +- `error-context.md` — DOM snapshot and console logs + +Everything but the specs and config is gitignored under `e2e/`. + +**Files:** + +- `e2e/tests/bedside-smoke.spec.js` — 26 tests for the Bedside module +- `e2e/tests/top-calculators.spec.js` — 27 tests for BP / BMI / Growth / + Bili / Vitals / BSA / Dose / Resus / GCS / Equipment +- `e2e/tests/auth-gated-smoke.spec.js` — 11 tests for the auth-gated tabs +- `e2e/playwright.config.js` — runs all the above under both `chromium` + (Desktop Chrome) and `mobile-chrome` (Pixel 5) projects + +**Writing a new test:** + +```js +const { test, expect } = require('@playwright/test'); + +test('my new smoke test', async ({ page }) => { + await page.goto('/e2e-harness.html'); // bypasses auth for calculators + await page.waitForFunction(() => window.__harnessReady === true); + await page.click('button.calc-nav-pill[data-calc="bedside"]'); + await expect(page.locator('#calc-bedside')).toBeVisible(); +}); +``` + +For auth-gated routes, use the login fixture in `auth-gated-smoke.spec.js` +as a template — it caches the token at module scope so you don't hit the +login rate-limit.