From 73612b18663c0145dcca8611904b7f21b5f84552 Mon Sep 17 00:00:00 2001 From: Austin Burdine Date: Fri, 28 Aug 2026 19:42:01 -0400 Subject: [PATCH] Fixed two flaky admin acceptance races (#30369) --- .../src/settings/membership/access.acceptance.test.tsx | 6 ++++++ .../settings/membership/tiers-checkout.acceptance.test.tsx | 6 +++++- 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/apps/admin/src/settings/membership/access.acceptance.test.tsx b/apps/admin/src/settings/membership/access.acceptance.test.tsx index 63eb3c19ff3..a98b74f80cb 100644 --- a/apps/admin/src/settings/membership/access.acceptance.test.tsx +++ b/apps/admin/src/settings/membership/access.acceptance.test.tsx @@ -30,6 +30,12 @@ function configWithPublicSiteAccessLimit() { async function choose(selectTestId: string, option: string) { await settingsScreen.access().getByTestId(selectTestId).click(); await settingsScreen.selectOptionExact(option).click(); + // Choosing an option starts the dropdown's close, it does not finish it: the + // list stays mounted and the body keeps `pointer-events: none` until the + // teardown completes. Anything clicked inside that window races it — the + // click is either refused or opens a layer the teardown then dismisses — so + // wait the dropdown out before the caller touches the next control. + await expect(settingsScreen.selectOptionExact(option)).toHaveCount(0); } describe('Access settings', () => { diff --git a/apps/admin/src/settings/membership/tiers-checkout.acceptance.test.tsx b/apps/admin/src/settings/membership/tiers-checkout.acceptance.test.tsx index ff24956c5a5..19b7f9e34eb 100644 --- a/apps/admin/src/settings/membership/tiers-checkout.acceptance.test.tsx +++ b/apps/admin/src/settings/membership/tiers-checkout.acceptance.test.tsx @@ -354,6 +354,9 @@ describe('Tier checkout collection', () => { await expect.element(modal.getByRole('button', { name: 'Saved' })).toBeVisible(); expect(createApi.lastRequest?.body).toMatchObject({ tiers: [{ name: createdTier.name }] }); + // The checkout write is chained after the tier's, so "Saved" — which the tier's own + // save flips — is reached before it lands. Wait for the write itself. + await expect.poll(() => putApi.requests.length).toBe(1); const sent = ( putApi.lastRequest?.body as { tiers_checkout_config: [{ shipping: { collect: boolean } }] } ).tiers_checkout_config[0]; @@ -380,7 +383,8 @@ describe('Tier checkout collection', () => { await modal.getByLabelText('Collect business tax ID').click(); await modal.getByRole('button', { name: 'Save' }).click(); await expect.element(modal.getByRole('button', { name: 'Saved' })).toBeVisible(); - expect(putApi.requests).toHaveLength(1); + // "Saved" is the tier save's signal; the checkout write is chained after it. + await expect.poll(() => putApi.requests.length).toBe(1); await modal.getByRole('button', { name: 'Close' }).click(); await expect(settingsScreen.tierDetailModal()).toHaveCount(0);