fix(tests): use node:buffer.Blob so URL.createObjectURL works on Node 22

Node 22 URL.createObjectURL strictly requires a native node:buffer Blob
and throws ERR_INVALID_ARG_TYPE when given a jsdom Blob (caught by
fetchImageAsBlob, returning ''). Node 24 relaxed this check, masking the
failure locally.

Tests 007, 011: replace MSW/Response-based fetch mocks with direct
vi.spyOn(fetch) mocks returning node:buffer Blobs via a duck-typed
response object. The real URL.createObjectURL now handles the correct
Blob type and returns a genuine blob: URL on all Node versions.

Test 012: URL.createObjectURL identity varies across Node versions
making it impossible to spy on reliably. Replace createObjectURLSpy
assertion with a completedFetches counter in the fetch mock, which
proves the same semantic guarantee (6 requests ran, 7th was cleared).

setup.ts: restore the original conditional guard so the vi.fn fallback
only applies when URL.createObjectURL is completely absent, not
overwriting a working real implementation.
This commit is contained in:
jubnl
2026-04-07 23:53:43 +02:00
parent f594cbc21b
commit 68b660e547
2 changed files with 35 additions and 19 deletions
+9 -5
View File
@@ -59,11 +59,15 @@ globalThis.ResizeObserver = vi.fn().mockImplementation(() => ({
disconnect: vi.fn(),
})) as unknown as typeof ResizeObserver;
// URL.createObjectURL / revokeObjectURL — in jsdom, modules access globals
// through window.URL (not globalThis.URL — these are different objects on CI).
// Targeting window.URL is required so the mock is visible to source modules.
Object.defineProperty(window.URL, 'createObjectURL', { writable: true, configurable: true, value: vi.fn(() => 'blob:mock') });
Object.defineProperty(window.URL, 'revokeObjectURL', { writable: true, configurable: true, value: vi.fn() });
// URL.createObjectURL / revokeObjectURL — Node 22 URL.createObjectURL requires
// a native node:buffer Blob; passing a jsdom Blob throws ERR_INVALID_ARG_TYPE.
// Tests that need blob URLs should mock fetch to return node:buffer Blobs so
// the real URL.createObjectURL works. For tests that only need the method to
// exist without returning a real URL, stub it here as a vi.fn fallback.
if (typeof URL.createObjectURL === 'undefined') {
Object.defineProperty(URL, 'createObjectURL', { writable: true, configurable: true, value: vi.fn(() => 'blob:mock') });
Object.defineProperty(URL, 'revokeObjectURL', { writable: true, configurable: true, value: vi.fn() });
}
// Element.prototype.scrollIntoView — jsdom doesn't implement it
Element.prototype.scrollIntoView = vi.fn();