fix(19): resolve post-merge wave-4 harness integration gaps
Two issues surfaced only when plans 19-04 (login UI) and 19-05 (Option C bypass + login.spec) were merged together and run against the real stack — neither executor could catch them in isolation: 1. LOCAL_SESSION_SECRET was added to the CI harness (ci.yml) but not to the local dev stack (docker-compose.dev.yml). Without it the real-login success path (POST /api/auth/local/login) 503s when signing the session cookie, so the e2e round-trip failed. Add the same fixed dev-only value to the dev compose override (dev-only target; never a production secret). 2. login.spec test 1 assumed clearing the local-session cookie yields a logged-out state, but under the always-on DEV_AUTH_BYPASS devAuthBypass() injects DEV_USER into /api/me regardless of any cookie — a logged-out state is architecturally unreachable in this bypass-only harness. Reframe the test to drive /login directly (validating the real-browser render of all brand + form surfaces) and move the unauthenticated root->/login redirect-gate coverage to a unit test in App.test.tsx where meQuery.isError is controllable. Result: API 446/446, PWA 265/265 (+2 gate tests), e2e desktop 42 passed / 3 skipped (all login specs green). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.8
parent
11977fddf4
commit
17a531550a
+15
-12
@@ -9,12 +9,16 @@
|
||||
* under DEV_AUTH_BYPASS=true. The OTHER specs (layout, calendar, lists) rely on that
|
||||
* cookie being present and do NOT clear it — they still reach the authed app unchanged.
|
||||
*
|
||||
* This spec runs in a SEPARATE browser context that clears the local-session cookie
|
||||
* (via storageState:'' and explicit cookie-clear) so the real login gate fires. After
|
||||
* verifying the form, it logs in as devuser/devpass to confirm the full round-trip.
|
||||
* IMPORTANT — bypass constraint: this harness is DEV_AUTH_BYPASS-only (global-setup
|
||||
* refuses a non-bypass DB). Under the bypass, devAuthBypass() injects DEV_USER into
|
||||
* every /api/* request, so /api/me is authed regardless of the local-session cookie —
|
||||
* clearing the cookie does NOT produce a logged-out state in the browser. We therefore
|
||||
* exercise the /login page DIRECTLY (the /login route always renders the form) for the
|
||||
* form + real-login round-trip, and cover the unauthenticated root→/login redirect gate
|
||||
* at the unit level in src/App.test.tsx (where meQuery.isError is controllable).
|
||||
*
|
||||
* Specs covered:
|
||||
* 1. Navigating to the app while unauthenticated → redirected to /login, brand + form visible
|
||||
* 1. /login renders all brand + form surfaces (real browser, real CSS/tokens)
|
||||
* 2. Wrong password → single "Incorrect username or password." error message
|
||||
* 3. Correct devuser/devpass → navigates into the app (out of /login)
|
||||
*
|
||||
@@ -74,16 +78,15 @@ test.describe('Login form — real auth round-trip (desktop/Chromium only)', ()
|
||||
'Login form tests only run on Chromium (desktop profile) — other profiles use the bypass cookie',
|
||||
);
|
||||
|
||||
test('unauthenticated navigation → /login gate: brand slot and form visible', async ({
|
||||
test('/login renders all brand + form surfaces (UI-SPEC Surfaces 2-7)', async ({
|
||||
page,
|
||||
context,
|
||||
baseURL,
|
||||
}) => {
|
||||
// Start from a clean state — no local-session cookie
|
||||
await context.clearCookies();
|
||||
|
||||
// Navigate to the app root; the PWA login gate should redirect to /login
|
||||
await page.goto(baseURL ?? 'http://localhost:5173', { waitUntil: 'networkidle' });
|
||||
// Navigate DIRECTLY to /login rather than asserting an unauthenticated root→/login
|
||||
// redirect: under the always-on DEV_AUTH_BYPASS, /api/me is authed via DEV_USER
|
||||
// injection regardless of the cookie, so visiting / lands on /calendar and a
|
||||
// logged-out state is unreachable here. The redirect gate is unit-tested in
|
||||
// src/App.test.tsx; this e2e proves /login renders every surface in a real browser.
|
||||
await page.goto('/login', { waitUntil: 'domcontentloaded' });
|
||||
|
||||
// Assert we are on the /login route
|
||||
await expect(page).toHaveURL(/\/login/);
|
||||
|
||||
Reference in New Issue
Block a user