fix(mock): scope /reset by MAC so parallel specs stop wiping each other

The re-authentication test passed locally but failed all three CI
attempts: no request carried a token, because self-hosted.e2e.ts issues
a GLOBAL `POST /reset` against the same mock from a parallel Playwright
worker, destroying the session mid-import. Running only stalker.e2e.ts
locally never triggered it.

Serializing within one file (4b31f7167) could not fix this — the
interference is between files. Mock state is per-MAC, so `/reset` now
accepts `?macAddress=` and clears only that MAC's data, favorites,
session and watchdog counters; the unscoped form is kept for callers
that own the whole server. Both spec files now reset only the MACs they
own, so no worker can disturb another.

Verified: a scoped reset of one MAC leaves another MAC's session intact
(and its own dies), and stalker.e2e.ts + self-hosted.e2e.ts run together
23/23 green — the combination that reproduced the CI failure.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
4grayandClaude Fable 5 committed 2026-08-01 19:55:09 +02:00
1 parent 23d0ca8afd
commit 3a93fef0f3
6 files changed
+89 -13

No files matched your search

+7 -1
View File
@@ -102,7 +102,13 @@ function expectRequestsUseTargetId(requests: string[], path: string): void {
test.beforeEach(async ({ page, request }) => {
await request.post(`${XTREAM_MOCK_SERVER}/reset`);
await request.post(`${STALKER_MOCK_SERVER}/reset`);
// Scope the Stalker reset to the MAC this file uses: a global reset would
// wipe the sessions of stalker.e2e.ts running in a parallel worker.
await request.post(
`${STALKER_MOCK_SERVER}/reset?macAddress=${encodeURIComponent(
DEFAULT_MAC
)}`
);
await installRuntimeConfig(page);
await page.goto('/');
});
+32 -3
View File
@@ -106,12 +106,38 @@ async function interceptStalkerRequests(page: Page): Promise<void> {
});
}
/** Every MAC this file touches; each is reset individually (see below). */
const OWNED_MACS = [
DEFAULT_MAC,
MINIMAL_MAC,
EMBEDDED_SERIES_MAC,
LEGACY_PAGINATION_MAC,
AUTH_FLOW_MAC,
AUTH_REAUTH_MAC,
AUTH_REJECTED_MAC,
];
/**
* Reset only the MACs this file owns. Mock state is per-MAC and other spec
* files (self-hosted.e2e.ts) talk to the same server from a parallel worker,
* so a global reset here would wipe their sessions mid-test — and theirs
* would wipe ours.
*/
async function resetMockServer(request: APIRequestContext): Promise<void> {
await Promise.all(OWNED_MACS.map((mac) => resetMockServerMac(request, mac)));
}
async function resetMockServerMac(
request: APIRequestContext,
mac: string
): Promise<void> {
let lastError: unknown;
for (let attempt = 0; attempt < 3; attempt += 1) {
try {
const response = await request.post(`${MOCK_SERVER}/reset`);
const response = await request.post(
`${MOCK_SERVER}/reset?macAddress=${encodeURIComponent(mac)}`
);
if (response.ok()) {
return;
}
@@ -630,9 +656,12 @@ test('@stalker mock server reset clears cached state', async ({ request }) => {
);
expect(before.ok()).toBeTruthy();
// Reset
const reset = await request.post(`${MOCK_SERVER}/reset`);
// Scoped reset — a global one would clear MACs owned by parallel specs.
const reset = await request.post(
`${MOCK_SERVER}/reset?macAddress=${encodeURIComponent(DEFAULT_MAC)}`
);
expect(reset.ok()).toBeTruthy();
expect((await reset.json()).mac).toBe(DEFAULT_MAC);
// Data is regenerated identically (deterministic seed)
const after = await request.get(