Archilyzer · Source

archilyzer

Archilyzer
git clone https://archilyzer.pages.dev/source/archilyzer.git
Log | Files | Refs | README | LICENSE

commit b8b0fd53c362907a06139731f372677c9b8a5959
parent fe29a92f0c60e32256e08dc506d52a218ecbeb97
Author: I Mean I'm Just Saying <imeanimjustsaying@kiwifarms.st>
Date:   Thu, 17 Sep 2026 20:36:49 -0400

e2e: two adjacent paused rows, and the pixel has to belong to the menu

One paused row alone does not reproduce the operator report: an opacity group still
paints above the plain rows below it. Two paused rows in a row is the smallest shape
that does, and selectOption never hit-tests, so the assertion asks the page who owns
the pixel. Verified: passes with 29aeeba, fails without it.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>

Diffstat:
Meditor/e2e/channel-priority.spec.ts | 55+++++++++++++++++++++++++++++++++++++++++--------------
1 file changed, 41 insertions(+), 14 deletions(-)

diff --git a/editor/e2e/channel-priority.spec.ts b/editor/e2e/channel-priority.spec.ts @@ -149,33 +149,60 @@ test("the Sync only preset is paused everywhere with sync pinned back", async ({ // // A row is dimmed when it is excluded from the build or its base tier is // Paused, and the dim used to sit on the `<tr>` as `opacity-60`. Opacity below -// 1 creates a stacking context, which confines the popover's `absolute z-30` to -// the row: every row below it painted over the menu and ate its clicks -// (operator report 2026-09-17). The dim is per cell now, with the Tier cell -// left alone. The click is what proves it — Playwright hit-tests the point, so -// a row painted on top fails the action with "intercepts pointer events". -test("a paused row's Advanced menu draws above the rows below it", async ({ +// 1 makes the row a stacking context painted as one group, so the panel's +// `absolute z-30` no longer lifts it out of the row: the NEXT dimmed row is a +// later group at the same level and paints straight over the menu (operator +// report 2026-09-17, on a corpus where paused rows sit next to each other). +// Two paused rows in a row is the smallest shape that reproduces it; one alone +// does not, because an opacity group still paints above the plain rows below. +test("a paused row's Advanced menu draws above the paused row below it", async ({ page, }) => { await resetData("two-slow-channels"); await page.goto(ALL); + // slow-a is the FIRST row and slow-b the one its panel hangs over. The + // assertion is meaningless on the last row of the table, which has nothing + // after it to be covered by. + const slugs = await page + .locator('[aria-label^="select slow-"]') + .evaluateAll((els) => + els.map((el) => el.getAttribute("aria-label")!.replace("select ", "")), + ); + expect(slugs).toEqual(["slow-a", "slow-b"]); + + await page.getByLabel("select all channels").check(); + await page.getByLabel("bulk tier").selectOption("paused"); await page - .getByLabel("tier for slow-a", { exact: true }) - .selectOption("paused"); + .getByLabel("channel priority bulk") + .getByRole("button", { name: "Apply tier" }) + .click(); await expect - .poll(async () => (await settings()).channelPriority?.channels["slow-a"]) - .toEqual({ tier: "paused" }); - // Reloaded, so the row renders dimmed from the server's own tier rather than - // from the control's optimistic state. + .poll(async () => (await settings()).channelPriority?.channels) + .toEqual({ "slow-a": { tier: "paused" }, "slow-b": { tier: "paused" } }); + // Reloaded, so both rows render dimmed from the server's own tiers rather + // than from the controls' optimistic state. await page.reload(); await page.getByLabel("advanced priority for slow-a").click(); - // `sync` is the first row of the popover, the part that hangs over slow-b. + // `sync` is the first control in the panel, the part that hangs over slow-b. const override = page.getByLabel("sync override for slow-a"); await expect(override).toBeInViewport(); - await override.selectOption("normal"); + // THE ASSERTION. `selectOption` never hit-tests, so it passes straight + // through a row painted on top of the panel; this asks the page directly who + // owns the pixel. With `opacity-60` back on the `<tr>` the answer is a cell + // of the paused slow-b row below. + const owner = await override.evaluate((el) => { + const r = el.getBoundingClientRect(); + const top = document.elementFromPoint(r.x + r.width / 2, r.y + r.height / 2); + return top === el || el.contains(top) + ? "the override" + : `${top?.tagName ?? "nothing"} ${top?.getAttribute("aria-label") ?? top?.textContent?.trim().slice(0, 40) ?? ""}`; + }); + expect(owner).toBe("the override"); + + await override.selectOption("normal"); await expect .poll(async () => (await settings()).channelPriority?.channels["slow-a"]) .toEqual({ tier: "paused", overrides: { sync: "normal" } });