スポンサーサイト

上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

[Java][Eclipse]EclEmmaのJaCoCoが気になる

EclEmmaに関連して書いたJaCoCoについて、少し分かってきたのでメモ的なまとめ。
使い方などは公式ドキュメントが詳しいのでいいとして、このエントリはどちらかというと自分なりの解釈込みの周辺情報です。
# 間違ってたらコメントいただけると助かります。

JaCoCo -Java Code Coverage Library
http://www.eclemma.org/jacoco/trunk/index.html

■JaCoCoってどんなの?
JaCoCoはEclEmmaの開発チームが、EMMAを置き換えるためのカバレッジライブラリとして
開発を進めてきたものです。
今までも単体で利用できましたが、EclEmma2.0で晴れて組み込まれました。

ドキュメントをつらつら読んでみたのですが。
既存のカバレッジライブラリは拡張性が乏しく、すでにメンテされていないEMMAを使い続けるよりは
自分たちで拡張や統合が容易な物を作っちゃお、という事になったようです。
JaCoCoは、Antタスクでの実行、Mavenプラグインなどのフレキシブルな運用を可能にし、
バックエンド技術として、もちろんEclipseプラグインとしてEclEmmaで使うことも目的としています。

■個人的に抜粋した特徴
  • C0に加えてC1(ブランチカバレッジ)の計測が可能
  • Javaバイトコードに対して計測(別エントリでもう少し詳しく)
  • サイクロマチック数の計測
  • HTML,XML,CSVでのレポート出力
  • Antタスクとしての実行
  • EPL(…これはいいか)
C1の計測とAntタスクは利用価値高いですねぇ。
サイクロマチック数は実装者への戒めでしょうか…

■計測方法(JaCoCoだけで)
EMMA同様、クラスファイルに計測用のコードを埋め込んで実行という形をとるようですが、
javaagentを利用したon-the-fly方式を採用することで、バイナリに直接埋め込むのではなく、メモリ上にクラスをロードする際に前処理を挟んでいるようです。(Pleiadesと同じ感じ。)
EclEmma1.5以前まで存在していた、In-place計測もなくなっていました。

実行データの出力は、リモートへの出力などいろいろな形式があるようですが
よくわからないので、今回は単純にローカルファイルに書き出します。

・実行方法
引数に-javaagentを指定する形です。
こちらからjacocoagent.jarを入手して下さい、zipを解凍すると入っています。

・実行例

java -javaagent:jacocoagent.jar %あとは実行クラスやらクラスパスやら%

引数はとりあえずナシで…^^

するとJVM終了と同時に以下のファイルが出てきます。

jacoco.exec

これが結果みたいです(EMMAでいうecもしくはesファイルかな)
でも中身は理解できる形のものではありません。

■レポート出力(JaCoCoだけではむりっぽい)
そこでレポート出力ですが、JaCoCo単体では出力が難しいみたいです。
Antタスクで出すか、EclEmmaに上記結果をインポートして出力するのが無難っぽいです。

一応、JaCoCoのソースも見てみましたがJaCoCo単体でレポートを出す方法はみつからず。
でもAPI Usage Examplesに、サンプルとしてこんな物がありました。
http://www.eclemma.org/jacoco/trunk/doc/examples/java/ReportGenerator.java
検証してないけど使えそう。
execファイルをプロジェクト直下にもってくる必要はありそうですね。

以上、とりあえず今回は概要と計測、レポートの出力について書きましたが
別エントリーでもう少し書いていきます。


☆余談
全然関係ないけど、最近きゃりーぱみゅぱみゅが気になってしょうがないです。
ぽーんぽーんうぇいうぇいうぇい♪ぽんぽんうぇいぽんうぇいぽんぽんっ♪
スポンサーサイト

theme : ソフトウェア
genre : コンピュータ

[Java][Eclipse]EclEmmaフィルタ機能の誤解

#このエントリーはEclEmma1.5.3をベースにしております。
#2.0.0のリリースで大きく仕様が変わりましたのでご確認ください。

EclipseでEclEmmaを利用されている方は多いと思います。
自分も使っているのですが、ヘルプを見てもわからない設定がありました。
EclEmmaのフィルタリング設定です。

Emmaをオフラインモードで使用する場合は、まずclassまたはjarへの
インストール(metadataの生成)が必要です。(詳しくはコチラ
そしてEmmaには、インストールの際カバレッジ計測対象クラスを
フィルタリングする機能があります。これですね→6.2. Coverage filters

フィルタ機能が地味に便利なのは、他のクラスの変更による影響を受けなくてすむ点です。
Emmaはクラスを変更すると、メタデータとカバレッジデータのTimeStampの違いから
すぐレポートが吐けなくなるのですが、スコープを絞ることでその可能性を極力減らすことができます。
(再計測すればいいジャンというのは、オフラインモードというところから察してください…)

でこの機能、当然EclEmmaもサポートしているはず…と信じて設定を見ると。
「ウィンドウ>設定>Java>コード・カバレッジ」にこのような↓項目があります。(クリックして拡大)

EclEmmaPreference

EclEmmaのヘルプ引用先(2.0で内容が変わりました)によると

  • Source folders only: Consider source based class path entries only. (Default: on)
  • Same project only: Pick only class path entries from the same project. This option works only for launch configurations that have a project associated, i.e. Java applications. (Default: off)
  • Only path entries matching: Comma separated list of strings, that must match with the class path entry. A class path entry matches the filter, if it contains one of the given strings. (e.g. "src/main/java", Default: no filter)



やった、Only path entries matchingでフィルタイングできるようです。ばんざーい。

しかし喜んだのもつかの間、ここでハマりました。どうやってもフィルタリングできない…
最終的にEclEmmaのソースとステップ実行で、やっと確認できたのですが。
これクラスパスに追加されているパスしかダメみたいです。
※確かにヘルプに書いてあるんですけど、先入観は怖い…てか例がおかしくない?

つまりクラス単位ではなく、まず%PROJECT_ROOT%/bin
あとはjarとかその他クラスパスに入っているものから、フィルタに
一致したもののみカバレッジを取得する…

って、それEmmaのフィルタと違うじゃぁーんヽ(●`Д´)ノ

おしまい

-----------------
■12/28追記
2011/12/18にEclEmma2.0.0がリリースされました。なんとタイムリー。。
2.0.0から、同チームが開発を進めていたJaCoCoという
カバレッジツールを使用しています。

また、設定でクラス単位でのフィルタが可能になっていました。Great!
http://www.eclemma.org/userdoc/preferences.html

機会があったら、また別のエントリで書きたいと思います。
残念ながらレポートの書式が変わってしまったため、EMMAベースで作っていた
独自の周辺ツールがついて行けてないので、すぐ実運用はできないかもしれません…

theme : ソフトウェア
genre : コンピュータ

[Java][Eclipse]JFaceのListViewerでアイコン表示

SWTのListにアイコンを表示することが出来ないかと調べていました。
すると、JFaceのListViewerを使用すれば表示が拡張できることがわかりました。
JFaceのViewerフレームワークは、それだけでは扱いづらいSWTのWidgetに強力なサポート機能を提供してくれます。

ListViewerは、LabelProviderのgetTextメソッドをオーバーライドして、ListのItemであるオブジェクトをどう表示するか自分で拡張できます。デフォルトはObject#toString()の戻り値です。

ソースは以下、ここではアイテムの文字列に簡単なインデックスを追加しています。

import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.viewers.ListViewer;
import org.eclipse.jface.window.ApplicationWindow;
import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.List;
import org.eclipse.swt.widgets.Shell;


public class ListViewerSample extends ApplicationWindow {

    public static void main(String[] args) {
        new ListViewerSample();
    }

    public ListViewerSample() {
        super(new Shell());
        setBlockOnOpen(true);
        open();
    }

    @Override
    protected Control createContents(Composite parent) {
        List list = new List(parent, SWT.NONE);
        // ListViewerに接続
        ListViewer viewer = new ListViewer(list);
        viewer.setLabelProvider(new LabelProvider(){
            private int index = 0;

            @Override
            public String getText(Object element) {
                // インデックスを追加
                return index++ + ":" + element.toString();
            }
        });

        viewer.add("Item");
        viewer.add("Item");
        viewer.add("Item");
        viewer.add("Item");
        return parent;
    }
}


実行結果はこちら

ListViewer

そして、今回行いたいのが、このリストのアイテムにアイコンを表示することなのですが。。。
これができない!

LabelProviderにはgetImageというメソッドもありまして、これをオーバーライドしてImageを返してあげれば表示されるものと思い込んでいたのですが、表示されませんでした。

でも同じくJFaceのTableViewerではこれが出来てしまうのです。
ソースは次のようになります。

import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.jface.window.ApplicationWindow;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.Table;


public class TableViewerSample extends ApplicationWindow {

    public static void main(String[] args) {
        new TableViewerSample();
    }

    public TableViewerSample() {
        super(new Shell());
        setBlockOnOpen(true);
        open();
    }

    @Override
    protected Control createContents(Composite parent) {
        Table table = new Table(parent, SWT.NONE);
        // TableViewerに接続
        TableViewer viewer = new TableViewer(table);
        viewer.setLabelProvider(new LabelProvider(){
            @Override
            public Image getImage(Object element) {
                // Imageを生成して返す
                Image icon =
                    new Image(
                            Display.getDefault(),
                    ".\\images\\generic_element.gif");
                return icon;
            }
        });

        viewer.add("Item");
        viewer.add("Item");
        viewer.add("Item");
        viewer.add("Item");
        return parent;
    }
}

実行結果はこうなります。

TableViewer_Icon

まさにやりたかったことはこれなのですが。。。
アイコン表示するにはTable使わないといけないのかなぁ。

同じ実装をListViewerに対してやっても無理なのです。
嫌だなぁ。。

more...

theme : ソフトウェア
genre : コンピュータ

自己紹介

煩悩即菩提

Name:煩悩即菩提


三流SEです。
開発は基本Javaです。
Androidアプリ作り隊。。

お絵かきを少々しとります。
こちらもぱっととしないのが悩みです。

bonnosokubodaiをフォローしてください

Pixivアカウント

カレンダー   
Recomend


ビデオニュース・ドットコム
検索フォーム
最新記事
最新コメント
月別アーカイブ
カテゴリ
最新トラックバック
リンク
上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。