103 lines
2.9 KiB
TypeScript
103 lines
2.9 KiB
TypeScript
import { describe, it, expect, vi, beforeEach } from 'vitest'
|
|
|
|
vi.mock('@/lib/prisma', () => ({
|
|
prisma: {
|
|
product: {
|
|
findMany: vi.fn(),
|
|
},
|
|
},
|
|
}))
|
|
|
|
vi.mock('@/lib/api-auth', () => ({
|
|
authenticateApiRequest: vi.fn(),
|
|
}))
|
|
|
|
import { prisma } from '@/lib/prisma'
|
|
import { authenticateApiRequest } from '@/lib/api-auth'
|
|
import { GET as getProducts } from '@/app/api/products/route'
|
|
|
|
const mockPrisma = prisma as unknown as {
|
|
product: { findMany: ReturnType<typeof vi.fn> }
|
|
}
|
|
const mockAuth = authenticateApiRequest as ReturnType<typeof vi.fn>
|
|
|
|
function makeRequest(): Request {
|
|
return new Request('http://localhost/api/products', {
|
|
method: 'GET',
|
|
headers: { Authorization: 'Bearer test-token' },
|
|
})
|
|
}
|
|
|
|
describe('GET /api/products', () => {
|
|
beforeEach(() => {
|
|
vi.clearAllMocks()
|
|
mockAuth.mockResolvedValue({ userId: 'user-1', isDemo: false })
|
|
})
|
|
|
|
// TC-P-04
|
|
it('returns products owned by the authenticated user', async () => {
|
|
mockPrisma.product.findMany.mockResolvedValue([
|
|
{ id: 'prod-1', name: 'Alpha', repo_url: null },
|
|
{ id: 'prod-2', name: 'Beta', repo_url: 'https://github.com/example/beta' },
|
|
])
|
|
|
|
const res = await getProducts(makeRequest())
|
|
const data = await res.json()
|
|
|
|
expect(res.status).toBe(200)
|
|
expect(data).toHaveLength(2)
|
|
expect(data[0]).toMatchObject({ id: 'prod-1', name: 'Alpha' })
|
|
expect(data[1]).toMatchObject({ id: 'prod-2', name: 'Beta' })
|
|
})
|
|
|
|
// TC-P-05
|
|
it('includes products where the user is a team member via productAccessFilter', async () => {
|
|
mockPrisma.product.findMany.mockResolvedValue([
|
|
{ id: 'prod-shared', name: 'Shared Product', repo_url: null },
|
|
])
|
|
|
|
const res = await getProducts(makeRequest())
|
|
const data = await res.json()
|
|
|
|
expect(res.status).toBe(200)
|
|
expect(data).toHaveLength(1)
|
|
expect(mockPrisma.product.findMany).toHaveBeenCalledWith(
|
|
expect.objectContaining({
|
|
where: expect.objectContaining({
|
|
archived: false,
|
|
OR: expect.arrayContaining([
|
|
{ user_id: 'user-1' },
|
|
{ members: { some: { user_id: 'user-1' } } },
|
|
]),
|
|
}),
|
|
})
|
|
)
|
|
})
|
|
|
|
// TC-P-06
|
|
it('returns empty array when user has no products', async () => {
|
|
mockPrisma.product.findMany.mockResolvedValue([])
|
|
|
|
const res = await getProducts(makeRequest())
|
|
const data = await res.json()
|
|
|
|
expect(res.status).toBe(200)
|
|
expect(data).toEqual([])
|
|
})
|
|
|
|
// TC-P-07
|
|
it('excludes archived products by querying with archived: false', async () => {
|
|
mockPrisma.product.findMany.mockResolvedValue([
|
|
{ id: 'prod-active', name: 'Active', repo_url: null },
|
|
])
|
|
|
|
const res = await getProducts(makeRequest())
|
|
|
|
expect(res.status).toBe(200)
|
|
expect(mockPrisma.product.findMany).toHaveBeenCalledWith(
|
|
expect.objectContaining({
|
|
where: expect.objectContaining({ archived: false }),
|
|
})
|
|
)
|
|
})
|
|
})
|