Atobaum

테스트 주도 개발에 대한 생각

TDD의 철학

테스트 주도 개발(best driven development, TDD)은 단순히 테스트를 먼저 쓰는게 아니라 테스트가 개발의 중심이 되는 프로그램 개발 방법론이다. 말하자면 구현은 그저 테스트를 통과하기 위해 쓰는 것이다. 이 점이 TDD의 다른 점이다.

보통의 개발에서는 테스트가 구현에 의존하나 TDD에서는 구현이 테스트에 의존한다. 따라서 개발을 시작할 때 어떤 클래스나 함수가 필요한지 묻지 않고 어떤 테스트가 필요한지 가장 먼저 물어야한다.

테스트를 썼으면 일단 테스트가 통과하도록 만든다. 일단 return 7; 같이 테스트하는 값을 그대로 사용해도 괜찮다. 중요한 것을 빨간불을 초록불로 바꾸는 것이다. 이제 테스트 코드를 추가하고 초록불이 뜨게 한다. 그리고 중복을 제거하고 불필요한 테스트를 지운다.

개발은 더도 말도 덜도 말고 테스트만 통과하도록 구현을 한다. 이때 물론 테스트를 통과하는 것이 중요하지만 테스트 이상의 구현을 하지 않는 것도 중요하다. 이렇게 함으로써 테스트는 문서의 역할도 하게 된다.

TDD에서는 구현을 다 쓰고 테스트 코드를 작성하거나 그 반대가 아니다. TDD에서 테스트코드와 구현 코드는 계속 상호작용하면서 자라난다.

조언

빨간 불

만약 개발을 하다가 빨간 불이 뜨면 일단 빨간 불을 지우는 일만 하라. 언제나 초록불이 떠 있어야 한다. 반면 일을 마칠 때 실패하는 테스트를 쓰고 그만두는 것도 괜찮다. 다음에 왔을 때 실패한 테스트부터 고치는 일을 하면 되기 때문에 어디서부터 다시 시작할지 알기 쉽기 때문이다.

테스트의 크기

TDD에서 테스트는 빨리 끝나야한다. 짧으면 1초도 안되는 간격으로 테스트를 진행하기 때문에 테스트가 오래걸리면 안된다. 그만큼 테스트는 작아야한다.

테스트의 양

테스트는 얼마나 있어야 하는가? 저자는 개발이 두려우면 테스트 코드가 더 필요한 것이라고 말한다. 반면 테스트 코드를 쓰는 것이 지겨우면 그만 만들때라고 한다(한상 지겨운데??).

개발을 진행하다보면 중복된 테스트 코드가 생긴다. 그럼 언제 중복된 테스트를 지워야하는가? 저자는 테스트를 삭제해도 자신감이 줄지 않을 때 삭제하라고 한다. 또한 만약 두 테스트가 같은 코드를 실행하더라고 둘이 다른 시나리오를 말한다면 남겨두라고 말한다.

중복 제거하는 법

예를들어 Dollar와 Franc 클래스가 있을 때 이를 Money로 추상화하고 싶다고 해보자. 먼저 빈 Money 클래스를 만들고 Dollar와 Franc이 Money를 상속받게 한다. Money 클래스는 비어있기 때문에 테스트는 깨지지 않는다. 그 후 각 클래스에 있는 중복된 메서드의 테스트를 수정한다(메서드명, 자료형 등). 이제 각 클래스의 구현을 수정된 테스트에 맞추어 바꾼다. 이제 각 클래스의 메서드가 같아졌을 것이다. 두 메서드를 Money 클래스로 옮기고 각 클래서의 메서드를 삭제한다. 테스트틑 깨지지 않는다.

장점

리팩토링을 과감하게 할 수 있게 한다.

제일 먼저 떠오르는 장점은 리팩토링이 두렵지 않다는 것이다. 코드를 바꾸어도 테스트가 있기 때문에 수정이 코드를 망치는지 알기 쉽다.

테스트 코드는 설계의 문제를 알려줄 수도 있다.

  • 너무 긴 셋업 코드가 필요하면 객체가 너무 크다는 뜻이다. 객체를 나누자.
  • 셋업 코드가 중복된다면 서로 엉킨 객체들이 많다는 뜻이다. 결합도를 낮추어보도록 해보자.
  • 테스트를 실행하는데 시간이 너무 오래걸린다면 작은 부분만 테스트 할 수 없다는 뜻이고 설계에 문제가 있다는 것을 암시한다. 실행 시간이 너무 오래걸리면 테스트를 자주 실행시킬 수 없다.
  • 예상치 못하게 실패하는 테스트가 있으면 코드에 이상한 의존성이 있다는것을 암시한다.

문서화

테스트를 문서로 사용할 수도 있다.

후기

TDD는 생각보다 짧은 주기로 돌아간다. TDD를 좀 더 연습해보고 책을 한 번 더 읽으면 새로 보이는게 있을 것 같다.

Reference

  • 켄트 벡. 테스트 주도 개발. 인사이트, 2014.