import { readdirSync, readFileSync } from "node:fs"; import { describe, expect, it } from "vitest"; import { chipLaneClass } from "./useChipOverflowFit"; // E10 S4. The chip lanes' hidden measurer is laid out UNBOUNDED on purpose (it exists to read natural // widths), and an absolutely-positioned box still feeds its ancestors' SCROLLABLE overflow even while // `visibility: hidden`. Un-clipped, that leaked to : at a 1024px viewport the channel manager's // document scrolled 249px sideways and the fixed header slid off. `chipLaneClass` carries the clip that // contains it — so the invariant worth locking is not "this lane looks right" but "every mirror lives // inside a lane that clips". A fifth lane hand-rolling `relative` is exactly the drift this catches, // and no DOM test can: jsdom has no layout, so the overflow it guards against is unobservable there. // // COUNTED per occurrence, not tested per file. The first cut asked `src.includes(chipLaneClass)`, which // a file could satisfy with ONE compliant lane while hand-rolling a second — and ChannelTags already // holds two lanes and two mirrors, so the likeliest place for a fifth lane was the one file the check // was blind inside (E10 review round 1). const MIRROR = "invisible absolute left-0 top-0"; // A mirror only exists to be measured, so the hook is the other half of the signature. Discovering by // BOTH means a mirror written with the utilities in another order is still caught by its import. const HOOK = "useChipOverflowFit"; function count(haystack: string, needle: string): number { return haystack.split(needle).length - 1; } /** Occurrences of `chipLaneClass` that are actually a LANE, i.e. not the import that brings it in. * Counting raw occurrences gave every file one free mirror — the import — so a second, unprotected * lane in a file that already had a compliant one still passed, which is the exact hole this test * was rewritten to close (E10 review round 2, caught by mutation). */ function laneCount(src: string): number { // `[^;]` rather than `[\s\S]`: an import is stripped up to ITS OWN `from "…";`. The lazy any-char // form ran past a side-effect import (`import "./x.css";` has no `from`) into the next statement's // `from`, swallowing whatever lay between — a lane there would be uncounted. return count(src.replace(/^\s*import\s[^;]*?\sfrom\s+"[^"]*";$/gm, ""), "chipLaneClass"); } /** Every source file under src/, not just src/components/ — App.tsx and main.tsx sit above it. */ function sources(): Array<[string, string]> { const walk = (u: URL, prefix: string): Array<[string, string]> => readdirSync(u, { withFileTypes: true }).flatMap((e) => { if (e.isDirectory()) return walk(new URL(`${e.name}/`, u), `${prefix}${e.name}/`); if (!/\.tsx?$/.test(e.name) || e.name.includes(".test.")) return []; return [ [`${prefix}${e.name}`, readFileSync(new URL(e.name, u), "utf-8")] as [string, string], ]; }); return walk(new URL("../", import.meta.url), ""); } /** Files that render a measurer, by either half of its signature. */ function withMirror(): Array<[string, string]> { return sources().filter( ([name, src]) => !name.startsWith("lib/useChipOverflowFit") && (src.includes(MIRROR) || src.includes(HOOK)), ); } describe("chip lane containment contract", () => { it("strips imports without swallowing what follows a side-effect import", () => { const src = [ 'import "./x.css";', "const lane = chipLaneClass;", 'import { chipLaneClass } from "./chipLane";', ].join("\n"); expect(laneCount(src)).toBe(1); }); it("keeps all three halves of the lane class — offsetParent, clip, and room for the focus ring", () => { expect(chipLaneClass.split(/\s+/)).toEqual( expect.arrayContaining(["relative", "overflow-clip", "[overflow-clip-margin:0.25rem]"]), ); }); it("gives every hidden chip measurer its own chipLaneClass lane", () => { const offenders = withMirror() .map(([name, src]) => ({ name, mirrors: count(src, MIRROR), lanes: laneCount(src), })) .filter((f) => f.lanes < f.mirrors); expect(offenders).toEqual([]); }); it("finds the measurers it claims to guard (the marker has not been renamed away)", () => { // The MIRROR alone, not the hook: `lib/chipOverflow.ts` names the hook in a prose comment and was // padding this canary, so it stayed satisfied with one real measurer fewer (round 2). expect(sources().filter(([, src]) => src.includes(MIRROR)).length).toBeGreaterThanOrEqual(3); }); // The clip is a Tailwind utility whose only occurrence is `chipLaneClass`, a `.ts` constant: if // source detection ever stopped covering that file, the utility would leave the bundle and the // leak above would return with every lane green. index.css anchors it; this keeps the anchor. it("keeps the clip in the bundle whatever source detection sees", () => { const css = readFileSync(new URL("../index.css", import.meta.url), "utf-8"); expect(css).toMatch(/@source inline\("[^"]*\boverflow-clip\b[^"]*"\)/); }); });