evOo-local/apps/web/e2e/smoke.spec.ts
Ingo Wagner bd3c6c2d47 fix(web): resolve React multi-version hook error via Vite alias
- Add Vite resolve.alias for react/react-dom to root node_modules
- Removes duplicate React instances from pnpm transitive deps
- Create E2E smoke test verifying no React hook errors
- Fix: pnpm resolves @dnd-kit deps to react@19.2.8, conflicting with
  app react@19.2.3 causing 'Invalid hook call' at runtime

Fixes: dark screen / Invalid hook call on /app
2026-09-23 13:18:08 +00:00

49 lines
1.5 KiB
TypeScript

/**
* Smoke test: verify the app loads without React errors.
*
* This test ensures that the Vite build resolves a single React
* instance (no duplicate React versions from pnpm transitive deps).
*/
import { test, expect } from "@playwright/test";
test("app loads without React hook errors", async ({ page }) => {
const consoleErrors: string[] = [];
const pageErrors: string[] = [];
page.on("console", (msg) => {
if (msg.type() === "error") consoleErrors.push(msg.text());
});
page.on("pageerror", (err) => {
pageErrors.push(err.message);
});
await page.goto("/app", { waitUntil: "domcontentloaded", timeout: 10000 });
await page.waitForTimeout(5000);
// The critical check: no "Invalid hook call" or related React errors
const hookErrors = pageErrors.filter((e) =>
e.includes("Invalid hook call") ||
e.includes("useMemo") ||
e.includes("useRef") ||
e.includes("useContext") ||
e.includes("more than one copy of React")
);
expect(hookErrors).toEqual([]);
// Root element must exist
await expect(page.locator("#root")).toBeAttached();
// Should show either login form or app content (not a blank/dark screen)
const bodyText = await page.evaluate(() => document.body?.innerText || "");
const hasContent =
bodyText.includes("Sign in") ||
bodyText.includes("Anmelden") ||
bodyText.includes("EvOo") ||
bodyText.includes("Projekte") ||
bodyText.includes("Heute") ||
bodyText.includes("Team");
expect(hasContent).toBe(true);
});