내 코드에 버그가 있지는 않을까... 단위 테스트!
*이번 장의 내용은 XCode에서 작성되었습니다.
Visual Studio, Eclipse를 사용하는 분들은 뒤로가기를 눌러주세요 단위테스트의 개념이라도 학습하고 가세요.
단위 테스트… 꼭 해야하나?
시험이 사실상 월요일 날 거의 끝나버린 나는 별달리 하는 일 없이 슈퍼 단간론파 2를 하고 있었다.
그래도 시험기간이긴 하니, 공부를 해야겠다 싶어서 관계도 없는 스위프트 웹 서버 프로그래밍을 해볼까 하는 와중에, 나도 패키지를 만들어야겠다는 생각이 들었다.
node.js의 패키지 매니저인 Node Package Manager(이하 npm)와 유사하게, Swift만의 패키지 매니저 Swift Package Manager(이하 spm)이 있다.
spm에 대해서는 다음 번에 포스팅 하기로 하고, 우선은 패키지를 만들며 항상 발생하는 문제점인 버그
를 잡기 위해 돌려보는 단위 테스트
에 대해 알아보자.
나는 이미 단위 테스트가 무엇인지 알고 있다. 그러나, XCode에서 단위테스트의 방법에 대해 조금 더 알았을 뿐이다.
XCode 열고, macOS > Command Line Tool을 선택해서 프로젝트를 생성한다.
여기서 main.swift
파일을 굳이 사용하지는 않겠지만, 일단 남겨두고, anagram.swift
파일을 만든다.
(그렇다. 이번 예제는 에너그램으로 한다.)
anagram.swift
func anagram(lhs: String, rhs: String) -> Bool {
return lhs == rhs
}
진정해라 나도 틀린 건 안다.알아
틀린 코드를 적은 것은 이 코드는 버그가 있다. 라는 뜻이지, 내가 바보다라는 뜻이 아니다.
여튼, 이제 우리가 만든 함수를 테스트 하기 위해 단위 테스트 모듈을 추가해야 한다.
Java 언어라면, jUnit이라는 정말 유명한 단위 테스트 툴을 사용하겠지만, 우리는 뭐… ㅎㅎ
File > New > Target을 선택한다.
시트가 나타나면, Text 탭에서 OS X Unit Testing Bundle
을 선택한다.
이름은 귀찮으니 Anagram Test
라고 짓자
그럼 아래 그림처럼 새로운 타겟(Target)이 추가된다.
타겟은 빌드 타겟을 의미하며, 경우에 따라 실행파일, 라이브러리, 프레임워크, 등등 여러가지가 될 수 있다.
테스트를 하기 위해서는 테스트 함수를 작성해야 한다.
웃기는 일이지만, XCode의 단위 테스트는 정말 간편하다.
함수 이름이 test
로 시작되면 그게 테스트 함수다.
func testAnagram() {
assert(anagram(lhs: "apple", rhs: "apple") == true, "anagram failed: apple")
assert(anagram(lhs: "samsung", rhs: "ssamung")) == true, "alagram failed: samaung")
}
테스트 함수 작성은 끝이 났다. 이제는 테스트를 할 차례인데…
CMD + R 키가 아니다.
CMD + R 키를 눌러서는 테스트를 할 수가 없다. 단위 테스트(Unit Test)는 CMD + U로 시작한다.
그러나, 여러분의 컴퓨터는 “뚱!” 하는 소리만 낼 뿐, 아무 동작도 하지 않는다.
단위 테스트를 하기 위해, 여러분은 Scheme을 변경해야 한다.
아까 1학년들 C 언어 조교를 들어가서, 디버그모드와 릴리즈 모드를 설명하기 위해 스킴 변경을 보여줬더니, “우와 이게 뭐에요?”라며 놀랐지만, 여러분은 안 놀라리라 믿는다.
(당연히 오래 살았으니, 별에별 일을 다 겪어서 놀라지도 않을 것이다.)
스킴(Scheme)을 변경하려면 XCode 타이틀 바의 [실행][중지] 버튼 오른쪽에 있는 Anagram 버튼을 눌러보라.
아래와 같은 사진이 나타날 것이다.
여기서 Anagram Test
를 눌러주자.
이제 CMD + U를 누르면 뭔가가 된다.
뭔가 상태바가 올라가는 것 같더니… 컴파일 에러가 발생한다.
anagram이라는 함수를 찾을 수 없다고 하는데, 이건 빌드 타겟에 파일이 포함되어 있지 않기 때문이다.
anagram.swift
파일을 선택하고 오른 쪽 속성 창을 보자.
Target Membership
이라는 창이 있다.
여기서 Anagram Test에 체크를 해야 한다.(해당 타겟에 이 파일을 포함시키겠다는 의미다.)
이제 여러분들은 CMD + U로 단위 테스트를 해도 된다.
그러나…
그런데 웬걸?
또 에러다… 이번엔 컴파일 에러다.
assert(anagram(lhs: "samsung", rhs: "ssamung") == true, "alagram failed: samaung")
위 코드에서 문제가 생겼는데, 이것은 단위 테스트 결과의 문제일 뿐이다. 걱정하지 말자.
애초에 samsung
과 ssamung
으로 애너그램을 판별하는데 ==
연산자로 비교한 것이 화근이다.
즉, 코드에 버그가 있다는 뜻
대충 단위테스트가 무엇을 의미하는지는 이해했으리라 생각한다.
뒷 내용은 읽어도 그만, 안 읽어도 그만이지만, 단위테스트란 함수가 특정 입력에 대해 그에 해당하는 출력을 올바르게 반환하는가
를 판단하는 데 사용된다는 것을 잊지 말자.
단위 테스트에 문제가 있다고 하니, anagram 함수를 고쳐주자.
func anagram(lhs: String, rhs: String) -> Bool {
return lhs.characters.sorted() == rhs.characters.sorted()
}
에너그램 함수는 이제 잘 동작할 것이다.