Next.js 15 + Playwright 도입 – E2E 테스트랑 조금 친해지기

2024. 11. 24. 22:37·FrontEnd/Testing

Next.js 15를 공부하면서 "이왕 하는 김에 테스트도 손에 익혀 보자" 싶어서
Playwright를 같이 붙이기 시작했다.

이번 글은 거창한 튜토리얼이라기보다는
"처음 깔고, 최소한의 설정을 하고, 내 페이지 하나를 실제로 눌러 본 기록"에 가깝다.


결론 먼저

  • Next.js 15 프로젝트에 Playwright를 붙이는 것만 보면 어렵지 않았다
  • pnpm create playwright로 설치하면 초기 설정 파일까지 한 번에 만들어 준다
  • playwright.config.ts에서 dev 서버만 Next에 맞게 지정해 주면 바로 테스트를 돌릴 수 있다
  • getByTestId를 쓰면 Tailwind 기반 UI에서도 꽤 편하게 요소를 찾을 수 있다
  • pnpm exec playwright show-report로 HTML 리포트를 바로 확인할 수 있어서,
    테스트 결과를 브라우저로 보는 경험이 생각보다 괜찮았다

0. 이번 글에서 하는 것

이 글에서 정리하는 내용은 대략 이렇다.

  • Playwright 설치 방법 정리 (pnpm 기준)
  • Next.js 15 dev 서버에 맞춘 최소 playwright.config.ts 설정
  • 다이얼로그 열고 닫히는지 확인하는 첫 테스트 코드
  • data-testid와 getByTestId로 요소를 잡는 패턴
  • 테스트 리포트 보는 방법과, 앞으로 자주 쓸 것 같은 API 메모

공식 문서는 여기들을 참고했다.

  • Next.js + Playwright 한글 문서
    • https://nextjs-ko.org/docs/pages/building-your-application/testing/playwright
  • Playwright 공식 문서
    • https://playwright.dev/docs/intro

1. 설치 – pnpm 기준

처음에는 "설치부터 헷갈리면 귀찮아져서 안 하게 되겠지" 싶어서, 일단 명령어부터 정리했다.

# (옵션) 처음부터 Playwright 템플릿까지 같이 만들고 싶을 때
pnpm create playwright

# 내가 사용한 방식 – Next.js 프로젝트에 테스트 러너만 추가
pnpm install -D @playwright/test

# Playwright에서 사용하는 브라우저 엔진 설치
pnpm exec playwright install

# 기본 테스트 실행 (headless)
pnpm exec playwright test

# HTML 리포트 보기
pnpm exec playwright show-report

# UI 모드로 테스트 실행
pnpm exec playwright test --ui

 

내 경우에는 처음 도입이라 pnpm create playwright를 사용했고, 테스트 폴더와 예제 파일, 설정 파일이 한 번에 만들어졌다.


2. 최소 설정 – Next dev 서버 붙이기

설치 후에 큰 설정을 건드리지는 않았고,
처음 테스트를 돌리기 위해서는 dev 서버 설정만 Next에 맞게 잡아 주면 됐다.

playwright.config.ts에서 webServer 부분만 다음처럼 수정했다.

// playwright.config.ts 일부

webServer: {
  command: "pnpm run dev",
  url: "http://localhost:3000",
  reuseExistingServer: !process.env.CI,
},

의도는 단순하다.

  • 테스트 실행 시 dev 서버를 자동으로 띄운다
  • 이미 떠 있는 경우에는 재사용한다
  • CI에서는 항상 새로 띄운다

여기까지만 맞춰 놓으면 pnpm exec playwright test로
Next.js 앱을 실제 브라우저에서 두드려 볼 수 있다.


3. 첫 테스트 – 다이얼로그 열리고 닫히는지 보기

내가 먼저 테스트해 본 것은 탑 네비게이션에서 열리는 다이얼로그였다.

  • 버튼을 클릭하면 다이얼로그가 올라온다
  • 다른 버튼을 누르면 다시 내려간다
  • Tailwind 클래스로 translate-y-full과 translate-y-0을 쓰고 있었다

그래서 테스트 목표는 이렇게 잡았다.

  • 처음에는 다이얼로그가 내려가 있는지 확인
  • 버튼을 클릭했을 때 올라오는지 확인
  • 닫기 버튼을 클릭했을 때 다시 내려가는지 확인
import { test, expect } from "@playwright/test";

test("탑네비게이션에서 다이얼로그 열리고 닫히는지 확인", async ({ page }) => {
  // 페이지 로드
  await page.goto("http://localhost:3000");

  // 필요한 요소들 미리 가져오기
  const openButton = page.getByTestId("address-dialog-open-button");
  const closeButton = page.getByTestId("address-dialog-close-button");
  const dialog = page.getByTestId("address-dialog");

  // 다이얼로그가 처음에는 닫혀 있는지 확인
  await expect(dialog).toHaveClass(/translate-y-full/);

  // 버튼 클릭해서 다이얼로그 열기
  await openButton.click();

  // 다이얼로그가 열렸는지 확인
  await expect(dialog).toHaveClass(/translate-y-0/);

  // 닫기 버튼 클릭
  await closeButton.click();

  // 다시 닫혔는지 확인
  await expect(dialog).toHaveClass(/translate-y-full/);
});

테스트 코드만 보면 딱 "사람이 직접 눌러 보는 순서" 그대로다.

  1. 페이지로 이동한다
  2. 버튼과 다이얼로그 요소를 잡는다
  3. 처음 상태를 검증한다
  4. 열기 버튼을 누른다
  5. 열린 상태를 검증한다
  6. 닫기 버튼을 누른다
  7. 닫힌 상태를 다시 검증한다

4. getByTestId와 data-testid – Tailwind에서 특히 편했다

처음에는 "클래스로 잡을까, 텍스트로 잡을까" 고민하다가,
공식 문서에서 소개하는 getByTestId를 써 보기로 했다.

Tailwind 클래스를 그대로 셀렉터로 쓰면

  • 클래스가 바뀔 때 테스트가 같이 깨지고
  • 의도와 상관없이 스타일 변경에 너무 민감해진다

그래서 테스트 전용으로 data-testid를 박아두고
그걸 기준으로 요소를 잡는 쪽이 훨씬 편했다.

실제 컴포넌트는 이런 식으로 바꿨다.

<div
  data-testid="address-dialog"
  className={clsx(
    "fixed bottom-0 left-0 right-0 top-0 z-20 mt-2 overflow-hidden rounded-md bg-gray-300/70 transition duration-300",
    dialog ? "translate-y-0" : "translate-y-full",
  )}
>
  {/* ... */}
</div>

버튼들도 마찬가지로 data-testid를 달아 두고 사용했다.

<button data-testid="address-dialog-open-button">주소 변경</button>
<button data-testid="address-dialog-close-button">닫기</button>

이렇게 해 두면 테스트 코드에서는 언제나

page.getByTestId("address-dialog");

처럼 읽기 쉬운 형태로 요소를 가져올 수 있다.


5. 리포트 보는 흐름

테스트를 돌리고 나면, 콘솔에 이런 식으로 메시지가 뜬다.

pnpm exec playwright test

Running 3 tests using 3 workers
  3 passed (30.9s)

To open last HTML report run:

pnpm exec playwright show-report

안내에 적힌 대로 명령어를 한 번 더 실행하면 된다.

pnpm exec playwright show-report

그러면 브라우저가 열리고

  • 어떤 테스트가 있었는지
  • 어느 단계에서 실패했는지
  • 스크린샷과 타임라인은 어떻게 찍혔는지

같은 정보를 한 번에 볼 수 있다.

처음에는 그냥 콘솔에 "passed"만 뜨는 것으로도 만족했는데,
HTML 리포트를 보고 나니 차라리 여기까지 같이 보는 편이
"테스트를 돌렸다"는 느낌이 더 많이 들었다.


6. 자주 쓰게 될 것 같은 API 메모

아직은 많이 써 본 단계는 아니고,
우선 공식 문서와 샘플 코드에서 자주 보이는 것들만 정리해 놓았다.

Playwright 기본 API는 여기에서 볼 수 있다.

  • https://playwright.dev/docs/api/class-locator

내가 특히 자주 보게 된 것들만 추리면 아래 정도다.

  • page.goto() 페이지를 지정한 URL로 이동
  • page.locator() 셀렉터로 요소 찾기
  • page.getByTestId() data-testid 기반으로 요소 찾기
  • locator.click() 요소 클릭
  • expect(locator).toBeVisible() 화면에 보이는지 확인
  • expect(page).toHaveURL() 현재 URL 검증
  • expect(locator).toContainText() 특정 텍스트 포함 여부 확인
  • expect(locator).toHaveClass() 클래스에 특정 패턴이 포함되어 있는지 확인

앞으로 테스트를 더 늘리면서

  • 어떤 것은 getByRole로 잡는 것이 좋은지
  • 어떤 것은 getByText나 getByPlaceholder가 더 나은지

같은 선택 기준도 조금씩 쌓아 갈 예정.


7. 작게 남겨두는 회고

Next.js 15에 Playwright를 붙여 본 첫 느낌은 이렇다.

  • 설치와 기본 설정은 생각보다 단순했다
  • 한 번 돌아가는 테스트를 만들고 나니, UI를 직접 눌러 보는 습관을
    그대로 코드로 옮기는 느낌이라 나쁘지 않았다
  • 다만 아직은 "테스트를 구조적으로 어떻게 나눌지"까지는 감이 덜 와서,
    일단은 자주 쓰는 화면부터 하나씩 눌러 보는 수준이다
저작자표시 변경금지 (새창열림)

'FrontEnd > Testing' 카테고리의 다른 글

Next.js 15 + Playwright 2편 – API 테스트 맛보기  (0) 2024.11.25
'FrontEnd/Testing' 카테고리의 다른 글
  • Next.js 15 + Playwright 2편 – API 테스트 맛보기
프론트엔드 개발자 jbeat
프론트엔드 개발자 jbeat
프론트엔드 개발자 블로그인데 일상도 쪼그으믐
  • 프론트엔드 개발자 jbeat
    jbeat 님의 블로그
    프론트엔드 개발자 jbeat
  • 전체
    오늘
    어제
    • 분류 전체보기 (44)
      • FrontEnd (43)
        • TypeScript (6)
        • JavaScript (18)
        • Next.js (3)
        • React (1)
        • Testing (2)
        • Third Party (1)
        • web (10)
        • Tooling (1)
        • coding test (0)
        • A.I (1)
      • 일상 (1)
        • wedding (1)
  • 블로그 메뉴

    • 홈
    • 태그
    • 방명록
  • 인기 글

  • 태그

    Android
    CrossOrigin
    omit
    preconnect
    컬렉션
    Next.js
    배열
    주니어
    Utility
    타입스크립트
    고차함수
    코테
    TypeScript
    yjs
    playwright
    CRDT
    pick
    이터러블
    javascript
    WebSocket
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.5
프론트엔드 개발자 jbeat
Next.js 15 + Playwright 도입 – E2E 테스트랑 조금 친해지기
상단으로

티스토리툴바