import { describe, it, expect, vi, beforeEach } from 'vitest'; import { StoresService } from './stores.service.js'; describe(StoresService.name, () => { const mockRepo = { findByHousehold: vi.fn(), findById: vi.fn(), create: vi.fn(), update: vi.fn(), deactivate: vi.fn(), }; let service: StoresService; beforeEach(() => { vi.clearAllMocks(); service = new StoresService({ storesRepository: mockRepo as never }); }); describe('list', () => { it('delegates to repository', async () => { const result = { data: [], pagination: { cursor: null, hasMore: false } }; mockRepo.findByHousehold.mockResolvedValue(result); const response = await service.list('hh1', { limit: 20 }); expect(response).toEqual(result); expect(mockRepo.findByHousehold).toHaveBeenCalledWith('hh1', { limit: 20 }); }); }); describe('getById', () => { it('returns store when found', async () => { const store = { _id: 'st-1', name: 'Walgreens' }; mockRepo.findById.mockResolvedValue(store); expect(await service.getById('st-1', 'hh1')).toEqual(store); }); it('throws NotFoundError when not found', async () => { mockRepo.findById.mockResolvedValue(null); await expect(service.getById('missing', 'hh1')).rejects.toThrow('Store not found'); }); }); describe('create', () => { it('delegates to repository', async () => { const store = { _id: 'st-1', name: 'CVS' }; mockRepo.create.mockResolvedValue(store); const result = await service.create({ name: 'CVS', tags: [], isActive: true } as never, 'hh1', 'user-1'); expect(result).toEqual(store); expect(mockRepo.create).toHaveBeenCalledWith(expect.anything(), 'hh1', 'user-1'); }); }); describe('update', () => { it('updates and returns store', async () => { mockRepo.findById.mockResolvedValue({ _id: 'st-1' }); const updated = { _id: 'st-1', name: 'CVS' }; mockRepo.update.mockResolvedValue(updated); const result = await service.update('st-1', 'hh1', { name: 'CVS' }); expect(result).toEqual(updated); }); it('throws NotFoundError on initial lookup failure', async () => { mockRepo.findById.mockResolvedValue(null); await expect(service.update('missing', 'hh1', {})).rejects.toThrow('Store not found'); }); it('throws NotFoundError when update returns null', async () => { mockRepo.findById.mockResolvedValue({ _id: 'st-1' }); mockRepo.update.mockResolvedValue(null); await expect(service.update('st-1', 'hh1', {})).rejects.toThrow('Store not found'); }); }); describe('deactivate', () => { it('deactivates and returns store', async () => { mockRepo.findById.mockResolvedValue({ _id: 'st-1' }); const deactivated = { _id: 'st-1', isActive: false }; mockRepo.deactivate.mockResolvedValue(deactivated); const result = await service.deactivate('st-1', 'hh1'); expect(result).toEqual(deactivated); expect(mockRepo.deactivate).toHaveBeenCalledWith('st-1', 'hh1'); }); it('throws NotFoundError when store not found', async () => { mockRepo.findById.mockResolvedValue(null); await expect(service.deactivate('missing', 'hh1')).rejects.toThrow('Store not found'); }); it('throws NotFoundError when deactivate returns null', async () => { mockRepo.findById.mockResolvedValue({ _id: 'st-1' }); mockRepo.deactivate.mockResolvedValue(null); await expect(service.deactivate('st-1', 'hh1')).rejects.toThrow('Store not found'); }); }); });