import { describe, it, expect, beforeAll, beforeEach, afterAll } from 'bun:test' import type { FastifyInstance } from 'fastify' import { createTestApp, cleanDb, seedTestCompany, registerAndLogin, } from '../../../src/test/helpers.js' describe('Category routes', () => { let app: FastifyInstance let token: string beforeAll(async () => { app = await createTestApp() }) beforeEach(async () => { await cleanDb(app) await seedTestCompany(app) const auth = await registerAndLogin(app) token = auth.token }) afterAll(async () => { await app.close() }) it('creates a category', async () => { const response = await app.inject({ method: 'POST', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Guitars', description: 'All guitars', sortOrder: 1 }, }) expect(response.statusCode).toBe(201) expect(response.json().name).toBe('Guitars') expect(response.json().sortOrder).toBe(1) }) it('creates a child category', async () => { const parentRes = await app.inject({ method: 'POST', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Instruments' }, }) const parentId = parentRes.json().id const childRes = await app.inject({ method: 'POST', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Brass', parentId }, }) expect(childRes.statusCode).toBe(201) expect(childRes.json().parentId).toBe(parentId) }) it('lists categories sorted by sortOrder', async () => { await app.inject({ method: 'POST', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Zzz Last', sortOrder: 99 }, }) await app.inject({ method: 'POST', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Aaa First', sortOrder: 1 }, }) const response = await app.inject({ method: 'GET', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, }) expect(response.statusCode).toBe(200) const body = response.json() expect(body.data.length).toBe(2) expect(body.data[0].name).toBe('Aaa First') }) it('soft-deletes a category', async () => { const createRes = await app.inject({ method: 'POST', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, payload: { name: 'To Delete' }, }) const delRes = await app.inject({ method: 'DELETE', url: `/v1/categories/${createRes.json().id}`, headers: { authorization: `Bearer ${token}` }, }) expect(delRes.json().isActive).toBe(false) const listRes = await app.inject({ method: 'GET', url: '/v1/categories', headers: { authorization: `Bearer ${token}` }, }) expect(listRes.json().data.length).toBe(0) }) }) describe('Supplier routes', () => { let app: FastifyInstance let token: string beforeAll(async () => { app = await createTestApp() }) beforeEach(async () => { await cleanDb(app) await seedTestCompany(app) const auth = await registerAndLogin(app, { email: `supplier-${Date.now()}@test.com` }) token = auth.token }) afterAll(async () => { await app.close() }) it('creates a supplier', async () => { const response = await app.inject({ method: 'POST', url: '/v1/suppliers', headers: { authorization: `Bearer ${token}` }, payload: { name: 'RS Musical', contactName: 'Bob Smith', email: 'bob@rsmusical.com', paymentTerms: 'Net 30', }, }) expect(response.statusCode).toBe(201) expect(response.json().name).toBe('RS Musical') expect(response.json().paymentTerms).toBe('Net 30') }) it('searches suppliers by name', async () => { await app.inject({ method: 'POST', url: '/v1/suppliers', headers: { authorization: `Bearer ${token}` }, payload: { name: "Ferree's Tools" }, }) await app.inject({ method: 'POST', url: '/v1/suppliers', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Allied Supply' }, }) const response = await app.inject({ method: 'GET', url: '/v1/suppliers?q=ferree', headers: { authorization: `Bearer ${token}` }, }) expect(response.statusCode).toBe(200) expect(response.json().data.length).toBe(1) expect(response.json().data[0].name).toBe("Ferree's Tools") }) it('updates a supplier', async () => { const createRes = await app.inject({ method: 'POST', url: '/v1/suppliers', headers: { authorization: `Bearer ${token}` }, payload: { name: 'Old Name' }, }) const updateRes = await app.inject({ method: 'PATCH', url: `/v1/suppliers/${createRes.json().id}`, headers: { authorization: `Bearer ${token}` }, payload: { name: 'New Name', paymentTerms: 'COD' }, }) expect(updateRes.statusCode).toBe(200) expect(updateRes.json().name).toBe('New Name') expect(updateRes.json().paymentTerms).toBe('COD') }) })