import { describe, expect, it, vi } from "vitest"; import { readToolcraftPersistedResourceRefs } from "./persistence-resource-refs"; function storageWith(entries: Record) { return { get length() { return Object.keys(entries).length; }, getItem: (key: string) => entries[key] ?? null, key: (index: number) => Object.keys(entries)[index] ?? null, }; } const payload = (mediaAssets: unknown[], version = 1) => JSON.stringify({ version, state: { mediaAssets } }); describe("durable workspace resource roots", () => { it("reads custom, legacy, current and newer-version snapshots without current-schema normalization", () => { const storage = storageWith({ "custom-workspace": payload([{ assetKind: "file", resourceRef: "file:custom" }]), "creative-apps-kit:old:state:v1": payload([{ assetKind: "image", resourceRef: "image:old" }]), "toolcraft:new:state:v9": payload([{ assetKind: "model", sourceBundleRef: "model:source", originalDocumentRef: "model:original", activeDocumentRef: "model:active", repairedDocumentRef: "model:repaired", repairPlanRef: "model:repair", analysis: { repairPlanRef: "model:analysis" }, originalAnalysis: { repairPlanRef: "model:original-analysis" }, }], 9), "theme": "dark", "unrelated": JSON.stringify({ state: { mediaAssets: [{ assetKind: "file", resourceRef: "not-workspace" }] } }), "malformed": "{", }); expect(readToolcraftPersistedResourceRefs(() => storage)).toEqual(new Set([ "file:custom", "image:old", "model:source", "model:original", "model:active", "model:repaired", "model:repair", "model:analysis", "model:original-analysis", ])); }); it("returns an empty set for readable empty storage", () => { expect(readToolcraftPersistedResourceRefs(() => storageWith({}))).toEqual(new Set()); }); it("does not let a denied storage getter escape", () => { expect(readToolcraftPersistedResourceRefs(() => { throw new DOMException("denied", "SecurityError"); })).toBeNull(); }); it.each(["key", "getItem"] as const)("fails closed when %s throws", (method) => { const storage = storageWith({ saved: payload([]) }); vi.spyOn(storage, method).mockImplementation(() => { throw new Error("unavailable"); }); expect(readToolcraftPersistedResourceRefs(() => storage)).toBeNull(); }); it.each([null, "same"])("rejects incomplete or duplicate enumeration (%s)", (key) => { const storage = { length: 2, key: () => key, getItem: () => payload([]) }; expect(readToolcraftPersistedResourceRefs(() => storage)).toBeNull(); }); it("rejects a missing value instead of returning partial roots", () => { const storage = { length: 1, key: () => "saved", getItem: () => null }; expect(readToolcraftPersistedResourceRefs(() => storage)).toBeNull(); }); it("detects a changing key inventory", () => { const entries = { saved: payload([]) }; const storage = storageWith(entries); const read = storage.getItem; storage.getItem = (key) => { Object.assign(entries, { another: payload([]) }); return read(key); }; expect(readToolcraftPersistedResourceRefs(() => storage)).toBeNull(); }); it("detects an observed snapshot replacement during the scan", () => { const storage = storageWith({ saved: payload([]) }); const read = vi.fn().mockReturnValueOnce(payload([])).mockReturnValue(payload([{ assetKind: "file", resourceRef: "file:new" }])); storage.getItem = read; expect(readToolcraftPersistedResourceRefs(() => storage)).toBeNull(); }); });