SoftwareEngineering/Java/UnitTest/JMockit

コードカバレッジの測定

コードカバレッジは、一連のソフトウェアメトリックで構成され、特定のテストスイートでどのくらいの量のプロダクションコードがカバーされているかを示すことができます。
これは純粋に量的なものであり、プロダクションコードまたはテストコードの品質については何も言及していません。
つまり、コードカバレッジレポートの調査では、到達不能なコードが発見されることがあり、これを排除することができます。
しかしもっと重要なのは、このようなレポートは、欠落しているテストの発見のためのガイドとして使用できることです。
これは、既存のプロダクションコードのテストを作成するときだけでなく、TDD(テスト駆動開発)のようにテストを初めて作成するときにも便利です。

JMockitカバレッジは、 ラインカバレッジ 、 パスカバレッジ 、 データカバレッジの 3つの相補的なコードカバレッジメトリックを提供します。

ラインカバレッジ

ライン・カバレッジ・メトリックは、ソース・ファイル内の実行可能コードがテストによってどの程度実行されたかを示します。
コードの各実行可能な行は、 覆われているか、 覆われているか、 部分的に覆われています。
最初のケースでは、実行可能コードはまったく実行されませんでした。
2番目のコードでは、 すべてのコードが少なくとも1回は完全に実行されました。
3番目のケースでは、行内の実行可能コードの一部だけが実行されました。
これは、たとえば、複雑なブール式の中に複数の論理条件を含むコードの行で発生する可能性があります。
JMockitカバレッジは、3つすべてのケースを識別し、実行可能な各コードラインのカバレッジ率を計算します。
カバーされていないラインの場合は0% 、カバードラインの場合は100% 、部分的にカバーされたラインの場合は、

分岐ポイントは、プログラムが2つの可能な実行パスの間で決定を下すたびに存在します。
論理条件を含むコード行は、少なくとも2つの実行可能セグメントに分割され、それぞれが別々のブランチに属します。
分岐点のない実行可能なソースコード行には、単一のセグメントが含まれています。
1つまたは複数の分岐点を有する線は、線の連続する分岐点によって分離された2つ以上の実行可能セグメントを含む。

NS >= 1は、与えられた行の実行可能セグメントの数です。
NEが、テスト実行中に少なくとも1回実行された(つまり、それらがカバーされているセグメント )その行のセグメント数である場合、そのラインのカバレッジ率を100 * NE / NSとして計算できます。

同様に、ファイル内のすべての実行可能コード行を考慮して、実行可能なセグメントの総数とカバーされたセグメントの総数から、ソースファイル全体の行カバレッジ率が計算されます。
パッケージのパーセンテージは、 パッケージに属するソースファイル全体のセグメントの合計数とカバーされた数から計算されます。
最後に、 総コードカバレッジ率は、すべてのパッケージの合計で同じ式によって計算されます。

パスカバレッジ

まったく異なるメトリックは、コードの行またはセグメントではなく、メソッドおよびコンストラクター本体で計算されるパスカバレッジです。
テスト実行中に、メソッドまたはコンストラクタを介して実行可能な実行パスのうち、 エントリから終了までの実行パスの数が少なくとも1回実行されたことを示します。

各メソッドまたはコンストラクターには単一のエントリポイントがありますが、複数の出口を持つことができます。
exitは、 return文またはthrow文が実行されたときに発生します。
これらはもちろん、 通常の出口です。
メソッド呼び出しの結果としてスローされた例外(またはエラー)、 null参照へのアクセス、または意図しないプログラムの失敗を引き起こす他のアクションを伝播することによって、メソッド/コンストラクタの実行を突然終了させることもできます。

可能な各パスは、完全に実行される(カバーされる)か、またはカバーされない(カバーされない)ことができます。
部分的にしか実行されないパス(すなわち、突然終了したパス)は、単にカバーされていないパスとみなされます。

メソッドまたはコンストラクタ本体のパスカバレッジ率は、ラインカバレッジ計算と同様の方法で計算されます。
NPがインプリメンテーション本体を通る可能なパスの数であり、 NPEがエントリから出口に実行されるパスの数である場合、メトリックは100 * NPE / NPとして計算されます。
また、ライン・カバレッジ・メトリックと同様に、この式をソース・ファイル全体、パッケージ全体、およびテスト実行によって触れられたパッケージ全体に拡張します。

データカバレッジ

テスト実行によってインスタンスおよび静的非最終フィールドの数が完全に行使された回数を測定します。
完全に行使されるためには、フィールドに少なくとも1つのテストで読み取られた最後の値が割り当てられていなければなりません。
パーセンテージは100 * NFE / NFとして計算され100 * NFE / NFは非最終フィールドの数で、 NFEは完全に実行されたフィールドの数です。

カバレッジ出力のタイプ

JMockit Coverageツールは、次のタイプの出力を生成できます。

  1. HTMLレポート:複数ページのHTMLレポートは、現在の作業ディレクトリの下にある "カバレッジレポート"ディレクトリに書き込まれます(必要に応じて別の出力ディレクトリを指定できます)。
    ディレクトリがまだ存在しない場合は作成されます。
    以前に生成された場合、その内容は上書きされます。
    このレポートには、テストスイートで扱われるすべてのJavaソースファイルを含むページが含まれます。
    デフォルトでは、ツールは現在の作業ディレクトリの下に直接または間接的に存在する " src "という名前のすべてのディレクトリ内の " .java "ソースファイルを探します。
    " src "と最上位のパッケージディレクトリの間の中間のサブディレクトリ(例えば " src/java "など)も検索されます。
  2. カバレッジデータファイル:現在の作業ディレクトリまたは指定された出力ディレクトリの下に、 " coverage.ser "という名前のシリアライズされたファイルが1つ書き込まれます。
    ファイルがすでに存在する場合は、その内容が上書きされるか、または指定された現在のテスト実行のメモリ内の結果が追加されます。
    これらのファイルは、外部ツールで読み込んで処理することができます。
    mockit.coverage.data.CoverageData.readDataFromFile(File)メソッドは、指定されたシリアライズされたファイルで利用可能なすべてのカバレッジデータを持つ新しいCoverageDataインスタンスを作成します。

コールポイント

カバレッジツールを使用してテストスイートを実行する場合、オプションの「コールポイント」情報があり、ユーザーが選択したとおりに収集できます。
コール・ポイントは、ソース・テスト・コード内の特定の行の実動コードが実行されたポイントです。

この余分な情報でカバレッジを生成すると、時間がかかり、出力が大幅に増加します。
テスト実行中に特定の行の生産コードを実行させたテストコードの行を知ることは有用です。
HTMLレポートに含めると、コールポイントのリストは最初は非表示になっていますが、各実行可能コード行をクリックすると簡単に表示できます。

カバレッジツールの設定

JUnit / TestNGテスト実行でJMockit Coverageツールを有効にするには、ランタイムクラスパスにjmockit-1.x.jarを追加し、少なくとも " coverage-output|metrics|classes "システムプロパティを1つ指定します。
JUnitでは、 jmockit-1.x.jarがクラスパスの最初に表示されていることを確認してjmockit-1.x.jar 。
( JMockitによるテストの実行の詳細については、チュートリアルの該当するセクションを参照してください)。

JMockitモーキングAPIを使用しない場合、クラスパスにjarファイルを追加しなくてもコードカバレッジを有効にできます。
代わりに、JVM初期化パラメータとして " -javaagent:<proper path>/jmockit-1.x.jar=coverage "を実行します。

ほとんどの場合、カバレッジツールは追加の設定を使用する必要はありません。
ただし、ツールの動作にはいくつかの側面がありますが、これらの動作はオプションでテスト実行のために構成することができます。
これは、テストスイートを実行しているJVMインスタンスに対して、複数の「 coverage- xyz 」 システムプロパティのうちの1つ以上を設定することによって行われます。

JUnitまたはTestNGのいずれかを使用して、Antターゲット、Maven surefireプラグイン設定、または選択したJava IDE用のテスト実行設定内でこれらのプロパティを簡単に指定できる必要があります。
JMockit固有のプラグインは必要ありません。

使用可能な構成プロパティーは次のとおりです。

  1. [jmockit-]coverage- output : html 、 html-nocp (「nocp」は「no call points」を表す)、 serial 、およびserial-append間のカンマで区切られた1つ以上の値で、生成される出力の種類を選択します試運転の終わりに 何も指定されない場合のデフォルトは、基本HTMLレポート( html-nocp )を生成することです。
    "html"と "html-nocp"の値は、 "serial"と "serial-append"のように相互に排他的です。
    ただし、同時に指定された各ペアの1つを持つことは有効です。
    そのような場合、テスト実行の最後に、両方の種類の出力が書き込まれます。
    " serial "または " serial-append "が存在すると、名前 " coverage.ser "のserial-append されたデータファイルが生成されます。
    「 serial-append 」の場合、現在のテストランで収集されたカバレッジデータは、既存のデータファイルの内容に追加されます(ファイルが存在しない場合は、「 serial 」と同じ効果があります)。
  2. [jmockit-]coverage- outputDir : " coverage.ser "または " index.html "ファイル(HTMLレポートの残りの " .html "ファイル)を書き込むために使用される出力ディレクトリへの絶対パスまたは相対パス。
    自動的に作成されたサブディレクトリ)。
    デフォルトでは、実行中のJVMの現在の作業ディレクトリが使用され、HTMLレポートのすべての " .html "ファイルが " coverage-report "サブディレクトリ内に生成されます。
  3. [jmockit-]coverage- srcDirs :HTMLレポートを生成するときに検索されるJavaソースディレクトリのカンマ区切りのリスト。
    これは、シリアライズされたデータファイルには関係ありません。
    各ディレクトリは、絶対パスまたは相対パスで指定します。
    そのようなディレクトリが指定されていない場合、現在の作業ディレクトリの下のすべての " src "ディレクトリが検索されます。
  4. [jmockit-]coverage- classes - [jmockit-]coverage- classes :OSのような正規表現(典型的な " * "と " ? "ワイルドカード)、またはjava.util.regexに準拠した正規表現のいずれか。
    指定された式は、プロダクトコードから(完全修飾名で)クラスを選択するために使用され、カバレッジ対象とみなされます。
    デフォルトでは、テスト実行中にロードされた実動コード内のすべてのクラスと、jarファイル内にないすべてのクラスが考慮されます。
    たとえば、 " some.package.* "はsome.packageまたは任意のサブパッケージの下にあるすべてのクラスを選択します。
    特殊なケースとして、プロパティが " loaded "として指定されている場合は、すべてのクラスが考慮されますが、テスト実行中にJVMによってロードされるクラスのみが考慮されます。
    コードベースの一部であるがロードされないクラスは除外されます。
    これは、テスト実行にコードベースのサブセットのみを対象としたテストが少々含まれている場合に非常に便利です。
  5. [jmockit-]coverage- excludes :以前のプロパティと同じですが、カバレッジのクラスをインスツルメンテーションするときに考慮から除外されるクラス名のためです。
    このプロパティは、 coverage-classesと一緒に使用することも、単独で使用することもできます。
    デフォルトでは、カバレッジ対象として選択されたクラス間のクラスは考慮から除外されません。
  6. [jmockit-]coverage- metrics :カバレッジ情報を収集するコードカバレッジメトリックの特定のセットを選択するline (デフォルト)、 path 、 data 、およびall間のカンマで区切られた1つ以上の単語。
  7. [jmockit-]coverage- check - [jmockit-]coverage- check :テスト実行の最後に実行される最小カバレッジチェックを指定するセミコロンで区切られた1つ以上のルール。
    デフォルトでは、このようなチェックは実行されません。
    詳細は、「 最低保証範囲の確認 」を参照してください。

複数のテスト実行の集計レポート

カバレッジツールは、テスト実行の終了時にレポートを生成すると、以前のレポートを常に上書きします。
通常、レポートが生成されるカバレッジデータには、現在のテスト実行中に収集されたものだけが反映されます。
今度は、複数のテストスイートまたはテスト実行構成があり、一連のテストでカバーされているコード用の単一の集約HTMLレポートを生成したいとします。
ここには、 "coverage.ser"というシリアル化されたデータファイルが入っています。

これらのファイルの生成を有効にするには、 coverage-outputシステムプロパティを " serial "または " serial-append "を含む値に設定するだけです。
これらの2つの値が示唆するように、複数のカバレッジデータファイルを組み合わせる方法はいくつかあります。
次のサブセクションでは、それぞれのケースの詳細を示します。

複数のデータファイルから集計レポートを生成する

複数のテスト・ランからカバレッジ・データを収集し、後ですべてのテスト・ランからの結果をまとめて集約したHTMLレポートを生成するとします。
各テスト実行では、独自のcoverage.serファイルを生成する必要があります。
これにより、後でレポートを作成する最後のステップでマージすることができます。
したがって、各テスト実行は、 " coverage-output=serial "で構成する必要があります。
各テスト実行によって生成された元のcoverage.ser出力ファイルを保存するには、それらを異なる出力ディレクトリに書き込むかコピーする必要があることに注意してください。

2つ以上のcoverage.serファイルが別々のディレクトリで使用可能であると仮定すると、 mockit.coverage.CodeCoverage.mainメソッド(通常のJavaの「main」メソッド)を実行することによって、集約レポートを生成できます。
これを容易にするために、 jmockit-1.x.jarファイルが実行可能です。
例として、次のAntタスクを使用できます。

<java fork="yes" dir="myBaseDir" jar="jmockit-1.x.jar">
   <jvmarg line="-Dcoverage-output=html"/>
   <arg line="module1-outDir anotherOutDir"/>
</java>

上記の例では、別のJVMインスタンスが実行されるベースディレクトリとして " myBaseDir "が使用されています。
コマンドライン引数として、 " coverage.ser "データファイルを含む2つの出力ディレクトリが指定されています。
その他の設定パラメータは、 " coverage-xyz "システムプロパティで指定できます。
この個別のJVMインスタンスは、各 " coverage.ser "データファイルを読み込み、メモリ内のカバレッジデータをマージし、終了する前に集約HTMLレポートを生成します。

各テスト実行後に追加された1つのデータファイルからの集計レポートの生成

複数のテスト実行の実行から集約カバレッジレポートを取得する別の方法は、すべてのテストのカバレッジデータを単一のデータファイルに蓄積することです。
これは、すべてのテスト実行に同じ作業ディレクトリを使用するか、 coverage-outputDirを共有ディレクトリに指定して、各テスト実行に対してcoverage-output= serial-appendを実行することで実現できます。
さらに、シーケンス内の最後のテストでは、 coverage-outputプロパティのhtmlまたはhtml-nocpをserial-appendと一緒に指定する必要があります。
もちろん、最初のテスト実行では、このファイルからデータを読み取ってはなりません 。
したがって、最初のテスト実行の前にファイルを削除するか、または最初のテスト実行でcoverage-output=serial使用することによってファイルを削除する必要があります。

したがって、出力モード「 serial 」と「 serial-append 」の違いは、最初に複数の「 coverage.ser 」ファイル(別々のテスト実行で使用される別のディレクトリにあります)を持ち、すべてのテスト実行の間に単一のデータファイル。

最小カバレッジの確認

必要に応じて、JMockit Coverageは、テスト実行の最後のカバレッジパーセンテージが任意の最小値を満たしていることを確認できます。
そのようなチェックは、 " coverage-check "システムプロパティに割り当てられた1つ以上のチェックルールによって指定できます(複数の場合は、 ";"文字で区切る必要があります)。

各検査ルールは、「[ スコープ :]最小行パーセント[、最小パスパーセント[、最小データパーセント]]」の形式でなければなりません。
スコープには3つのタイプがあります。

  • 合計 :スコープが指定されていない場合のデフォルト値。
    これは、各メトリックの合計パーセンテージを示します。
    たとえば、ルール「 80 」は、総ラインカバレッジが少なくとも80%であり、他のメトリックに対して最小パーセンテージがないことを指定します。
    3つのメトリックのすべてについて閾値を指定する例は、「 70,60,85 」とすることができる。
    「 0 」の値は、最小値を指定しないためにも使用できます。
  • perFile : 各ソースファイルが満たさなければならない最小パーセンテージを指定します。
    1つ以上のファイルのパーセンテージが低くなると、チェックに失敗します。
    例: " perFile:50,0,40 "。
    これは、各ソースファイルの行カバレッジが50%以上で、データカバレッジの少なくとも40%が必要であることを意味します。
  • パッケージ :サブパッケージを含む、指定されたパッケージ内のソースファイルセットの最小合計パーセンテージを指定します。
    たとえば、「 com.important:90,70 」というルールは、「 com.important 」の下にあるファイルの合計回線カバレッジは90%以上、合計パスカバレッジは少なくとも70%になるように指定しています。

すべての検査(ある場合)は、テスト実行の最後に実行されます(JVMシャットダウン時)。
他の形式の出力(HTMLレポート、シリアライズされたファイル)は影響を受けません。
個々のチェックが失敗すると、説明的なメッセージが標準出力に出力されます。
1つ以上のチェックが失敗した場合は、2つの最終的なアクションが実行され、事実が報告されます。
まず、 coverage.check.failed 。
チェック不能な名前の空のファイルが現在の作業ディレクトリに作成されます。
AssertionError 、エラー(具体的にはAssertionError )がスローされます。
チェックが実行されてもすべてが合格すると、カレントディレクトリに存在する " coverage.check.failed "ファイルが削除されます。

カバレッジチェックの成功または失敗をマークするためのファイルの使用は、ファイルが存在するときにビルドに失敗することによって、ビルドツールがそれに応じて反応することを可能にすることを目的としています。
たとえば、Antビルドスクリプトでは次のことができます。

<fail message="Coverage check failed">
   <condition><available file="coverage.check.failed"/></condition>
</fail>

Mavenのpom.xmlファイルでは次のようになります。

<plugin>
   <artifactId>maven-enforcer-plugin</artifactId>
   <executions>
      <execution>
         <id>coverage.check</id>
         <goals><goal>enforce</goal></goals>
         <phase>test</phase>
         <configuration>
            <rules>
               <requireFilesDontExist>
                  <files><file>target/coverage.check.failed</file></files>
               </requireFilesDontExist>
            </rules>
         </configuration>
      </execution>
   </executions>
</plugin>

Mavenプロジェクトでカバレッジを有効にする

Mavenの "テスト"目標を使ってテストを実行する場合、 pom.xmlファイルに " jmockit.version "プロパティが適切に定義されていると仮定して、 "jmockit"依存関係が必要になります。

<dependency>
   <groupId>org.jmockit</groupId>
   <artifactId>jmockit</artifactId>
   <version>${jmockit.version}</version>
   <scope>test</scope>
</dependency>

Maven 2/3では、 surefireプラグインは、通常、実際にテストを実行する責任があります。
カバレッジツールをアクティブにして設定するには、適切な " coverage-xyz "システムプロパティの値を指定します。

<plugin>
   <artifactId>maven-surefire-plugin</artifactId>
   <configuration>
      <systemPropertyVariables>
         <!-- At least one of the following needs to be set: -->
         <coverage-output>html</coverage-output>     <!-- or: html-nocp, serial, serial-append -->
         <coverage-metrics>all</coverage-metrics>    <!-- or: line, path, data -->
         <coverage-classes>loaded</coverage-classes> <!-- or a "*" expression for class names -->

         <!-- Other properties, if needed: -->
         <coverage-outputDir>my-dir</coverage-outputDir>       <!-- default: target/coverage-report -->
         <coverage-srcDirs>sources</coverage-srcDirs>          <!-- default: all "src" directories -->
         <coverage-excludes>some.package.*</coverage-excludes> <!-- default: empty -->
         <coverage-check>80</coverage-check>                   <!-- default: no checks -->
      </systemPropertyVariables>
   </configuration>
</plugin>

最後に、テストでJMockitモーキングAPIを実際に使用しない場合でも、 "jmockit"依存関係がなくてもカバレッジツールを使用することは可能です。
必要なのは、 surefireプラグインを次のように設定することだけです。

<plugin>
   <artifactId>maven-surefire-plugin</artifactId>
   <configuration>
      <argLine>
-javaagent:"${settings.localRepository}"/org/jmockit/jmockit/${jmockit.version}/
jmockit-${jmockit.version}.jar=coverage
         <!-- coverage properties -->
      </argLine>
   </configuration>
</plugin>

MavenサイトにHTMLレポートを含める

生成されたMavenサイトのドキュメントにJMockit Coverage HTMLレポートを含めるには、 src/site/site.xml記述子ファイルを提供する必要があります。
内容は以下のようになります。

<?xml version="1.0" encoding="UTF-8"?>
<project
   xmlns="http://maven.apache.org/DECORATION/1.3.0"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xsi:schemaLocation="http://maven.apache.org/DECORATION/1.3.0
                       http://maven.apache.org/xsd/decoration-1.3.0.xsd">
   <body>
      <menu ref="reports"/>
      <menu>
         <item name="Code Coverage Report" href="../../coverage-report/index.html"/>
      </menu>
   </body>
</project>

カバレッジをオフにする

特定のテスト実行でカバレッジを一時的にオフにするには、 coverage-outputシステムのプロパティを " -Dcoverage-output= none "のような未知の出力形式に設定します。
" -Dcoverage-metrics= none "または " -Dcoverage-classes= none "を設定すると、同じ効果が得られます。

もう1つ、よりインタラクティブな方法は、関連する出力ファイルがすでに生成されている場合に、その出力ファイルの読み取り専用属性を操作することです。
作業ディレクトリ内で常に操作される特定のファイルは、シリアル出力の場合は " coverage-report/index.html "、HTML出力の場合は " coverage-report/index.html "です。
ファイル属性は起動時にJMockitによってチェックされます。
読み取り専用としてマークされている場合は上書きできないため、JMockitはその試みを完全に回避します。
作業ディレクトリは、通常、Java IDEのテスト実行構成ごとに個別に選択することができます。
また、Java IDEは通常、プロジェクト内のファイルの読み取り専用ステータスを切り替える簡単なメカニズムを提供します。
IntelliJ IDEAでは、ステータスバーをダブルクリックして、エディタで目的のファイルを開き、 Eclipseではエディタで選択されたテキストファイルの "プロパティ"画面( "Alt + Enter"と入力すると開くことができます)に "読み取り専用"チェックボックスがあります。


トップ   差分 バックアップ リロード   一覧 単語検索 最終更新   ヘルプ   最終更新のRSS
Last-modified: 2018-03-24 (土) 20:10:22 (628d)