Navigation

How to Run Findbugs, Pmd, Checkstyle, JUnit and Cobertrua with an Ant Build-Script?

BY MARKUS SPRUNCK

This article describes an Ant-build sample that runs the five tools Findbugs [1], Checkstyle [2], PMD [3], JUnit [4] and Cobertura [5]. Additionally it creates and collects the native HTML reports of each tool. Ant-builds have the big advantage over Maven-builds that you have everything under control and a minimal foot print of the build result. This justifies the overhead of writing the build.xml file.

The sometimes huge number of not needed libraries and difficult control of the used libraries is the main reason why I don't like Maven for real projects. Maven is better than Ant [7] for quick hacks.

The Example Code

Just copy the build.xml (file #1) in your project and change the paths checkstyle.home.dir, cobertura.home.dir, findbugs.home.dir and pmd.home.dir to your directories. This example has been compiled and executed with junit-4.5.jar - but other versions should make no problem.

<projectname="AntDefault"default="run"basedir="."><description>
Ant build sample for running
- findbugs,
- pmd,
- checkstyle,
- cobertrua and
- junit.
</description><!-- Change the paths to your individual installation directories --><propertyname="checkstyle.home.dir"location="C:/EU/checkstyle/checkstyle-5.0"/><propertyname="cobertura.home.dir"value="C:/EU/cobertrua/cobertura-1.9.2"/><propertyname="findbugs.home.dir"value="C:/EU//findbugs/findbugs-1.3.9-rc2"/><propertyname="pmd.home.dir"value="C:/EU//pmd/pmd-4.2.5"/><propertyname="lib.dir"location="${basedir}/lib"/><propertyname="src.dir"location="${basedir}/src"/><propertyname="bin.dir"location="${basedir}/bin"/><propertyname="htm.dir"location="${basedir}/html"/><propertyname="report.dir"location="${basedir}/report"/><propertyname="report.checkstyle.dir"location="${report.dir}/checkstyle"/><propertyname="report.junit.dir"location="${report.dir}/junit"/><propertyname="report.findbugs.dir"location="${report.dir}/findbugs"/><propertyname="report.cobertura.dir"location="${report.dir}/cobertura"/><propertyname="report.pmd.dir"location="${report.dir}/pmd"/><propertyname="instrumented.dir"location="${basedir}/instrumented"/><propertyname="report.temp.dir"location="${report.dir}/temp"/><propertyname="cobertura.ser.file"location="${report.temp.dir}/cobertura.ser"/><pathid="run.classpath"><pathelementpath="${bin.dir}"/><pathelementpath="${basedir}/lib/junit-4.5.jar"/></path><pathid="cobertura.classpath"><pathrefid="run.classpath"/><filesetdir="${cobertura.home.dir}"><includename="cobertura.jar"/><includename="lib/**/*.jar"/></fileset></path><taskdefclasspathref="cobertura.classpath"resource="tasks.properties"/><!-- --><targetname="clean"description="Delete all result to start with a clean build."><deletedir="${report.junit.dir}"/><deletedir="${report.findbugs.dir}"/><deletedir="${report.cobertura.dir}"/><deletedir="${report.checkstyles.dir}"/><deletedir="${report.temp.dir}"/><deletedir="${bin.dir}"/></target><targetname="prepare.report.dir"description="Prepares the reports folder"><copytodir="${report.dir}"><filesetdir="${htm.dir}"><includename="*.htm"/></fileset></copy></target><!-- --><targetname="findbugs"depends="compile"description="Run code analysis over code to check for problems."><!-- Fail this target if FindBugs is not installed. --><availablefile="${findbugs.home.dir}/lib/findbugs.jar"property="findbugs.available"/><failunless="findbugs.available"message="Error: FINDBUGS_HOME not set or findbugs.jar not found."/><taskdefname="findbugs"classname="edu.umd.cs.findbugs.anttask.FindBugsTask"classpath="${findbugs.home.dir}/lib/findbugs-ant.jar"/><!-- Run FindBugs. --><mkdirdir="${report.findbugs.dir}"/><findbugshome="${findbugs.home.dir}"workHard="true"output="xml:withMessages"outputFile="${report.findbugs.dir}/findbugs.xml"><classlocation="${bin.dir}"/><auxClasspath><filesetfile="${basedir}/lib/junit-4.5.jar"/></auxClasspath></findbugs></target><!-- --><pathid="pmd2.classpath"><pathelementlocation="${build}"/><filesetdir="${pmd.home.dir}/lib/"><includename="*.jar"/></fileset></path><taskdefname="pmd"classname="net.sourceforge.pmd.ant.PMDTask"classpathref="pmd2.classpath"/><targetname="report.pmd"><mkdirdir="${report.pmd.dir}"/><pmdrulesetfiles="rulesets/favorites.xml"><formattertype="xml"toFile="${report.pmd.dir}/pmd_report.xml"/><filesetdir="${src.dir}"><includename="**/*.java"/></fileset></pmd><xsltin="${report.pmd.dir}/pmd_report.xml"style="${pmd.home.dir}/etc/xslt/pmd-report-per-class.xslt"out="${report.pmd.dir}/pmd_report.html"/></target><!-- --><targetname="compile"depends="clean"description="Compile the entire project."><mkdirdir="${bin.dir}"/><javacdebug="true"debuglevel="lines, source"srcdir="${src.dir}"destdir="${bin.dir}"classpathref="run.classpath"/></target><!-- --><targetname="cobertura.instrument"depends="clean, compile"description="Instrument the project for code coverage."><mkdirdir="${report.temp.dir}"/><cobertura-instrumenttodir="${instrumented.dir}"datafile="${cobertura.ser.file}"><ignoreregex="org.apache.log4j.*"/><filesetdir="${bin.dir}"><includename="**/*.class"/><excludename="**/*Test.class"/></fileset></cobertura-instrument></target><!-- --><targetname="junit"depends="clean, compile, cobertura.instrument"description="Run all junit test cases."><mkdirdir="${report.cobertura.dir}"/><mkdirdir="${report.temp.dir}"/><junitprintsummary="yes"fork="yes"haltonfailure="no"><!-- Specify the name of the coverage data file to use. The value specified below is the default. --><syspropertykey="net.sourceforge.cobertura.datafile"file="${cobertura.ser.file}"/><!-- Note the classpath order: instrumented classes are before the original (uninstrumented) classes. This is important. --><classpathlocation="${instrumented.dir}"/><classpathlocation="${bin.dir}"/><classpathlocation="${basedir}/lib/junit-4.5.jar}"/><!-- The instrumented classes reference classes used by the Cobertura runtime, so Cobertura and its dependencies must be on your classpath. --><classpathrefid="cobertura.classpath"/><formattertype="plain"/><formattertype="xml"/><batchtesttodir="${report.temp.dir}"><filesetdir="${src.dir}"><includename="**/*Test.java"/></fileset></batchtest></junit></target><!-- --><targetname="report.junit"depends="junit"description="Create a report for the test result."><deletedir="${report.junit.dir}"/><mkdirdir="${report.junit.dir}"/><junitreporttodir="${report.junit.dir}"><filesetdir="${report.temp.dir}"><includename="*.xml"/></fileset><reportformat="frames"todir="${report.junit.dir}"/></junitreport></target><!-- --><targetname="report.findbugs"description="Generate a report on error analysis."><xsltin="${report.findbugs.dir}/findbugs.xml"style="${findbugs.home.dir}/src/xsl/fancy.xsl"out="${report.findbugs.dir}/findbugs-default.html"/></target><!-- --><targetname="report.cobertura"depends="junit"description="Generate an HTML report on Cobertura."><cobertura-reportformat="html"datafile="${cobertura.ser.file}"destdir="${report.cobertura.dir}"><filesetdir="${src.dir}"><includename="**/*.java"/></fileset></cobertura-report></target><!-- --><targetname="report.checkstyle"description="Generate a report of code convention violations."><taskdefresource="checkstyletask.properties"classpath="${checkstyle.home.dir}/checkstyle-all-5.0.jar"/><!-- run verification of installation--><availablefile="${checkstyle.home.dir}/checkstyle-all-5.0.jar"property="checkstyle.available"/><failunless="checkstyle.available"message="Error: CHECKSTYLE_HOME not set or checkstyle-all-5.0.jar not found."/><mkdirdir="${report.checkstyle.dir}"/><!-- run analysis--><checkstyleconfig="${checkstyle.home.dir}/sun_checks.xml"failureProperty="checkstyle.failure"failOnViolation="false"><formattertype="xml"tofile="${report.checkstyle.dir}/checkstyle_report.xml"/><filesetdir="${src.dir}"includes="**/*.java"/></checkstyle><stylein="${report.checkstyle.dir}/checkstyle_report.xml"out="${report.checkstyle.dir}/checkstyle_report.html"style="${checkstyle.home.dir}/contrib/checkstyle-noframes.xsl"/></target><!-- --><targetname="clean.temp"description="Delete all temporary files and folders."><deletedir="${instrumented.dir}"/><deletedir="${report.temp.dir}"/></target><!-- --><targetname="run"description="Run the build"depends="clean, prepare.report.dir, report.checkstyle, report.pmd, compile, cobertura.instrument, junit, report.junit, findbugs, report.findbugs, report.cobertura, clean.temp"></target></project>

The build file expects to further files index.htm (File #2) and menue.htm (File #3) in the sub-directory "${basedir}/html". These two files create the entry page shown in figure 1.