Test Coverage는 개발자가 작성한 테스트 코드가 대상 소스 코드에 대해 테스트하는 코드를 작성했는지 그 커버하는 정도를 백분률과 코드 라인을 통해 알려주는 것을 말하며, Test Coverage를 분석하고 그 결과를 리포팅하는 것에 대해 설명한다.
Test Coverage는 개발자가 작성한 코드에 대해 상응하는 테스트를 갖는 소스 코드의 비율을 평가하는 작업으로 다음과 같은 개념을 이해하는 것이 좋다.
Test Coverage를 수행하는 데는 다양한 툴이 있고, 각각 평가하는 나름의 로직을 갖고 있으며, 리포팅 또한 그 로직에 상응하는 형태라고 볼 수 있다. 따라서, 필요에 맞는 도구를 잘 선택하면 된다.
본 개발환경에서는 라이선스를 고려하여 EMMA와 EclEmma를 선택했다.
그러나, 코드를 수정하지 않고 툴로서 사용하기만 한다면 Cobertura를 사용하는 것도 괜찮다.
구분 | 툴 이름 |
---|---|
상용 | Clover |
오픈소스 | Cobertura, EMMA |
Eclipse Plug-in | EclEmma, Coverlipse |
본 개발환경에서 채택은 하지 않았지만, 고려대상 중 하나였던 Cobertura의 특징은 다음과 같다.
EMMA는 오픈소스로서 라이선스는 CPL (Common Public License) v1.0 이다.
Ant와 Maven에서 실행 가능하며, Command-line에서도 사용 가능하다.
자세한 내용은 EclEmma Home을 참조하기 바란다.
Ant에서 EMMA를 쓰는 일은 조금 까다롭다. 따라서, Ant 수행에 대해서는 EMMA 사이트와 Using EMMA With ANT For JUnit Test Coverage Reporting를 참조하기 바란다.
전체 설정 내용은 EMMA 실행을 위한 pom.xml 설정 샘플을 참조하기 바란다.
<build> <plugins> <!-- test --> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <configuration> <skipTests>false</skipTests> <forkMode>always</forkMode> <reportFormat>xml</reportFormat> </configuration> </plugin> <!-- EMMA --> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>emma-maven-plugin</artifactId> <version>1.0-alpha-1</version> </plugin> </plugins> </build>
<reporting> <plugins> <!-- EMMA Coverage Reporting --> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>emma-maven-plugin</artifactId> <inherited>true</inherited> </plugin> </plugins> </reporting>
전체 설정 내용은 EMMA 실행을 위한 build.xml 설정 샘플을 참조하기 바란다.
<!-- EMMA 세팅 생략 --> <target name="emma-jars" depends="build" description="Uses Emma to instrument the jar files"> <emma enabled="${emma.enabled}"> <instr mode="fullcopy" outdir="${basedir}/build/temp" merge="yes" filter="egovframework.dev.tst.*" metadatafile="${artifactsDir}/test-coverage/coverage.em"> <instrpath> <fileset dir="build/" includes="${ant.project.name}.jar" /> </instrpath> </instr> </emma> </target> <target name="test.with.emma" depends="emma-jars"> . . . 중략 . . . <junit fork="yes" printsummary="yes" haltonfailure="no" failureproperty="test.failed" errorproperty="test.failed" dir="${basedir}"> <classpath> <path refid="master-classpath" /> <path refid="test-classpath" /> <path refid="emma.lib" /> <fileset dir="${basedir}/build/temp/lib" includes="${ant.project.name}.jar" /> <pathelement location="${testbuild.dir}" /> </classpath> <formatter type="xml" /> <batchtest fork="yes" todir="${artifactsDir}/test-results/xml"> <fileset dir="${testbuild.dir}"> <include name="**/*Test.class" /> </fileset> </batchtest> </junit> </target>
<!-- Test Code Coverage Report --> <target name="emmareport" depends="test.with.emma"> <move file="${basedir}/coverage.ec" todir="${artifactsDir}/test-coverage" /> <emma description="now we can generate the emma report" enabled="${emma.enabled}"> <report sourcepath="${src.dir}" sort="+name,+method,+class" metrics="method:70,line:80,class:100" depth="method" columns="name,class,method,block,line" encoding="UTF-8"> <infileset dir="${artifactsDir}/test-coverage" includes="*.em, *.ec" /> <!-- XML Report --> <xml outfile="${artifactsDir}/test-coverage/coverage.xml" /> <!-- Text Report --> <txt outfile="${artifactsDir}/test-coverage/coverage.txt" /> <!-- HTML Report --> <html outfile="${artifactsDir}/test-coverage/coverage.html" /> </report> </emma> </target>