Files
emdash-cms--emdash/e2e/tests/admin-css-isolation.spec.ts
wehub-resource-sync b3a7f98e5a
CI / E2E Cloudflare (4/8) (push) Failing after 0s
CI / E2E Cloudflare (8/8) (push) Failing after 1s
CI / Lint (push) Failing after 1s
Auto Extract / Extract (push) Failing after 4s
CI / Version Check (push) Failing after 9s
CI / Integration Tests (push) Failing after 1s
CI / E2E tests (1/8) (push) Failing after 1s
CI / E2E tests (2/8) (push) Failing after 2s
CI / E2E tests (3/8) (push) Failing after 2s
CI / Browser Tests (push) Failing after 1s
CI / E2E tests (5/8) (push) Failing after 1s
CI / E2E Cloudflare (2/8) (push) Failing after 2s
CI / Typecheck (push) Failing after 1s
CI / Changeset Validation (push) Failing after 2s
CI / E2E Cloudflare (5/8) (push) Failing after 1s
CI / E2E Cloudflare (6/8) (push) Failing after 1s
CI / E2E Cloudflare (7/8) (push) Failing after 1s
CodeQL / Analyze (javascript-typescript) (push) Failing after 1s
Format / Format (push) Failing after 0s
CodeQL / Analyze (actions) (push) Failing after 4s
CI / E2E tests (4/8) (push) Failing after 1s
CI / E2E tests (6/8) (push) Failing after 1s
CI / E2E tests (7/8) (push) Failing after 2s
CI / E2E tests (8/8) (push) Failing after 1s
CI / E2E Cloudflare (1/8) (push) Failing after 1s
CI / E2E Cloudflare (3/8) (push) Failing after 2s
Preview Releases / Publish Preview (push) Failing after 0s
zizmor / Run zizmor (push) Failing after 1s
Release / Release (push) Failing after 2s
CI / Smoke Tests (push) Failing after 5m36s
CI / Tests (push) Failing after 6m36s
Release / Sync Templates (push) Has been skipped
CI / E2E Tests (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 12:23:53 +08:00

60 lines
2.3 KiB
TypeScript

/**
* Admin CSS isolation (#1281)
*
* The admin shell imports the compiled Kumo/Tailwind v4 stylesheet. In
* `astro dev`, Astro injects every CSS module reachable from the project's
* Vite graph into every page's <head>, so a top-level `import "...styles.css"`
* in the admin route leaked the admin theme onto public, non-admin routes —
* overriding host `:root` tokens (`--text-base`, `--text-lg`, ...) and applying
* admin author styling to otherwise-unstyled pages.
*
* Importing the stylesheet as `?url` keeps it out of the page CSS graph and
* scopes it to a route-local <link>. These tests pin both halves: the leak is
* gone from public routes, and the admin route still pulls the stylesheet in.
*/
import { test, expect } from "../fixtures";
const TAILWIND_SIGNATURE = "tailwindcss v4";
const KUMO_SIGNATURE = "kumo";
const ADMIN_STYLESHEET_LINK = /<link[^>]+rel="stylesheet"[^>]+href="([^"]+)"/;
test.describe("admin CSS isolation", () => {
test("public routes do not include the admin stylesheet", async ({ page }) => {
await page.goto("/");
const inlineStyles = await page.$$eval("style", (nodes) =>
nodes.map((n) => n.textContent ?? ""),
);
const leaked = inlineStyles.find(
(css) => css.includes(TAILWIND_SIGNATURE) && css.includes(KUMO_SIGNATURE),
);
expect(leaked, "admin Tailwind/Kumo theme leaked into a public route's inline <style>").toBe(
undefined,
);
const linkedHrefs = await page.$$eval("link[rel='stylesheet']", (nodes) =>
nodes.map((n) => n.getAttribute("href") ?? ""),
);
expect(linkedHrefs.some((href) => href.includes("admin"))).toBe(false);
const textBase = await page.evaluate(() =>
getComputedStyle(document.documentElement).getPropertyValue("--text-base").trim(),
);
expect(textBase, "Kumo's --text-base bled onto the host :root").toBe("");
});
test("admin route still loads the admin stylesheet", async ({ request }) => {
const response = await request.get("/_emdash/admin");
const html = await response.text();
const match = html.match(ADMIN_STYLESHEET_LINK);
expect(match, "admin shell is missing its <link rel=stylesheet>").not.toBeNull();
const cssResponse = await request.get(match![1]!);
const css = await cssResponse.text();
expect(css).toContain(TAILWIND_SIGNATURE);
expect(css).toContain(KUMO_SIGNATURE);
});
});