TDD & RTL

코와->코어·2022년 5월 21일
0

세미나 자료

목록 보기
7/7

TDD

Test Driven Development 테스트 주도 개발
:작은 단위의 테스트 케이스를 작성하고 테스트를 통과하는 코드를 추가하면서 기능 구현


개발 주기

write failing test: 실패하는 테스트 코드 작성

make test pass: 테스트 코드를 성공시키기 위한 실제 코드 작성

refactor: 중복 코드 제거, 일반화 등의 리팩토링

  • 불필요한 설계를 피하고 정확한 요구 사항에 집중 가능
  • 코드를 두 번 짜야 하고 계속해서 테스트를 하면서 고쳐야 하기 때문에
    개발 속도가 느려짐

  • implementation driven test 구현 주도 테스트
    앱이 어떻게 구현되는지에 대해 테스트
  • behavior driven test 행위 주도 테스트
    사용자 경험 위주로 테스트
 <h2 class="title">제목</h2>
 
  • h2, title vs 제목


RTL

react testing library

virtual DOM이 아니라 실제 브라우저 DOM을 기준으로 테스트를 작성
-> 어떤 react 컴포넌트를 사용하는지는 의미 없고 사용자 브라우저에서 렌더링하는 콘텐츠에 관심


설치

yarn create react-app your-project-name / yarn add --dev jest (개발 의존성 옵션)

yarn add --dev @testing-library/react @testing-library/jest-dom @testing-library/user-event


환경 설정


// testConfig.js



// 각 테스트가 끝나면 다음 테스트를 위해 dom에 렌더링해둔 내용 지우기
 import "@testing-library/react/cleanup-after-each";



// jest-dom이 제공하는 기능 test runner에게 인식 
import "@testing-library/jest-dom/extend-expect";


실행

yarn test


  1. DOM에 컴포넌트를 렌더링해주는 render()

Render


  1. DOM에서 특정 영역을 선택하기 위한 쿼리 함수들

getBy : error
queryBy : null
findBy : error && await


LabelText > PlaceholderText > Text > DisplayValue > AltText > Title > Role > TestId


  1. 특정 이벤트를 발생시켜주는 fireEvent/userEvent객체


  1. Expect
    https://jestjs.io/docs/expect

apollo graphql 로 받아오는 데이터를 가짜로 받아오는 방법 MockedProvider


//LoginPage.test.js

import {fireEvent, render, screen, cleanup} from '@testing-library/react';
import LoginPage from './LoginPage';
import userEvent from '@testing-library/user-event'

// 1. 화면에 잘 그려지는가?
describe("Rendering test", () => {
  afterEach(cleanup)
  it('rendering test', () => {

    render(<LoginPage />);
    const title = screen.getByText('Log in Page');

    // const { getByText } = render(<Example />);
    // const title = getByText('Log in Page');

    expect(title).toBeInTheDocument();

    const id = screen.getByLabelText('ID');
    const pw = screen.getByLabelText('PW');
    expect(id).toBeInTheDocument();
    expect(pw).toBeInTheDocument();


    const button = screen.getByTestId('login-button');
    expect(button).toBeInTheDocument();
  })

});

describe('testing click event', () => {
  afterEach(cleanup)
  it("login fail event", () => {
    render(<LoginPage />);

    const id = screen.getByLabelText('ID');
    const pw = screen.getByLabelText('PW');
    const button = screen.getByTestId('login-button');

    expect(button).toBeDisabled();

    userEvent.type(id, 'admin')
    userEvent.type(pw, '0000')

    // fireEvent.change(id, {target: {value: 'admin'}})
    // fireEvent.change(pw, {target: {value: '0000'}})

    userEvent.click(button)

    expect(id).toHaveValue(undefined)
    expect(pw).toHaveValue(undefined)

  })

  it("login success event", () => {
    render(<LoginPage />);

    const id = screen.getByLabelText('ID');
    const pw = screen.getByLabelText('PW');
    const button = screen.getByTestId('login-button');

    expect(button).toBeDisabled();

    userEvent.type(id, 'admin')
    userEvent.type(pw, '1234')

    expect(button).toBeEnabled();

    userEvent.click(button)
    expect(screen.getByText('Hello, admin!')).toBeInTheDocument()
  })
})

참고

https://wooaoe.tistory.com/33
https://www.daleseo.com/react-testing-library/
https://testing-library.com/docs/dom-testing-library/cheatsheet/ https://fullmoon1344.tistory.com/162
https://tecoble.techcourse.co.kr/post/2021-10-22-react-testing-library/
https://learn-react-test.vlpt.us/#/

profile
풀스택 웹개발자👩‍💻✨️

0개의 댓글