UNPKG

@dbs-portal/core-api

Version:

HTTP client and API utilities for DBS Portal

221 lines 10.3 kB
/** * Example MSW integration tests */ import { describe, it, expect, afterEach, afterAll } from 'vitest'; import { http, HttpResponse } from 'msw'; import { setupMSWTesting, mockHelpers, testFactories, testAssertions } from './test-utils'; import { createApiClient } from '../../client/factory'; import { createApiUrl, MSW_HEADERS } from './msw-utils'; describe('MSW Integration Examples', () => { const msw = setupMSWTesting(); afterEach(() => { msw.cleanup(); }); afterAll(() => { msw.teardown(); }); describe('Basic API Mocking', () => { it('should mock a simple GET request', async () => { // Add custom handler for this test msw.addHandlers(http.get(createApiUrl('/api/test'), () => { return HttpResponse.json(mockHelpers.success({ message: 'Hello from mock!' })); })); const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); const response = await client.get('/api/test'); expect(testAssertions.isSuccessResponse(response.data)).toBe(true); expect(response.data.data.message).toBe('Hello from mock!'); }); it('should mock a POST request with validation', async () => { msw.addHandlers(http.post(createApiUrl('/api/users'), async ({ request }) => { const body = await request.json(); if (!body.email) { return HttpResponse.json(mockHelpers.validationError([ { field: 'email', message: 'Email is required' } ]), { status: 422 }); } const user = testFactories.user({ email: body.email }); return HttpResponse.json(mockHelpers.success(user), { status: 201 }); })); const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); // Test validation error try { await client.post('/api/users', {}); } catch (error) { expect(error.response.status).toBe(422); expect(testAssertions.isErrorResponse(error.response.data)).toBe(true); } // Test successful creation const response = await client.post('/api/users', { email: 'test@example.com' }); expect(response.status).toBe(201); expect(testAssertions.isSuccessResponse(response.data)).toBe(true); expect(response.data.data.email).toBe('test@example.com'); }); }); describe('Authentication Mocking', () => { it('should mock login flow', async () => { const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); // Test login const loginResponse = await client.post('/api/auth/login', { email: 'test@example.com', password: 'password123' }); expect(testAssertions.isSuccessResponse(loginResponse.data)).toBe(true); expect(loginResponse.data.data.tokens.accessToken).toBeDefined(); expect(loginResponse.data.data.user.email).toBe('test@example.com'); // Test authenticated request const token = loginResponse.data.data.tokens.accessToken; const meResponse = await client.get('/api/auth/me', { headers: { Authorization: `Bearer ${token}` } }); expect(testAssertions.isSuccessResponse(meResponse.data)).toBe(true); expect(meResponse.data.data.email).toBe('test@example.com'); }); it('should handle invalid credentials', async () => { const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); try { await client.post('/api/auth/login', { email: 'wrong@example.com', password: 'wrongpassword' }); } catch (error) { expect(error.response.status).toBe(400); expect(testAssertions.isErrorResponse(error.response.data)).toBe(true); expect(error.response.data.errors[0].code).toBe('INVALID_CREDENTIALS'); } }); }); describe('CRUD Operations', () => { it('should mock CRUD operations for users', async () => { // Add CRUD handlers for users const users = []; let nextId = 1; msw.addHandlers( // GET /api/users - List users http.get(createApiUrl('/api/users'), ({ request }) => { const url = new URL(request.url); const page = Number.parseInt(url.searchParams.get('page') || '1', 10); const pageSize = Number.parseInt(url.searchParams.get('pageSize') || '10', 10); return HttpResponse.json(mockHelpers.paginated(users, page, pageSize)); }), // POST /api/users - Create user http.post(createApiUrl('/api/users'), async ({ request }) => { const body = await request.json(); const user = testFactories.user({ ...body, id: `user_${nextId++}` }); users.push(user); return HttpResponse.json(mockHelpers.success(user), { status: 201 }); }), // GET /api/users/:id - Get user by ID http.get(createApiUrl('/api/users/:id'), ({ params }) => { const user = users.find(u => u.id === params['id']); if (!user) { return HttpResponse.json(mockHelpers.error('User not found', 'NOT_FOUND'), { status: 404 }); } return HttpResponse.json(mockHelpers.success(user)); }), // PUT /api/users/:id - Update user http.put(createApiUrl('/api/users/:id'), async ({ params, request }) => { const userIndex = users.findIndex(u => u.id === params['id']); if (userIndex === -1) { return HttpResponse.json(mockHelpers.error('User not found', 'NOT_FOUND'), { status: 404 }); } const body = await request.json(); users[userIndex] = { ...users[userIndex], ...body, updatedAt: new Date().toISOString() }; return HttpResponse.json(mockHelpers.success(users[userIndex])); }), // DELETE /api/users/:id - Delete user http.delete(createApiUrl('/api/users/:id'), ({ params }) => { const userIndex = users.findIndex(u => u.id === params['id']); if (userIndex === -1) { return HttpResponse.json(mockHelpers.error('User not found', 'NOT_FOUND'), { status: 404 }); } users.splice(userIndex, 1); return HttpResponse.json(mockHelpers.success(null), { status: 204 }); })); const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); // Test create const createResponse = await client.post('/api/users', { email: 'new@example.com', firstName: 'New', lastName: 'User' }); expect(createResponse.status).toBe(201); expect(testAssertions.isSuccessResponse(createResponse.data)).toBe(true); const userId = createResponse.data.data.id; // Test get by ID const getResponse = await client.get(`/api/users/${userId}`); expect(testAssertions.isSuccessResponse(getResponse.data)).toBe(true); expect(getResponse.data.data.email).toBe('new@example.com'); // Test list const listResponse = await client.get('/api/users'); expect(testAssertions.isPaginatedResponse(listResponse.data)).toBe(true); expect(listResponse.data.data.items).toHaveLength(1); // Test update const updateResponse = await client.put(`/api/users/${userId}`, { firstName: 'Updated' }); expect(testAssertions.isSuccessResponse(updateResponse.data)).toBe(true); expect(updateResponse.data.data.firstName).toBe('Updated'); // Test delete const deleteResponse = await client.delete(`/api/users/${userId}`); expect(deleteResponse.status).toBe(204); // Verify deletion try { await client.get(`/api/users/${userId}`); } catch (error) { expect(error.response.status).toBe(404); } }); }); describe('Error Simulation', () => { it('should simulate network errors', async () => { msw.addHandlers(http.get(createApiUrl('/api/network-error'), () => { return HttpResponse.error(); })); const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); try { await client.get('/api/network-error'); } catch (error) { expect(error.code).toBe('ERR_NETWORK'); } }); it('should simulate server errors', async () => { msw.addHandlers(http.get(createApiUrl('/api/server-error'), () => { return HttpResponse.json(mockHelpers.error('Internal server error', 'INTERNAL_ERROR'), { status: 500 }); })); const client = createApiClient({ baseURL: 'http://localhost:3000', headers: MSW_HEADERS }); try { await client.get('/api/server-error'); } catch (error) { expect(error.response.status).toBe(500); expect(testAssertions.isErrorResponse(error.response.data)).toBe(true); } }); }); }); //# sourceMappingURL=example.test.js.map