1
0
Fork 0
polaris-task-force/tests/e2e/operations.e2e.spec.ts
Z8MB1E d16e721ccc test(e2e): seed e2e user, serialize workers, and deflake specs
The suite could not pass on the test database: global setup now seeds the shared dev/Test123 login with a superuser Roles doc and the dashboard rank, and points its own Payload connection at the test database. Playwright runs one worker with generous test and expect timeouts because first navigation to a route triggers a cold webpack compile, and gains E2E_BROWSER_PATH to swap the browser binary when the installed Vivaldi crashes under automation. The landing page gains the missing h1 the guest specs assert, login flows wait for the redirect to land, strict-mode locator collisions get exact or level-scoped matches, the session banner test re-signs the login claims with a short expiry using the runtime secret, and the reservation dialog click forces the dispatch and verifies the dialog opened (the trigger goes aria-hidden behind the modal mid-click, which stranded the retry loop).
2026-09-30 18:43:29 -04:00

59 lines
2.8 KiB
TypeScript

import { mkdirSync } from "node:fs";
import { expect, test } from "@playwright/test";
const SHOT_DIR = ".omo/evidence/screenshots";
async function shot(page: import("@playwright/test").Page, name: string): Promise<void> {
mkdirSync(SHOT_DIR, { recursive: true });
await page.screenshot({ path: `${SHOT_DIR}/${name}.png`, fullPage: true });
}
/**
* Operations surfaces: role-scoped visibility and failure-state behavior.
* NOTE: these tests exercise the real dev server and are run in the final
* verification wave (F3) under the dev-server protocol, not on every change.
*/
test.describe("Operations surfaces", () => {
test("guests are gated away from /operations by the landing page", async ({ page }) => {
await page.goto("/operations");
await expect(page.getByRole("heading", { level: 1 })).toHaveText("Polaris Task Force");
});
test("an authed user sees the operations overview with role sections", async ({ page }) => {
await page.goto("/login");
await page.getByLabel("Username").fill("dev");
await page.getByLabel("Password").fill("Test123");
await page.getByRole("button", { name: "Log in" }).click();
await page.waitForURL((url) => !url.pathname.startsWith("/login"), { timeout: 30_000 });
await page.goto("/operations");
await expect(page.getByRole("heading", { name: "Operations", level: 1 })).toBeVisible();
await expect(page.getByText("Recent operations")).toBeVisible();
await shot(page, "operations-overview-authed");
await expect(page.getByText("My extractions")).toBeVisible();
});
test("the ledger shows empty and filtered states without raw payloads", async ({ page }) => {
await page.goto("/login");
await page.getByLabel("Username").fill("dev");
await page.getByLabel("Password").fill("Test123");
await page.getByRole("button", { name: "Log in" }).click();
await page.waitForURL((url) => !url.pathname.startsWith("/login"), { timeout: 30_000 });
await page.goto("/operations/ledger?status=dead-letter");
await expect(page.getByRole("heading", { name: "Operations ledger" })).toBeVisible();
await expect(page.getByText("No operation events match this view.")).toBeVisible();
await shot(page, "operations-ledger-dead-letter-empty");
});
test("an unknown operation id renders the empty AAR state", async ({ page }) => {
await page.goto("/login");
await page.getByLabel("Username").fill("dev");
await page.getByLabel("Password").fill("Test123");
await page.getByRole("button", { name: "Log in" }).click();
await page.waitForURL((url) => !url.pathname.startsWith("/login"), { timeout: 30_000 });
await page.goto("/operations/definitely-not-a-real-operation");
await expect(page.getByText("No operation events are recorded under")).toBeVisible();
await shot(page, "operations-aar-unknown-empty");
});
});