import { PermissionKey, SystemRole } from "@capakraken/shared"; import { beforeEach, describe, expect, it, vi } from "vitest"; const { createAuditEntry } = vi.hoisted(() => ({ createAuditEntry: vi.fn(), })); vi.mock("../lib/audit.js", () => ({ createAuditEntry, })); import { countryRouter } from "../router/country.js"; import { createCallerFactory } from "../trpc.js"; const createCaller = createCallerFactory(countryRouter); function createProtectedCaller( db: Record, options: { role?: SystemRole; granted?: PermissionKey[]; } = {}, ) { const { role = SystemRole.USER, granted = [] } = options; return createCaller({ session: { user: { email: "user@example.com", name: "User", image: null }, expires: "2099-01-01T00:00:00.000Z", }, db: db as never, dbUser: { id: role === SystemRole.ADMIN ? "user_admin" : "user_1", systemRole: role, permissionOverrides: granted.length > 0 ? { granted } : null, }, }); } describe("country router", () => { beforeEach(() => { createAuditEntry.mockReset(); }); it("lists countries through the protected router", async () => { const findMany = vi.fn().mockResolvedValue([ { id: "country_de", code: "DE", name: "Germany", metroCities: [] }, ]); const caller = createProtectedCaller({ country: { findMany }, }); const result = await caller.list({ isActive: true }); expect(findMany).toHaveBeenCalledWith({ where: { isActive: true }, include: { metroCities: { orderBy: { name: "asc" } } }, orderBy: { name: "asc" }, }); expect(result).toHaveLength(1); }); it("allows detailed country reads with resource-overview permission", async () => { const findFirst = vi.fn().mockResolvedValue({ id: "country_de", code: "DE", name: "Germany", isActive: true, dailyWorkingHours: 8, scheduleRules: null, metroCities: [{ id: "city_berlin", name: "Berlin", countryId: "country_de" }], _count: { resources: 4 }, }); const caller = createProtectedCaller({ country: { findUnique: vi.fn().mockResolvedValue(null), findFirst, }, }, { granted: [PermissionKey.VIEW_ALL_RESOURCES], }); const result = await caller.getByIdentifier({ identifier: "DE" }); expect(findFirst).toHaveBeenCalledWith({ where: { code: { equals: "DE", mode: "insensitive" } }, include: { metroCities: { orderBy: { name: "asc" } }, _count: { select: { resources: true } }, }, }); expect(result._count.resources).toBe(4); }); it("creates and updates countries through the admin router", async () => { const findUnique = vi .fn() .mockResolvedValueOnce(null) .mockResolvedValueOnce({ id: "country_de", code: "DE", name: "Germany", }); const create = vi.fn().mockResolvedValue({ id: "country_de", code: "DE", name: "Germany", metroCities: [], }); const update = vi.fn().mockResolvedValue({ id: "country_de", code: "DE", name: "Deutschland", metroCities: [], }); const caller = createProtectedCaller({ country: { findUnique, create, update }, }, { role: SystemRole.ADMIN, }); const created = await caller.create({ code: "DE", name: "Germany", dailyWorkingHours: 8, }); const updated = await caller.update({ id: "country_de", data: { name: "Deutschland", }, }); expect(create).toHaveBeenCalledWith({ data: { code: "DE", name: "Germany", dailyWorkingHours: 8, }, include: { metroCities: true }, }); expect(update).toHaveBeenCalledWith({ where: { id: "country_de" }, data: { name: "Deutschland" }, include: { metroCities: true }, }); expect(created.id).toBe("country_de"); expect(updated.name).toBe("Deutschland"); expect(createAuditEntry).toHaveBeenCalledTimes(2); }); });