From 6d07aa605951492d1180ed614785f09cf456f6c3 Mon Sep 17 00:00:00 2001 From: Xubin Ren Date: Mon, 11 May 2026 07:35:37 +0000 Subject: [PATCH] test(webui): cover randomUUID entry shim fallback Add a focused regression test for the non-secure-context WebUI entry shim so missing crypto.randomUUID no longer depends on manual verification. Co-authored-by: Cursor --- webui/src/tests/main-randomuuid.test.tsx | 42 ++++++++++++++++++++++++ 1 file changed, 42 insertions(+) create mode 100644 webui/src/tests/main-randomuuid.test.tsx diff --git a/webui/src/tests/main-randomuuid.test.tsx b/webui/src/tests/main-randomuuid.test.tsx new file mode 100644 index 000000000..a7660ac24 --- /dev/null +++ b/webui/src/tests/main-randomuuid.test.tsx @@ -0,0 +1,42 @@ +import { afterEach, beforeEach, describe, expect, it, vi } from "vitest"; + +const render = vi.fn(); +const createRoot = vi.fn(() => ({ render })); + +vi.mock("react-dom/client", () => ({ + default: { createRoot }, +})); + +vi.mock("@/App", () => ({ + default: () => null, +})); + +describe("main entry crypto shim", () => { + const originalRandomUUID = globalThis.crypto.randomUUID; + + beforeEach(() => { + vi.resetModules(); + createRoot.mockClear(); + render.mockClear(); + document.body.innerHTML = '
'; + delete (globalThis.crypto as Crypto & { randomUUID?: Crypto["randomUUID"] }).randomUUID; + }); + + afterEach(() => { + Object.defineProperty(globalThis.crypto, "randomUUID", { + value: originalRandomUUID, + configurable: true, + }); + document.body.innerHTML = ""; + }); + + it("installs a randomUUID fallback when the browser omits it", async () => { + await import("../main"); + + expect(globalThis.crypto.randomUUID).toEqual(expect.any(Function)); + expect(globalThis.crypto.randomUUID()).toMatch( + /^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/, + ); + expect(createRoot).toHaveBeenCalledWith(document.getElementById("root")); + }); +});