테스트 코드와 TDD

SSO·2023년 9월 25일
0

Web-Develop-Study

목록 보기
4/18

최근에 개인 프젝도 느릿느릿 개발하고 있는 와중에.......
개발 흥미를 돋구기 위해 새로운 지식에 대해서 한 번 알아보고자 한다....

오늘 알아볼 건 바로바로 테스트 코드 !
테스트 코드에 대해서 주변에서 애기는 많이 들었다.
진짜 중요해!! 꼭 해봐야 해!! 등등 현직자 선배들의 말도 많이 들어보았다.
하지만 직접 공부해보거나 작성해 본 적은 한 번도 없어서 개인 프젝에 적용도 해볼겸 오늘은 테스트 코드에 대한 기본 개념을 학습해보고자 한다!


💡 테스트 코드란?

테스트 코드(Test code)는 말 그대로 소프트웨어의 기능과 동작을 테스트하는 데에 사용되는 코드이다.
이 테스트는 소프트웨어의 결함을 찾아내고 수정하는 과정에서 매우 중요한 역할을 한다!
테스트 코드는 개발자가 작성한 코드를 실행해보고 예상한 대로 실행되는지, 예상대로 결과가 나오는 지를 확인하는 데에도 사용된다.

테스트 코드에는 여러가지의 종류가 있지만 그 중에서 프론트엔드 테스트는 크게 세 종류가 있다!

  • 단위 테스트 (Unit Testing)
  • 통합 테스트 (Intergration Testing)
  • e2e 테스트 (End to End Testing)

이러한 종류의 테스트는 각각 특정 측면에서 소프트웨어를 테스트하고 평가한다.
각각의 테스트에 대해서는 밑에서 더 자세히 알아보도록 하자.


💡 테스트 코드를 사용해야 하는 이유는?

  • 정확한 인지: 테스트 코드 작성을 통해 요구사항의 기능적인 항목들을 정리하며 내가 무엇을 개발하고 있는지 정확히 인지할 수 있다.
  • 리팩토링 부담 절감: 테스트 코드가 있으면 코드 수정 후에도 기능이 정상적으로 작동하는지를 검증할 수 있어 이러한 점에서 리팩토링 시 부담을 덜 수 있다.
  • 높은 코드 퀄리티: 개발이 진행된 프로젝트에서 테스트 코드를 작성하다 보면 다양한 문제들을 마주하게 되는데 이러한 문제들이 복잡하게 얽혀 있는 의존성으로 인해 테스트 코드 작성이 어렵다는 것이다. 테스트 코드를 미리 작성하고 코드를 작성한다면 의존성이 높은 부분을 개선하며 코드의 퀄리티를 높일 수 있다.

🧐 프론트엔드에서도 테스트 코드가 중요할까?

다만 테스트 코드에 대해서 공부하면서 한 가지 의문점이 들었다.
처음 접했던 테스트 코드의 내용들은 대부분 백엔드와 관련된 내용이 주였다.
그래서 따로 프론트엔드의 테스트 코드에 대해 서치해서 알아보고는 했다.
여기서 든 의문점은 프론트엔드에서는 테스트 코드가 안중요한가?라는 의문이 들었다.

결론을 먼저 말하자면
프론트엔드에서도 테스트 코드가 중요하다!! 이다.

그 이유는 백엔드의 다양한 기능들이 프론트엔드로 옮겨오기도 하고 이러한 과정에서 React와 같은 프론트엔드 프레임워크들이 생겨난다.
typescript도 어떻게 보면 javascript의 자유성을 일정 부분 포기하고 일일히 type을 지정하며 소프트웨어를 더 잘 관리하기 위해 생겨난 언어라고 할 수 있다.
이러한 변화에 따라 프론트엔드 코드와 퀄리티가 중요해지고 그러면서 프론트엔드의 테스트도 함께 중요해진 것이라고 볼 수 있다.

그러므로 개발자가 되기 위해서는 테스트 코드에 대한 학습이 필수 !!


💡 TDD

TDD Cycle

TDD란!
Test Driven Development의 약자로 '테스트 주도 개발'이라고 한다.
쉽게 말해 테스트할 코드를 먼저 작성하고 나서 개발을 진행하고 이 과정에서 사전에 작성한 테스트를 거친다. TDD에서 테스트를 실패할 경우 테스트를 통과하기 위한 최소한으로 코드를 개선한다. 그 후 최종적으로 테스트에 성공한 코드를 리팩토링하기 때문에 리팩토링 부담이 적다!

그림을 잘 살펴봐보자.

  • 빨강(Write a failing test): 실패하는 테스트를 작성한다.
  • 초록(Make the test pass): 가능한 테스트가 통과하게 작성한다.
  • 파랑(Refactor): 초록 단계에서 일단 통과하게 작성한 코드를 완벽하게 리팩토링한다.
    TDD사이클은 이 세 단계의 반복인 셈이다!!

TDD의 장점

  • 테스트 코드를 작성하고 리팩토링 단계를 여러번 거치면서 끊임없이 보완하기에 코드의 안정성이 높다.
  • 테스트 커버리지(테스트 코드로 검증되는 영역)가 높아진다.
  • 테스트 코드로 빠르고 객관적인 피드백을 받을 수 있다.
  • 테스트 코드를 먼저 작성하면서 설계 과정에서의 구조적 문제를 쉽게 찾을 수 있다.

TDD의 단점

  • 여러 테스트 코드를 작성해야 하기 때문에 기능 구현까지의 시간이 늘어난다.
  • 사전 지식을 학습하고 효과적으로 사용할 수 있을 때까지의 개별적으로 러닝커브가 존재할 수 있다.

📌 좋은 TDD의 특징 (FIRST 규칙)

  • Fast: 테스트는 빠르게 동작해 자주 돌릴 수 있어야 한다.
  • Independent: 각각의 테스트는 독립적이며 서로 의존해서는 안 된다.
  • Repeatable: 어느 환경에서도 반복할 수 있어야 한다.
  • Self-Validating: 테스트는 성공 또는 실패로 bool 값으로 결과를 내어 자체적으로 검증되어야 한다.
  • Timely: 테스트는 테스트하려는 실제 코드를 구현하기 직전에 구현해야 한다.

💡 테스트의 종류


📌 단위 테스트 (Unit Testing)

단위 테스트는 최소 단위로 기능이 잘 작동하는지 확인하는 방법이다. 프론트엔드에서는 컴포넌트가 잘 렌더링되는지, 혹은 특정 함수가 잘 실행되는지 등을 확인한다. 즉 프론트엔드 코드에서의 단위는 단일 컴포넌트 혹은 단일 서비스가 될 수 있다.

또한 단위 테스트는 프로젝트의 최소 단위를 테스트하기 때문에 테스트의 양이 가장 적어 효율적이다!

다만, 소프트웨어의 구조가 명확하지 않고, 단일 단위의 기능이 자주 변경되는 환경에서는 테스트가자주 변경되어야 하고 이는 테스트 작성의 효율을 떨어뜨려 구조가 명확하지 않은 프로젝트에서 사용하는 것은 추천하지 않는다고 한다. 즉, 리팩토링이 자주 일어나지 않는 구조가 명확한 프로젝트에서 사용하는 것이 좋다!

단위 테스트는 별도의 통합이 필요없기 때문에 백엔드 API가 구현이 안되어도 작성이 가능하다!


📌 통합 테스트 (Intergration Testing)

통합 테스트는 말 그대로 통합된 기능을 테스트한다. 단위 테스트가 단일 컴포넌트나 단일 서비스를 기준으로 테스트를 진행했다면 통합 테스트는 단위들 간의 데이터를 주고받는 환경을 테스트한다.

통합 테스트는 전략에 따라 프론트엔드의 전체 단위만 통합해서 테스트할 수도 있고, 백엔드와 데이터베이스까지 모두 통합해서 테스트를 진행할 수도 있다.

모든 단위의 상호작용에 대해 테스트가 가능하다!
다만 모든 상호작용을 테스트 하기 때문에 모든 단위에 대해서 설정 방법 등을 알고 있어야 하므로 단위 테스트에 비해서는 코드 작성이 어렵고 많은 시간 투자와 노력이 필요하다.


📌e2e테스트

e2e테스트end to end의 약자로, 소프트웨어의 가장 끝단인 사용자로부터 가장 끝단인 백엔드 인프라까지 테스트하는 것을 의미한다.
e2e테스트는 cypress, playwright등의 도구를 통해 브라우저 동작을 자동화하여 테스트를 진행한다.
사용자 관점에서 전체 시나리오를 테스트하기 때문에 코드가 변경되더라도 테스트를 변경할 필요가 없다!

다른 테스트들과 다리 전체 시나리오를 테스트하기 때문에 소프트웨어의 무결성을 보장하기 좋다.
여기서 무결성이란 integrity로 정확성이라고 이해하면 된다.

하지만 사용자 관점에서 전체 시나리오를 테스트하기 때문에 굉장히 많은 테스트가 필요하고 프론트엔드만 따로는 불가능하며 백엔드와의 통합이 필요하다. 또한 전체를 테스트하기에 시간이 오래 걸려 자주 테스트하기 어렵다는 점이 있다.



💡 프론트엔드 관점에서의 테스트

위의 내용에서 알아본 테스트 코드에 대한 개념들은 소프트웨어의 관점에서 알아보았다.
그렇다면 프론트엔드 개발자는 어떻게 테스트 코드를 작성해야 할까?

먼저 프론트엔드에서 테스트의 대상은 무엇이 있을지 생각해보자.
생각해보면 시각적 요소(UI/UX 등), 사용자 이벤트 처리, API 통신과 같이 크게 3가지를 떠올릴 수 있다.

그렇다면 이 3가지 대상을 어떻게 테스트할 수 있을까!

  1. 시각적 요소
    프론트엔드 개발자들은 디자이너에게 받은 디자인을 보고 컴포넌트를 생성하고 여기에 스타일을 입히며 디자인대로 구현하는 작업을 한다. 여기서 html에 css를 더해 컴포넌트가 실제로 브라우저에서 렌더링되는 모습이 의도한 대로 나타나는지를 테스트한다. 이런 테스트에 사용되는 도구로는 Jest가 대표적이다.
  1. 사용자 이벤트 처리
    프론트엔드 개발자는 사용자의 마우스, 키보드 등의 입력 이벤트를 적절한 이벤트 핸들러로 처리하는 작업도 한다. 이러한 이벤트들이 의도한 대로 잘 작동하는지 테스트하는 경우 React팀이 권장하는 테스트 도구인 testing-library에서 제공하는 패키지를 활용하면 테스트 할 수 있다.
  1. API 통신
    프론트엔드 개발자는 API서버와 통신하도록 하는 작업도 수행한다. 이를 테스트하는 방법은 여러가지가 있지만 우리가 흔히 쓰는 React팀에 따르면, Jest를 활용하면 다양한 모듈을 간단한 방법으로 mocking할 수 있기 때문에 Jest를 테스트 도구로 활용할 것을 권장하고 있다.

오늘은 테스트 코드의 기본적인 개념에 대해서 간단하게 알아보고 프론트엔드에서는 무엇을, 어떻게 테스트하는지 간략하게 알아보았다.
다음 포스팅에서는 프론트엔드에서 테스트 코드를 어떻게 작성하는지, 어떤 라이브러리를 사용하는지 알아보고 직접 프로젝트에 적용을 해 볼 예정이다!

-그럼 오늘 포스팅 끝👋-

profile
👩🏻‍💻👊🏻⭐️

0개의 댓글