Post

FEํ…Œ์ŠคํŠธ(1)

๐Ÿ“Œ์‹œ์ž‘ํ•˜๋ฉฐ

๋“œ๋””์–ด ์ด ๋‚ ์ด ์™”๋‹ค ๊ฐœ์ธ์ ์œผ๋กœ ํ”„๋ก ํŠธ์—”๋“œ ํ…Œ์ŠคํŠธ์— ํฅ๋ฏธ๊ฐ€ ์žˆ์–ด ์ธํ”„๋Ÿฐ์—์„œ ๊ฐ•์˜๋ฅผ ์ˆ˜๊ฐ•ํ–ˆ์—ˆ๊ณ , ํ•œ๋™์•ˆ์€ ํ…Œ์ŠคํŠธํ•ด๋ณผ ๋งŒํ•œ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋งŒ๋“ค์–ด ํ…Œ์ŠคํŠธ๋ฅผ ์ž‘์„ฑํ•˜๋Š” ์‹œ๊ฐ„์„ ๊ฐ€์กŒ๋‹ค.

ํ”„๋ก ํŠธ์—”๋“œ ํ…Œ์ŠคํŠธ์— ๋Œ€ํ•ด โ€œ์ •๋ง ํ•„์š”ํ•œ๊ฐ€?โ€๋ผ๋Š” ์˜๊ฒฌ๋„ ์žˆ์ง€๋งŒ, ๋‚˜๋Š” ํ…Œ์ŠคํŠธ์— ๊ธ์ •์ ์ธ ์ž…์žฅ์ด๋‹ค.

์ด์œ ๋Š”, ๊ทœ๋ชจ๊ฐ€ ํฐ ํ”„๋กœ์ ํŠธ ์ง„ํ–‰์‹œ ์˜ˆ์ƒ์น˜ ๋ชปํ•œ ์‚ฌ์ด๋“œ ์ดํŽ™ํŠธ๋ฅผ ์ตœ๋Œ€ํ•œ ์ค„์ด๊ณ  ์‹ถ๋‹ค๋Š” ๊ฒƒ๊ณผ, ํ…Œ์ŠคํŠธ ์ž‘์„ฑ์„ ํ†ตํ•ด ๋” ๋‚˜์€ ์ปดํฌ๋„ŒํŠธ ๊ตฌ์กฐ๋ฅผ ๋งŒ๋“ค ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ–ˆ๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค.๐Ÿค”

๊ทธ๋ž˜์„œ vitest์™€ react Testing Library๋ฅผ ์‚ฌ์šฉํ•ด ํ…Œ์ŠคํŠธํ–ˆ๋˜ ๋‚ด์šฉ์„ ์ „์ฒด์ ์œผ๋กœ ์ •๋ฆฌํ•ด๋ณด๊ณ ์ž ํ•œ๋‹ค.

(์•„์ง ๊ณต๋ถ€์ค‘์ด๋ผ ๋‚ด์šฉ์ด ์ •ํ™•ํ•˜์ง€ ์•Š์„ ์ˆ˜ ์žˆ๋‹ค๐Ÿ˜…)

โœ…Vitest

์ด๋ฆ„์—์„œ๋„ ์•Œ ์ˆ˜ ์žˆ๋“ฏ์ด, Vitest๋Š” Vite๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ ํ•œ ํ…Œ์ŠคํŠธ ๋„๊ตฌ๋กœ์„œ, Vite์˜ ์„ค์ • ํŒŒ์ผ์ธ vite.config.ts ํŒŒ์ผ์„ ์‚ฌ์šฉํ•˜์—ฌ ๊ฐœ๋ฐœ, ๋นŒ๋“œ, ํ…Œ์ŠคํŠธ ํ™˜๊ฒฝ์„ ์ผ๊ด€์„ฑ ์žˆ๊ฒŒ ์œ ์ง€ํ•  ์ˆ˜ ์žˆ๋‹ค.

๋˜ํ•œ, Vitest๋Š” ๊ธฐ์กด ํ…Œ์ŠคํŠธ ๋„๊ตฌ์ธ Jest์™€ ํ˜ธํ™˜๋˜๋Š” API๋ฅผ ์ œ๊ณตํ•˜๋ฉฐ, ๋ชจํ‚น, ์Šค๋ƒ…์ƒท, ์ปค๋ฒ„๋ฆฌ์ง€ ๋“ฑ ํ…Œ์ŠคํŠธ์— ํ•„์š”ํ•œ ๋‹ค์–‘ํ•œ ๊ธฐ๋Šฅ์„ ์ œ๊ณตํ•œ๋‹ค.

ํฌ๊ฒŒ Vitest์˜ ์žฅ์ ์€ ์•„๋ž˜ 4๊ฐ€์ง€๋‹ค.

  1. Vite์™€์˜ ํ†ตํ•ฉ
  2. ๋น ๋ฅธ ์†๋„
  3. ๊ฐ€๋ฒผ์›€
  4. API ํ˜ธํ™˜์„ฑ

์ด๋Ÿฌํ•œ ์žฅ์ ์„ ๋ฐ”ํƒ•์œผ๋กœ ํ…Œ์ŠคํŠธ๋Š” Vitest๋ฅผ ํ†ตํ•ด ์ ‘ํ•˜๊ฒŒ ๋˜์—ˆ๋‹ค.

โœ…React Testing Library

(React) Testing Library๋Š” ์‚ฌ์šฉ์ž ์ค‘์‹ฌ์˜ ๋ฐฉ์‹์œผ๋กœ UI ์ปดํฌ๋„ŒํŠธ๋ฅผ ํ…Œ์ŠคํŠธํ•˜๋Š” ๋ฐ ๋„์›€์„ ์ค€๋‹ค.

์˜ˆ๋ฅผ ๋“ค์–ด, Testing Library์—์„œ ์ œ๊ณตํ•˜๋Š” DOM Testing Library๋Š” DOM ๋…ธ๋“œ๋ฅผ ์ฟผ๋ฆฌํ•˜๊ณ  ์ƒํ˜ธ์ž‘์šฉํ•˜๋Š” ๋ฐ ์ค‘์ ์„ ๋‘๋Š”๋ฐ, ์ด๋•Œ ์‹ค์ œ ์‚ฌ์šฉ์ž๊ฐ€ ํ™”๋ฉด์„ ๋ณผ ๋•Œ, ์ฃผ๋กœ ์ƒํ˜ธ์ž‘์šฉํ•˜๋Š” ์š”์†Œ์ธ ํ…์ŠคํŠธ, ๋ ˆ์ด๋ธ”, ๋˜๋Š” ์ ‘๊ทผ์„ฑ ์†์„ฑ(aria-label ๋“ฑ)์„ ์ด์šฉํ•ด getByText, getByRole, getByLabelText ๊ฐ™์€ ์ฟผ๋ฆฌ ๋ฉ”์„œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ DOM ์š”์†Œ์— ์ ‘๊ทผํ•˜๋„๋ก ๊ถŒ์žฅํ•˜๊ณ  ์žˆ๋‹ค.

โœ…Vitest์™€ React Testing Library

Vitest๋Š” ๋น ๋ฅด๊ณ  ๊ฐ„ํŽธํ•œ ํ…Œ์ŠคํŠธ๋ฅผ ๊ฐ€๋Šฅํ•˜๊ฒŒ ํ•ด์ฃผ๊ณ , Testing Library๋Š” ์‹ค์ œ ์‚ฌ์šฉ์ž๊ฐ€ ์›น์„ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ์‹์„ ๊ธฐ๋ฐ˜์œผ๋กœ ํ…Œ์ŠคํŠธํ•  ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์—, ์ด ๋‘ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ์˜ ์žฅ์ ์„ ๋ชจ๋‘ ํ™œ์šฉํ•ด FE ํ…Œ์ŠคํŠธ๋ฅผ ์ž‘์„ฑํ•œ๋‹ค.

โœ…์„ค์น˜

๋‚˜๋Š” ํ˜„์žฌ Next.js๋ฅผ ๊ฐ€์žฅ ๋งŽ์ด ์‚ฌ์šฉํ•˜๊ณ  ์žˆ๊ธฐ ๋•Œ๋ฌธ์—, Next.js ๊ณต์‹๋ฌธ์„œ์—์„œ ์ œ์•ˆํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์‹œ๋„ํ–ˆ๋‹ค. pagesํด๋”์™€ appํด๋” ๋ชจ๋‘ ์ƒ์„ฑ๋˜๋Š”๋ฐ pages ํด๋”๋Š” ์‚ฌ์šฉํ•˜์ง€ ์•Š์•„์„œ ์‚ญ์ œํ–ˆ๋‹ค.

1
npx create-next-app@latest --example with-vitest ํด๋” ์ด๋ฆ„

์„ค์น˜๊ฐ€ ์™„๋ฃŒ๋˜์—ˆ๋‹ค๋ฉด ํ•„์š”ํ•œ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ์ถ”๊ฐ€๋กœ ์„ค์น˜ํ•ด์ค€๋‹ค. (์ด๋•Œ react testing library๋กœ ํฌํ•จ๋œ๋‹ค.)

1
2
3
npm install -D vitest @vitejs/plugin-react jsdom @testing-library/react @testing-library/dom
# or
yarn add -D vitest @vitejs/plugin-react jsdom @testing-library/react @testing-library/dom

๋‘๊ฐ€์ง€๋ฅผ ์„ค์น˜ํ•˜๋ฉด ์ž๋™์œผ๋กœ vitest.config.ts์™€ ํ•„์š”ํ•œ ๋ช…๋ น์–ด๊ฐ€ ์ž๋™์œผ๋กœ ์„ธํŒ…๋œ๋‹ค.

1
2
3
4
5
6
7
8
{
  "scripts": {
    "dev": "next dev",
    "build": "next build",
    "start": "next start",
    "test": "vitest"
  }
}

โœ… Vitest ์ต์Šคํ…์…˜

vs code์—์„œ test๋ฅผ ์‰ฝ๊ฒŒ ์‹คํ–‰ํ•˜๊ณ  ํ™•์ธํ•˜๊ธฐ ์œ„ํ•ด Vitest ์ต์Šคํ…์…˜์„ ์„ค์น˜ํ•ด์ฃผ์—ˆ๋‹ค.

์‚ฌ์šฉ ๋ฒ„์ „์€ v1.0.7์œผ๋กœ, ์ž‘์„ฑํ•˜๋Š” ํ˜„์žฌ ์ตœ์‹ ์€ v1.2.8์ด์ง€๋งŒ ์ „์— ์„ค์น˜ํ•  ๋‹น์‹œ ์ž‘์„ฑํ•œ ํ…Œ์ŠคํŠธ๋ฅผ ์ œ๋Œ€๋กœ ์žก์•„๋‚ด์ง€ ๋ชปํ•˜๋Š” ๋ฌธ์ œ๊ฐ€ ์žˆ์—ˆ๊ณ , stack oveflow์—์„œ ๊ฐ™์€ ๋ฌธ์ œ๋ฅผ ๊ฒช๊ณ  ์žˆ๋Š” ์‚ฌ๋žŒ๋“ค์˜ ์กฐ์–ธ์— ๋”ฐ๋ผ ๋ฒ„์ „์„ ๋‹ค์šด๊ทธ๋ ˆ์ด๋“œ ํ•ด ์ง„ํ–‰ํ–ˆ๋‹ค.

โœ…Test code ํŒŒ์ผ๋ช…

test ์ฝ”๋“œ๋Š” ์ปดํฌ๋„ŒํŠธ์ด๋ฆ„.test.tsx ๋˜๋Š” ์ปดํฌ๋„ŒํŠธ์ด๋ฆ„.spec.tsx ํ˜•์‹์œผ๋กœ ์ž‘์„ฑํ•œ๋‹ค. test๋Š” ์•Œ๊ฒ ๋Š”๋ฐ spec์€ ๋ฌด์Šจ ์ด์œ ์—์„œ ์‚ฌ์šฉํ•˜๊ฒŒ ๋˜์—ˆ๋Š”์ง€ ์ฐพ์•„๋ณด์•˜๋Š”๋ฐ,

  • test.tsx: ํ…Œ์ŠคํŠธ ํŒŒ์ผ์ž„์„ ๋‚˜ํƒ€๋‚ด๋Š” ์ผ๋ฐ˜์ ์ธ ์˜๋ฏธ
  • spec.tsx: โ€œspecificationโ€์˜ ์•ฝ์ž๋กœ, ํŠน์ • ์ปดํฌ๋„ŒํŠธ๋‚˜ ํ•จ์ˆ˜์˜ ๋™์ž‘์„ ์„ค๋ช…ํ•˜๋Š” ํ…Œ์ŠคํŠธ๋ฅผ ์˜๋ฏธ

ํ•œ๋‹ค๊ณ  ํ•œ๋‹ค. ์ด ๋ถ€๋ถ„์€ ํŒ€์›๊ณผ ์ƒ์˜ํ•ด์„œ ํ†ต์ผํ•˜๋ฉด ์ข‹์„ ๋“ฏ ํ•˜๋‹ค.

โœ…๋‹จ์œ„ ํ…Œ์ŠคํŠธ

ํ…Œ์ŠคํŠธ๋ฅผ ์ง„ํ–‰ํ•˜๊ธฐ ์•ž์„œ, ํ…Œ์ŠคํŠธ๋ฅผ ์ง€์นญํ•˜๋Š” ์šฉ์–ด๋ฅผ ์งš๊ณ  ๋„˜์–ด๊ฐ€๋ณด์ž. ๋‹จ์œ„ ํ…Œ์ŠคํŠธ (Unit Test) ๋ž€ ์•ฑ์—์„œ ๊ฐœ๋ณ„์ ์ธ ์ž‘์€ ๋‹จ์œ„(ํ•จ์ˆ˜๋‚˜ ๋ฉ”์„œ๋“œ, ์ปดํฌ๋„ŒํŠธ)๋ฅผ ๋…๋ฆฝ์ ์œผ๋กœ ํ…Œ์ŠคํŠธํ•˜๋Š”๊ฒƒ์„ ๋งํ•œ๋‹ค. ์ „์ฒด ์‹œ์Šคํ…œ๋ณด๋‹ค๋Š” ํŠน์ • ์ž‘์€ ๋‹จ์œ„์— ๋Œ€ํ•œ ํ…Œ์ŠคํŠธ๋ผ๋Š” ํŠน์ง•์ด ์žˆ๋‹ค.

๋ณดํ†ต ๊ณตํ†ต ์ปดํฌ๋„ŒํŠธ๋Š” ๋‹จ์œ„ ํ…Œ์ŠคํŠธ์— ์ ํ•ฉํ•œ๋ฐ, ๋‹ค๋ฅธ ์ปดํฌ๋„ŒํŠธ์™€์˜ ์˜์กด์„ฑ์ด ์ ๊ณ , ์ž์ฃผ ์‚ฌ์šฉ๋˜๊ธฐ ๋•Œ๋ฌธ์— ์•ˆ์ •์„ฑ์„ ๋†’์ผ ํ•„์š”๊ฐ€ ์žˆ๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค.

โœ…ํ†ตํ•ฉ ํ…Œ์ŠคํŠธ

ํ†ตํ•ฉ ํ…Œ์ŠคํŠธ(Integration Test) ๋Š” ์—ฌ๋Ÿฌ ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ํ•จ๊ป˜ ๋™์ž‘ํ•ด์•ผ ํ•  ๋•Œ ์˜ฌ๋ฐ”๋ฅธ ์ƒํ˜ธ์ž‘์šฉ์ด ์ด๋ฃจ์–ด์ง€๋Š”์ง€ ํ™•์ธํ•˜๋Š” ๋ฐฉ์‹์ด๋‹ค. ์ฆ‰, ๋‹จ์œ„ ํ…Œ์ŠคํŠธ๋ณด๋‹ค ์กฐ๊ธˆ ๋” ํฐ ๋ฒ”์œ„์˜ ๊ฒƒ์„ ํ…Œ์ŠคํŠธํ•˜๋Š” ๊ฒƒ์œผ๋กœ, ๋‹จ์œ„ ํ…Œ์ŠคํŠธ๋งŒ์œผ๋กœ๋Š” ์ „์ฒด ์‹œ์Šคํ…œ์˜ ๋™์ž‘์„ ๊ฒ€์ฆํ•  ์ˆ˜ ์—†๊ธฐ ๋•Œ๋ฌธ์—, ์—ฌ๋Ÿฌ ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ํ•จ๊ป˜ ๋™์ž‘ํ•  ๋•Œ ๋ฐœ์ƒํ•˜๋Š” ์˜ค๋ฅ˜๋ฅผ ๋ฐฉ์ง€ํ•  ์ˆ˜ ์žˆ๋‹ค.

๐Ÿ—‚๏ธ์ฐธ๊ณ  ์‚ฌ์ดํŠธ

This post is licensed under CC BY 4.0 by the author.