import { describe, it, expect, vi, beforeEach } from 'vitest'; import { isHttpError } from '@sveltejs/kit'; import { createLocals, mockUser, createFormRequest } from '$lib/test-utils'; const { sendMail } = vi.hoisted(() => ({ sendMail: vi.fn() })); vi.mock('$lib/server/resend', () => ({ sendMail })); vi.mock('$lib/db', () => ({ prisma: { user: { findUnique: vi.fn() }, profile: { findFirst: vi.fn() }, licenseKey: { findMany: vi.fn(), findUnique: vi.fn(), create: vi.fn(), delete: vi.fn() } } })); import { prisma } from '$lib/db'; import { load, actions } from './+page.server'; const mockFindUnique = prisma.user.findUnique as ReturnType; const mockProfileFindFirst = prisma.profile.findFirst as ReturnType; const mockLicenseKeyCreate = prisma.licenseKey.create as ReturnType; const mockLicenseKeyFindUnique = prisma.licenseKey.findUnique as ReturnType; const mockLicenseKeyDelete = prisma.licenseKey.delete as ReturnType; describe('admin license-keys createKey action', () => { beforeEach(() => { vi.clearAllMocks(); }); it('returns records via load', async () => { const records = [{ id: 'k1', key: 'AAAA-BBBB-CCCC-DDDD' }]; (prisma.licenseKey.findMany as ReturnType).mockResolvedValue(records); const result = await load({} as any); expect(prisma.licenseKey.findMany).toHaveBeenCalledWith({ include: { user: true }, orderBy: { key: 'asc' } }); expect(result).toEqual({ records }); }); it('rejects unauthenticated requests', async () => { const locals = createLocals(); const req = createFormRequest({ email: 'jane@example.com' }); const err = await actions.createKey({ request: req, locals } as any).catch((e) => e); expect(isHttpError(err, 403)).toBe(true); }); it('returns error when email is missing', async () => { const locals = createLocals(mockUser({ roleId: 3 }) as any); const req = createFormRequest({}); const result = await actions.createKey({ request: req, locals } as any); expect(result).toEqual({ success: false, action: 'createKey', error: 'Email is required' }); }); it('creates a key with only an email when no user exists yet', async () => { mockFindUnique.mockResolvedValue(null); mockProfileFindFirst.mockResolvedValue(null); mockLicenseKeyCreate.mockResolvedValue({}); sendMail.mockResolvedValue({ id: 'email-1' }); const locals = createLocals(mockUser({ roleId: 3 }) as any); const req = createFormRequest({ email: 'nobody@example.com' }); const result = await actions.createKey({ request: req, locals } as any); expect(result).toEqual({ success: true, action: 'createKey' }); expect(mockLicenseKeyCreate).toHaveBeenCalledOnce(); const createCall = mockLicenseKeyCreate.mock.calls[0][0]; expect(createCall.data.active).toBe(true); expect(createCall.data.userId).toBeUndefined(); expect(createCall.data.email).toBe('nobody@example.com'); expect(sendMail).toHaveBeenCalledOnce(); const mailCall = sendMail.mock.calls[0][0]; expect(mailCall.to).toBe('nobody@example.com'); expect(mailCall.templateId).toBe('license-key-delivery'); expect(mailCall.data.firstName).toBe('Valued Customer'); }); it('creates a license key and sends email with license_key variable', async () => { const user = mockUser({ roleId: 3 }); const profile = { firstName: 'Jane' }; mockFindUnique.mockResolvedValue(user); mockProfileFindFirst.mockResolvedValue(profile); mockLicenseKeyCreate.mockResolvedValue({}); sendMail.mockResolvedValue({ id: 'email-1' }); const locals = createLocals(user as any); const req = createFormRequest({ email: user.email }); const result = await actions.createKey({ request: req, locals } as any); expect(result).toEqual({ success: true, action: 'createKey' }); expect(mockLicenseKeyCreate).toHaveBeenCalledOnce(); const createCall = mockLicenseKeyCreate.mock.calls[0][0]; expect(createCall.data.key).toMatch(/^[A-Z0-9]{4}-[A-Z0-9]{4}-[A-Z0-9]{4}-[A-Z0-9]{4}$/); expect(createCall.data.active).toBe(true); expect(createCall.data.userId).toBe('user-1'); expect(sendMail).toHaveBeenCalledOnce(); const mailCall = sendMail.mock.calls[0][0]; expect(mailCall.to).toBe(user.email); expect(mailCall.templateId).toBe('license-key-delivery'); expect(mailCall.data.license_key).toBeDefined(); expect(mailCall.data.license_key).toBe(createCall.data.key); expect(mailCall.data.firstName).toBe('Jane'); }); it('sends email with license_key even when profile is missing', async () => { const user = mockUser({ roleId: 3 }); mockFindUnique.mockResolvedValue(user); mockProfileFindFirst.mockResolvedValue(null); mockLicenseKeyCreate.mockResolvedValue({}); sendMail.mockResolvedValue({ id: 'email-1' }); const locals = createLocals(user as any); const req = createFormRequest({ email: user.email }); await actions.createKey({ request: req, locals } as any); const mailCall = sendMail.mock.calls[0][0]; expect(mailCall.templateId).toBe('license-key-delivery'); expect(mailCall.data.license_key).toBeDefined(); expect(mailCall.data.firstName).toBe('Jane Doe'); }); it('still returns success when email sending fails', async () => { const user = mockUser({ roleId: 3 }); mockFindUnique.mockResolvedValue(user); mockProfileFindFirst.mockResolvedValue({ firstName: 'Jane' }); mockLicenseKeyCreate.mockResolvedValue({}); sendMail.mockRejectedValue(new Error('Resend API down')); const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {}); const locals = createLocals(user as any); const req = createFormRequest({ email: user.email }); const result = await actions.createKey({ request: req, locals } as any); expect(result).toEqual({ success: true, action: 'createKey' }); expect(mockLicenseKeyCreate).toHaveBeenCalledOnce(); consoleSpy.mockRestore(); }); }); describe('admin license-keys replace action', () => { beforeEach(() => { vi.clearAllMocks(); }); it('rejects unauthenticated requests', async () => { const locals = createLocals(); const req = createFormRequest({ id: 'k1' }); const err = await actions.replace({ request: req, locals } as any).catch((e) => e); expect(isHttpError(err, 403)).toBe(true); }); it('returns error when id is missing', async () => { const locals = createLocals(mockUser({ roleId: 3 }) as any); const req = createFormRequest({}); const result = await actions.replace({ request: req, locals } as any); expect(result).toEqual({ success: false, action: 'replace', error: 'Missing key id' }); }); it('returns error when the key does not exist', async () => { mockLicenseKeyFindUnique.mockResolvedValue(null); const locals = createLocals(mockUser({ roleId: 3 }) as any); const req = createFormRequest({ id: 'missing' }); const result = await actions.replace({ request: req, locals } as any); expect(result).toEqual({ success: false, action: 'replace', error: 'License key not found' }); }); it('deletes the old key and creates a replacement preserving the owner', async () => { mockLicenseKeyFindUnique.mockResolvedValue({ id: 'k1', key: 'AAAA-BBBB-CCCC-DDDD', userId: 'user-1', email: null }); mockLicenseKeyDelete.mockResolvedValue({}); mockLicenseKeyCreate.mockResolvedValue({}); const locals = createLocals(mockUser({ roleId: 3 }) as any); const req = createFormRequest({ id: 'k1' }); const result = await actions.replace({ request: req, locals } as any); expect(result).toEqual({ success: true, action: 'replace' }); expect(mockLicenseKeyDelete).toHaveBeenCalledWith({ where: { id: 'k1' } }); expect(mockLicenseKeyCreate).toHaveBeenCalledOnce(); const createCall = mockLicenseKeyCreate.mock.calls[0][0]; expect(createCall.data.key).toMatch(/^[A-Z0-9]{4}-[A-Z0-9]{4}-[A-Z0-9]{4}-[A-Z0-9]{4}$/); expect(createCall.data.active).toBe(true); expect(createCall.data.userId).toBe('user-1'); expect(createCall.data.email).toBeNull(); }); });