[기술블로그] EP8. 매주 반복하는 테스트, 나만 피곤한가요?: AI를 활용한 E2E 테스트 자동화

2026-04-16 | 개발 이야기, 사이냅 이야기

안녕하세요! 키냅스(Kynapse)에서 프론트엔트와 팀 개발환경 AX를 맡고 있는 개발자, 현승환입니다.

매주 같은 시간, 같은 사람들이 모여 같은 버튼을 누르고 같은 화면을 확인하는 일이 있었습니다.
테스트 자체가 의미 없는 건 아니었지만, 솔직히 말하면 꽤 지루했습니다.
더 문제는, 이 시간이 지나도 늘 마음 한구석이 찜찜했다는 점이었죠.

“이번 주는 진짜 다 확인된 걸까?”

문서는 있었지만 테스트 흐름은 사람의 기억에 많이 기대고 있었고,
반복되는 회귀 테스트는 팀의 집중력을 조금씩 갉아먹고 있었습니다.
그래서 이번에는 단순히 Playwright 스크립트를 몇 개 만드는 수준이 아니라,
AI가 이해할 수 있는 테스트 명세를 새로 설계하고, 그 명세를 기반으로 실제 E2E 자동화까지 연결하는 흐름을 만들었습니다.

이번 글에서는 그 과정을 정리해보려고 합니다.
기존 TC를 그대로 코드로 옮기지 않고,
왜 먼저 문서 구조부터 바꿔야 했는지,
그리고 AI 에이전트를 붙였을 때 어디서 잘 되고 어디서 막혔는지까지 현실적으로 공유해보겠습니다.

 

[EP8. 핵심 요약]

  • 기존 수동 TC 재해석
    기존 테스트 케이스는 버튼, 라벨, 호버 같은 원자 체크 중심이라 AI가 그대로 소비하기 어려웠고, 이를 사용자 목적 기반 시나리오 구조로 재구성

  • AI 친화형 E2E 명세 체계 구축
    라우트, 권한, 상태, locator, API 기대 결과까지 포함하는 YAML 기반 테스트 명세 체계를 설계하고, planner가 탐색한 결과를 generator가 코드로 변환할 수 있도록 연결

  • 진입점 가이드와 반복 개선
    도메인별 진입점과 범위를 함께 알려주자 시나리오 생성 품질이 안정되었고, 프롬프트와 스키마를 반복 개선하면서 기대 커버리지보다 넓은 테스트 자산 확보

  • 실제 자동화 운영 경험 축적
    병렬 실행 멈춤, 레거시 경로 참조, 다국어 locator 문제 같은 현실적인 장애물을 해결하며, 사람이 하던 주간 회귀 테스트를 자동화 가능한 구조로 전환

| 테스트는 매주 돌렸는데, 문서는 아무도 완전히 믿지 못했다

처음 출발점은 TC 현행 점검이었습니다.
여기서 드러난 기존 TC의 특징은 꽤 익숙했습니다.

  • 라벨 확인

  • 버튼 클릭

  • 호버, 스크롤

  • 반복 사용 시나리오

  • 권한 조건

초기 커버리지를 빠르게 확보하는 데는 나쁘지 않은 구조였습니다.
하지만 AI가 이 문서를 읽고 스스로 테스트를 만들게 하려는 순간 문제가 분명해졌습니다.

버튼은 있는데 목적이 없었습니다.
라벨은 있는데 왜 그 흐름을 검증해야 하는지 설명이 부족했습니다.
권한은 있었지만 상태 조건은 약했고,
무엇보다 이 항목이 코드 어디와 연결되는지 근거가 없었습니다.

사람은 맥락을 추론할 수 있습니다.
하지만 에이전트는 그렇지 않습니다.
에이전트에게 “버튼 클릭”은 정보가 아니라 거의 힌트 수준에 가깝습니다.

| 체크리스트를 버린 게 아니라, 한 단계 위로 올렸습니다

핵심은 기존 점검표를 폐기하는 게 아니라,
그 위에 “사용자 목적 중심 시나리오 계층”을 얹는 것이었습니다.

예를 들어 기존에는 이런 식이었습니다.

  • 사용자 정보 클릭

  • 팀 전환 메뉴 표시

  • 설정 이동

  • 로그아웃 동작

이걸 그대로 유지하면 테스트 수는 많아지는데,
전체 흐름은 잘 보이지 않습니다.
반면 시나리오 구조로 바꾸면 훨씬 선명해집니다.

“사용자가 계정 메뉴에서 필요한 행동을 끝까지 수행할 수 있는가?”

이 질문 아래에

  • 사용자 역할

  • 팀 개수

  • 선행 조건

  • 단계

  • 기대 결과

  • 예외 케이스

  • 관련 코드 근거

를 붙이기 시작하면, 문서는 더 이상 사람이 보는 체크리스트가 아니라
AI가 읽고 테스트 코드로 옮길 수 있는 명세가 됩니다.

이때 특히 중요했던 건 세 가지였습니다.

  • 권한만 보지 않고 상태 축도 함께 넣기

  • route, component, API, permission logic과 연결하기

  • locator 전략까지 미리 문서에 포함하기

결국 저희가 만들고 싶었던 건 “예쁜 QA 문서”가 아니라,
“명세에서 코드로 바로 이어지는 테스트 자산”이었습니다


| planner, generator, healer를 붙여 “문서 → 코드” 흐름을 만들다

구조를 정리한 뒤에는 PlayWright 로 tc 만들기로 본격적인 자동화를 붙였습니다.
이번 흐름에서 활용한 주인공은 Playwright의 세 가지 에이전트였습니다.

  • planner: 실제 화면을 탐색하며 테스트 계획을 세움

  • generator: 계획 문서를 Playwright 테스트 코드로 바꿈

  • healer: 실패한 테스트를 실행하며 스스로 수정 시도

여기서 중요한 건,
처음부터 generator에게 “테스트 코드 만들어”라고 던지지 않았다는 점입니다.
먼저 AI가 읽기 쉬운 테스트 명세 체계를 만들고,
그다음 planner가 앱을 탐색해서 그 구조에 맞는 시나리오를 채우게 했습니다.

실제로 이 과정에서 다음과 같은 산출물이 나왔습니다.

  • README.md: 이 명세 체계가 왜 필요한지 설명

  • schema.yaml: 시나리오 문서의 canonical schema 정의

  • index.yaml: 전체 시나리오 목록과 우선순위 정리

  • 도메인별 scenario yaml: auth, sidebar, navigation, document-management, search, settings 등

결과적으로 17개의 핵심 시나리오가 먼저 생성됐고,
이 문서들은 단순 요약이 아니라
Playwright 코드로 곧바로 변환 가능한 step, assertion, locator, precondition 정보를 담게 되었습니다.

이 순간부터 테스트 문서는 “회의 때 보는 자료”가 아니라,
에이전트가 계속 갱신하고 확장할 수 있는 운영 자산이 되기 시작했습니다.

| 진입점을 알려주자, AI가 덜 헤매기 시작했다

하지만 문서 구조만 좋아졌다고 바로 원하는 결과가 나오진 않았습니다.
진입점을 알려주고 tc 생성 시도를 하면서 또 한 번 현실을 배웠거든요.

처음에는 꽤 단순하게 생각했습니다.

“AI가 똑똑하니까 앱을 보면 알아서 다 만들겠지?”

그런데 막상 돌려보니, 화면이 한눈에 드러나는 기능은 잘 찾는데
진입 경로가 직관적이지 않거나 특정 문맥에서만 보이는 기능은 놓치는 경우가 있었습니다.
특히 대분류가 큰 기능은 AI가 지나치게 넓게 잡거나,
반대로 기대보다 좁게 생성하는 일이 반복됐습니다.

그래서 접근을 바꿨습니다.
그냥 “테스트 시나리오 만들어”가 아니라,
어떤 도메인을 대상으로 할지, 어디서 시작해야 할지, 어떤 레벨까지 포함할지를 함께 넘겨주기 시작한 것이죠.

예를 들면

  • sidebar

  • search

  • settings

  • document-management

  • research-documents

처럼 도메인을 잘게 나눠 주고,
각 도메인에 대해 최소한 아래 축을 채우게 했습니다.

  • happy path

  • 권한 분기

  • 상태 분기

  • 예외/실패 분기

  • 회귀 위험이 높은 반복 흐름

이 변화가 꽤 컸습니다.
기대한 영역만 겨우 맞추는 수준이 아니라,
오히려 저희가 수동 TC에서 놓친 구간까지 초과 커버하는 경우가 생겼습니다.
예를 들어 사이드바 영역을 기준으로 비교했을 때,
단순 메뉴 노출 수준을 넘어 실제 문서 메뉴의 동작까지 넓게 포착하는 사례도 확인할 수 있었습니다.

물론 모든 초과 커버가 다 좋은 것은 아니었습니다.
문서 메뉴처럼 별도 도메인으로 분리해야 할 영역도 발견됐고,
태그 제한이나 문서 편집 화면처럼 다른 기능군으로 넘겨야 할 테스트도 구분해야 했습니다.
하지만 바로 이 점이 오히려 좋았습니다.

테스트 자동화가 단순히 “있는 문서를 복사”하는 게 아니라,
도메인 경계를 다시 정리하게 만드는 계기가 되었기 때문입니다.

|한 번에 10개는 욕심이었다: 스크립트 생성 중 트러블 슈팅

문서를 코드로 바꾸는 단계는 가장 지루한 과정이었습니다.
AI가 자꾸 실행되다가 멈춰서 그 과정을 계속 모니터링 해야 했거든요.
정리하면 문제는 아주 “현업스러운” 것들이었습니다.

첫 번째는 잘못된 참조였습니다.
이전에 프로토타입으로 이 만들어둔 TC 생성 스킬을 참고하면서도,
builder 스킬이 이미 레거시가 된 .pipeline/tc 경로를 바라보고 있었던 거죠.
겉으로 보면 생성기가 잘 도는 것 같은데,
실제로는 오래된 구조를 참고하고 있었던 셈입니다.

두 번째는 병렬 실행이었습니다.

“빨리 끝내려면 많이 돌리면 되겠지”가 제일 위험했습니다.

처음에는 스펙 생성 작업을 10개씩 병렬로 돌렸는데,
곧바로 세션이 꼬이기 시작했습니다.

  • running이 끝나지 않음

  • seed.spec.ts를 찾지 못함

  • 순차로 하라고 해도 내부적으로 병렬처럼 멈춤

3개로 줄여도 미묘했고,
결국 순차 실행 쪽으로 조정하는 과정이 필요했습니다.
여기에 /mcp > playwright test > reconnect 같은 연결 복구 작업까지 거치면서,
“에이전트를 잘 쓰는 것”과 “도구 세션을 안정적으로 유지하는 것”은 별개의 문제라는 걸 확실히 체감했습니다.

세 번째는 locator 문제였습니다.
가장 대표적인 사례가 저장 완료 토스트였습니다.

테스트는 “Settings saved“를 기대했는데,
실제 UI는 다국어 처리된 “설정이 저장되었습니다”를 띄우고 있었죠.
즉, 기능은 정상인데 locator가 상태를 제대로 감지하지 못해 실패한 것입니다.

처음에는 data-testid를 더 추가하는 방향도 검토했습니다.
하지만 코드 수정 범위가 너무 넓고 관리 비용도 커질 수 있겠다고 판단해,
현실적인 선택으로 테스트 실행 환경을 영어 기준으로 고정했습니다.

이 결정은 소소해 보여도 꽤 중요했습니다.
자동화에서 실패 원인을 “기능 불량”과 “검증 기준 불안정”으로 분리해 생각하게 해줬기 때문입니다.

|1차 실행 결과는 처참했지만, 오히려 가능성을 봤습니다

문서와 스크립트를 어느 정도 갖춘 뒤 실제로 실행해보니,
1차 결과는 썩 아름답지 않았습니다.

“3개 빼고 전부 실패”

숫자만 보면 좌절할 만합니다.
하지만 오히려 여기서 가능성이 보였습니다.
이미 테스트가 “실패하는 위치”를 말해주기 시작했기 때문입니다.

예전에는 사람이 하나씩 눌러보다가
“어? 여기 뭔가 이상한데?” 정도로 감지하던 문제가,
이제는 코드와 로그, locator, 화면 상태 기준으로 드러나기 시작했습니다.

그리고 healer 에이전트가 직접 브라우저를 열어 깨지는 테스트의 원인을 보정하면서,
적어도 “한 번 만들고 끝나는 스크립트”가 아니라
“실행하면서 고쳐나갈 수 있는 자동화 루프”에 들어섰다는 걸 확인했습니다.

이건 생각보다 큰 차이였습니다.
테스트 자동화의 진짜 시작은 통과율 100%가 아니라,
실패를 구조적으로 다룰 수 있게 되는 시점이라는 걸 배웠으니까요.

|결론: 바뀐 건 테스트 시간만이 아니었습니다

이번 작업의 가장 직접적인 성과는 분명합니다.
매주 팀 7명이 약 40분씩 들여 반복하던 테스트,
즉 한 번 돌릴 때마다 약 4시간 40분이 소모되던 회귀 점검을 백그라운드에서 자동화 가능한 구조로 옮기기 시작했습니다.

하지만 진짜 변화는 시간 절감 그 이상이었습니다.

  • 테스트 문서가 사람 기억 의존형 체크리스트에서, AI와 코드가 함께 읽는 명세 자산으로 바뀌었습니다.

  • 기능 단위가 아니라 사용자 목적과 상태 분기로 시나리오를 재구성하면서, 회귀 테스트의 품질 기준이 더 선명해졌습니다.

  • route, component, permission, locator, API 기대값이 한 문서 안에 묶이면서 테스트와 코드베이스의 연결성이 높아졌습니다.

  • 도메인 단위로 시나리오를 다시 나누는 과정에서 제품 구조를 더 명확히 이해하게 되었고, 문서 메뉴처럼 별도 관리가 필요한 영역도 자연스럽게 드러났습니다.

  • 실패한 테스트가 “왜 실패했는지”를 기록해주기 시작하면서, QA 시간이 단순 확인에서 원인 분석과 개선으로 이동했습니다.

  • 새로 합류한 팀원이 기존 TC 시트를 해석하는 대신, 구조화된 시나리오 문서와 자동화 결과를 보고 기능을 이해할 수 있는 기반이 생겼습니다.

  • 릴리즈 전 사람이 직접 테스트 했기에 “이번엔 놓친 게 없을까?”라는 감각적 불안 대신, 적어도 어느 영역이 자동으로 검증됐는지 말할 수 있게 되었습니다.

  • 재사용 가능한 SKILL set, 시나리오를 생성, 스크립트를 생성, 실패하는 시나리오를 해결,이 남아 앞으로는 추가되는 다른 기능군에도 같은 방식을 테스트를 만들 수 있는 발판이 생겼습니다.

물론 아직 끝난 건 아닙니다.
추가로 검토하고 싶은 것도 분명합니다.

  • 여러 Playwright 인스턴스를 안정적으로 병렬 실행해 전체 테스트 시간을 더 줄이기

  • 관리자/일반 사용자뿐 아니라 더 세밀한 권한 차이를 자동화에 반영하기

  • 회원가입, 회원탈퇴처럼 인증과 외부 의존성이 큰 작업의 자동화 전략 정리하기

  • 팀 나가기, 권한 변경처럼 되돌리기 번거로운 작업을 안전하게 검증할 격리 환경 마련하기

  • 다국어 환경에서도 흔들리지 않는 locator 전략을 장기적으로 정비하기

그래도 분명한 건 하나입니다.
이제 테스트는 더 이상 “사람이 매주 참고 견디는 의식”이 아니라,
문서, 코드, 에이전트가 함께 돌리는 시스템으로 바뀌고 있다는 점입니다.

반복되는 회귀 테스트가 피곤하게만 느껴졌다면,
그건 팀이 게을러서가 아니라 아직 테스트 자산이 자동화되기 좋은 구조가 아니었기 때문일지도 모릅니다.
저희도 이번에 그걸 꽤 뼈저리게 배웠거든요.

앞으로는 이 기반 위에 더 많은 도메인을 붙이고,
실패를 더 빨리 발견하고,
팀이 정말 집중해야 할 검증에 시간을 쓰는 방향으로 계속 개선해보려 합니다.

이런 고민들과 개선 과정을 바탕으로, 더 나은 서비스를 만들어가고 있습니다.
앞으로도 지속적으로 발전해 나갈 키냅스의 모습을 지켜봐 주세요!

👉 [kynapse.ai 더 알아보기]

사이냅 문서뷰어

어디서 어떻게 사용되고 있을까요?

사이냅 문서뷰어의 적용사례를 만나보세요

[개인정보 수집, 이용에 대한 동의 절차]

사이냅 문서뷰어 적용사례를 만나보세요

차원이 다른 HTML5 웹에디터

사이냅 에디터

사이냅 에디터가 어디에 활용될 수 있을까요?
다양한 적용사례를 만나보세요

[개인정보 수집, 이용에 대한 동의 절차]

한 차원 높은 HTML5 웹에디터를 만나보세요