- MSW
- MSW setting
- MSW를 활용한 간단한 testing
Mock by intercepting requests on the network level. Seamlessly reuse the same mock definition for testing, development, and debugging.
API Mocking 라이브러리
로써, 서버로 향하는 네트워크 요청을 가로채서 모의 응답을 보내주는 역할
을 수행 -> Service Worker를 통해 HTTP 요청을 가로챈다.API를 네트워크 수준에서 Mocking이 가능
하다.비동기 데이터 작업
이 필수로 존재하게 된다.요구사항을 파악하며 API 스펙
에 대해 이야기를 하게 된다.백엔드 개발자는 API를 설계
하고 프론트엔드 개발자는 설계된 API를 통해 데이터 Fetching 작업을 통해 얻은 데이터를 브라우저에 렌더링
시킨다.테스팅도 해야하며, 기획자에게 진행 사항을 공유
해야하기 때문에 백엔드 개발자를 기다리고 있을 수는 없다.
API가 설계 되기 전에 데이터 작업을 테스팅 하기 위한 도구가 필요
한데, 그것이 바로 MSW
이다.MSW가 제공하는 과정은 다음과 같다.
- 클라이언트 측에서 서버 측에 요청
- Service Worker에선 해당하는 실제 요청을 복사
- MSW에게 해당 요청과 일치하는 모의 응답을 제공 받고 이를 브라우저에게 그대로 전달
이러한 과정을 통해, 실제 서버 존재 여부와 상관없이 실제 요청으로 이어지지 않고 예상 할 수 있는 요청에 대해 Mocking이 가능
하다.
즉, 서버를 직접 만들 필요 없이
msw 라이브러리를 통해 실제 요청을 가로 챈 후 모의 응답을 브라우저 측에 제공
하여 마치 실제 http 통신을 하는 거 같은 경험을 개발자에게 제공
한다.
그렇기 때문에, 프론트엔드 개발자는 백엔드 개발자의 API 설계를 기다릴 필요 없이 msw를 통해 데이터 패칭 관련 테스팅을 진행
할 수 있다.
npm install msw --save-dev
yarn add msw
handler.ts
import { rest } from 'msw';
export const handlers = [
rest.get('http://localhost:5000/products', (req, res, ctx) => {
return res(
ctx.status(200),
ctx.json([
{
name: 'America',
imagePath: 'images/america.jpeg',
},
{
name: 'England',
imagePath: 'images/england.jpeg',
},
])
);
})
모의 응답을 제공할 handler를 setting
한다.url, 콜백 함수
가 필요하다.request, response, context
총 3개의 매개변수가 필요한데, request는 매칭 요청에 대한 정보
, response는 모의 응답을 생성하는 기능적 유틸리티
, context는 모의 응답의 상태 코드, 헤더, 본문 등을 설정
하는데 도움을 준다.status나 필요한 데이터를 return
한다.import { setupWorker } from 'msw';
import { handlers } from './handlers';
export const worker = setupWorker(...handlers);
import { setupServer } from 'msw/node';
import { handlers } from './handlers';
export const server = setupServer(...handlers);
jest로 테스팅할 땐 node 환경에서 돌아가기 때문
에 server 파일을 만들었다.npx msw init public/ --save
서비스 워커를 브라우저에 등록
한다.if (process.env.NODE_ENV === 'development') {
worker.start();
}
브라우저에서 service worker가 잘 동작하는 지 체크
하기 위해 추가해준다.mocking enabled
가 뜬다면 잘 연결 된 것import { server } from './server';
import '@testing-library/jest-dom';
export function mockServer() {
beforeAll(() => server.listen());
afterEach(() => server.restoreHandlers());
afterAll(() => server.close());
}
필요한 test 파일에서만 testing할 수 있도록 진행
import { render, screen } from '@testing-library/react';
import OrderComponent from '../../../components/OrderPage/OrderComponent';
import { mockServer } from '../../../utils/mocks/setUpTest';
describe('Product component test', () => {
mockServer();
test('check rendering image from server', async () => {
render(OrderComponent());
const productImages = await screen.findAllByRole('img', {
name: /product/i,
});
expect(productImages).toHaveLength(2);
});
});
axiosError가 되어 fail
이 된 것을 확인 할 수 있었다.