import { describe, expect, it } from "bun:test"; import { Panic, panic, isPanic } from "./error"; describe("Panic", () => { describe("constructor", () => { it("creates Panic with message", () => { const p = new Panic({ message: "something went wrong" }); expect(p).toBeInstanceOf(Panic); expect(p.message).toBe("something went wrong"); expect(p._tag).toBe("Panic"); expect(p.name).toBe("Panic"); }); it("creates Panic with cause", () => { const cause = new Error("original error"); const p = new Panic({ message: "wrapped", cause }); expect(p.cause).toBe(cause); expect(p.stack).toContain("Caused by:"); }); it("creates Panic without cause", () => { const p = new Panic({ message: "no cause" }); expect(p.cause).toBeUndefined(); }); }); describe("toJSON", () => { it("serializes Panic to JSON", () => { const p = new Panic({ message: "test" }); const json = p.toJSON(); expect(json).toMatchObject({ _tag: "Panic", name: "Panic", message: "test", }); }); it("serializes Panic with Error cause", () => { const cause = new Error("cause"); const p = new Panic({ message: "test", cause }); const json = p.toJSON(); expect(json).toMatchObject({ _tag: "Panic", message: "test", cause: { name: "Error", message: "cause", }, }); }); it("serializes Panic with non-Error cause", () => { const p = new Panic({ message: "test", cause: "string cause" }); const json = p.toJSON(); expect(json).toMatchObject({ _tag: "Panic", message: "test", cause: "string cause", }); }); }); }); describe("isPanic", () => { it("returns true for Panic instances", () => { const p = new Panic({ message: "test" }); expect(isPanic(p)).toBe(true); }); it("returns false for regular errors", () => { const e = new Error("test"); expect(isPanic(e)).toBe(false); }); it("returns false for non-errors", () => { expect(isPanic("string")).toBe(false); expect(isPanic(null)).toBe(false); expect(isPanic(undefined)).toBe(false); expect(isPanic({})).toBe(false); }); }); describe("panic", () => { it("throws Panic with message", () => { expect(() => panic("test message")).toThrow(Panic); try { panic("test message"); } catch (e) { expect(isPanic(e)).toBe(true); if (isPanic(e)) { expect(e.message).toBe("test message"); } } }); it("throws Panic with cause", () => { const cause = new Error("original"); try { panic("wrapped", cause); } catch (e) { expect(isPanic(e)).toBe(true); if (isPanic(e)) { expect(e.message).toBe("wrapped"); expect(e.cause).toBe(cause); } } }); });