首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

Ant + JUnit + Cobertura 實現程式碼覆蓋率自動化測試

     編輯:Java 相關知識

建構腳本總覽

整合 Cobertura 程式碼覆蓋率工具,於 Ant 建構流程中自動執行:儀器化類別 → 執行 JUnit 測試 → 生成 XML/HTML 覆蓋率報告 → 覆蓋率門檻檢查。

完整 build.xml

<?xml version='1.0' encoding="UTF-8" ?>
<project name="Server" default="coverage" basedir=".">
  <property name="src.dir" value="./src/"/>
  <property name="classes.dir" value="./bin/"/>

  <property name="cobertura.dir" value="./cobertura-1.9/"/>
  <property name="reports.dir" value="reports"/>
  <property name="instrumented.dir" value="instrumented"/>
  <property name="reports.xml.dir" value="${reports.dir}/junit-xml"/>
  <property name="reports.html.dir" value="${reports.dir}/junit-html"/>
  <property name="coverage.xml.dir" value="${reports.dir}/cobertura-xml"/>
  <property name="coverage.html.dir" value="${reports.dir}/cobertura-html"/>

  <path id="classpath">
    <fileset dir="./lib/" includes="**/*.jar"/>
  </path>
  <path id="cobertura.classpath">
    <fileset dir="${cobertura.dir}">
      <include name="cobertura.jar"/>
      <include name="lib/**/*.jar"/>
    </fileset>
  </path>
  <taskdef classpathref="cobertura.classpath" resource="tasks.properties"/>

  <target name="init" depends="clean">
    <mkdir dir="${classes.dir}"/>
    <mkdir dir="${instrumented.dir}"/>
    <mkdir dir="${reports.xml.dir}"/>
    <mkdir dir="${reports.html.dir}"/>
    <mkdir dir="${coverage.xml.dir}"/>
    <mkdir dir="${coverage.html.dir}"/>
  </target>

  <target name="compile" depends="init" description="compile classes">
    <javac destdir="${classes.dir}" srcdir="${src.dir}" debug="yes">
      <classpath><path refid="classpath"/></classpath>
    </javac>
  </target>

  <target name="jar" depends="compile" description="build release jar">
    <jar destfile="${ant.project.name}.jar">
      <fileset dir="${classes.dir}"><include name="**/*.class"/></fileset>
    </jar>
  </target>

  <!-- 儀器化類別(排除測試類別) -->
  <target name="instrument" depends="compile">
    <cobertura-instrument todir="${instrumented.dir}">
      <fileset dir="${classes.dir}">
        <include name="**/*.class"/>
        <exclude name="**/test/**/*.class"/>
      </fileset>
    </cobertura-instrument>
  </target>

  <!-- 執行測試並收集覆蓋率資料 -->
  <target name="cover-test" depends="compile">
    <junit fork="yes" dir="${basedir}" failureProperty="test.failed">
      <sysproperty key="net.sourceforge.cobertura.datafile" file="${basedir}/cobertura.ser"/>
      <!-- Classpath 順序關鍵:儀器化類別優先 -->
      <classpath refid="classpath"/>
      <classpath location="${instrumented.dir}"/>
      <classpath location="${classes.dir}"/>
      <classpath refid="cobertura.classpath"/>
      <formatter type="xml"/>
      <test name="${testcase}" todir="${reports.xml.dir}" if="testcase"/>
      <batchtest todir="${reports.xml.dir}" unless="testcase">
        <fileset dir="${src.dir}"><include name="**/*Test.java"/></fileset>
      </batchtest>
    </junit>

    <junitreport todir="${reports.xml.dir}">
      <fileset dir="${reports.xml.dir}"><include name="TEST-*.xml"/></fileset>
      <report format="frames" todir="${reports.html.dir}"/>
    </junitreport>
  </target>

  <!-- 覆蓋率門檻檢查 -->
  <target name="coverage-check">
    <cobertura-check branchrate="34" totallinerate="100"/>
  </target>

  <!-- 生成 XML 覆蓋率報告 -->
  <target name="coverage-report">
    <cobertura-report srcdir="${src.dir}" destdir="${coverage.xml.dir}" format="xml"/>
  </target>

  <!-- 生成 HTML 覆蓋率報告 -->
  <target name="alternate-coverage-report">
    <cobertura-report destdir="${coverage.html.dir}">
      <fileset dir="${src.dir}"><include name="**/*.java"/></fileset>
    </cobertura-report>
  </target>

  <target name="coverage" depends="jar,instrument,cover-test,coverage-report,alternate-coverage-report"
    description="Compile, instrument, run tests, generate JUnit and coverage reports."/>

  <target name="clean" description="delete all intermediary files">
    <delete dir="${classes.dir}" quiet="true"/>
    <delete dir="${instrumented.dir}" quiet="true"/>
    <delete dir="${reports.xml.dir}" quiet="true"/>
    <delete dir="${reports.html.dir}" quiet="true"/>
    <delete dir="${coverage.xml.dir}" quiet="true"/>
    <delete dir="${coverage.html.dir}" quiet="true"/>
    <delete dir=".clover" quiet="true"/>
    <delete file="cobertura.log" quiet="true"/>
    <delete file="cobertura.ser" quiet="true"/>
  </target>
</project>

關鍵流程解析

  1. compile:編譯主程式碼,debug="yes" 保留行號資訊供覆蓋率分析。
  2. instrument:cobertura-instrument 修改位元碼插入探針,輸出至 instrumented/,**排除測試類別**(避免汙染覆蓋率統計)。
  3. cover-test:
    • fork="yes" 獨立 JVM 執行,確保資料檔 cobertura.ser 正確寫入。
    • Classpath 順序:**儀器化類別 → 原始類別 → Cobertura 庫**,確保載入已儀器化版本。
    • batchtest 掃描 **/*Test.java 執行所有測試。
    • junitreport 生成 HTML 測試報告。
  4. coverage-report / alternate-coverage-report:分別生成機器可讀 XML 與人類可讀 HTML 覆蓋率報告。
  5. coverage-check:設定門檻(分支覆蓋 34%、行覆蓋 100%),未達標建構失敗。

目錄結構建議

project/
├── src/           # 主程式碼
├── junit/         # 測試碼(或 src 同層)
├── lib/           # 依賴 JAR
├── cobertura-1.9/ # Cobertura 解壓目錄
├── reports/       # 輸出報告
│   ├── junit-xml/
│   ├── junit-html/
│   ├── cobertura-xml/
│   └── cobertura-html/
├── instrumented/  # 儀器化類別
├── bin/           # 編譯輸出
└── build.xml

使用指令

ant coverage   # 完整流程:編譯→儀器化→測試→報告
ant coverage-report   # 僅生成覆蓋率報告(需先執行 cover-test)
ant clean      # 清理所有產出物

進階技巧

  • CI 伺服器(Jenkins/GitLab CI)整合:發佈 cobertura-html/ 為覆蓋率報告成果。
  • 多模組專案:各模組獨立 cobertura.ser,最後合併報告。
  • 排除生成代碼(如 DTO、Parser):<exclude name="**/generated/**/*.class"/>。
  • 歷史趨勢追蹤:保留歷次 cobertura.ser 或 XML 報圖表化。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved