概要
Randoopは、Java用テストクラスジェネレータ、指定したクラスのJUnit形式のテストクラスを自動生成する。
特徴
ソースから、リグレッションテストと、エラー検知テストを生成する。
Randoop generates unit tests using feedback-directed random test generation
フィードバック指向のランダムテスト生成だそうです。
OpenJDKのバグを見つけた実績があるそうです。
https://randoop.github.io/randoop/manual/index.html#Introduction
ユースケース、業務のどこに使えるか(いつ使うか、どのように使うか)
”自前で作るテストケース以外の方法で”デグレを検知できる。
注意点、リスク
コードの改修に合わせて、Randoopのテストもメンテナンス(自動生成しなおし)する必要がある。
導入するなら、ある程度自動化が進んでいるプロジェクトの方が良さそう。
使い方
(参考)GitHubプロジェクト
SumServiceを利用して、MultiplyServiceを実装しています。
(MultiplyServiceは、SumServiceに依存)
SumService、MultiplyServiceのソース
https://github.com/taka2/randoop-sample/tree/master/src/main/java/randoop_sample
1. テスト生成対象クラスをmyclasses.txtに書く
randoop_sample.SumService
randoop_sample.MultiplyService
2. Randoopでテストクラスを生成する
java -classpath $(RANDOOP_JAR) randoop.main.Main gentests --classlist=myclasses.txt --timelimit=60
生成されたクラス
https://github.com/taka2/randoop-sample/tree/master/src/test/java
3. 生成したクラスをそのまま実行する
これは当然テストが全ケースパスする。
4. SumServiceを修正する
return a+b;
を
return a+b+1;
にする。
939/946がfail。SumServiceもMultiplyServiceもデグレしているので、ほとんど全てのテストがfailする。
5. MultiplyServiceを修正する
SumServiceを元に戻して、MultiplyServiceを修正する。
for(int i=0; i<b; i++) {
を
for(int i=0; i<=b; i++) {
にする。
482/946がfail。MultiplyServiceのみデグレしているので、半分くらいのテストがfailする。
結論
繰り返しになりますが、メリットでデメリットはこんな感じかと。
メリット
”自前で作るテストケース以外の方法で”デグレを検知できる。
デメリット
コードの改修に合わせて、Randoopのテストもメンテナンス(自動生成しなおし)する必要がある。
そもそも、ErrorTestが生成されなかったり(エラーがないから?)、RegressionTestも生成されないケースがあったり、結構不安定なので、いまいち未完成なのかなと思ったり。実戦投入は厳しいかなと思う。。
java.util.TreeSetのテストクラス生成に失敗したケース。
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : (java.util.Collection extends E>) -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : (java.util.Collection extends E>) -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : (java.util.Collection extends E>) -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : (java.util.Collection extends E>) -> java.util.TreeSet
Instantiation error for operation java.util.TreeSet. : () -> java.util.TreeSet
...
参考資料
- Randoop: Automatic unit test generation for Java
- GitHub - randoop/randoop: Automatic test generation for Java
- AWS Well-Architected フレームワークによる クラウド ベスト プラクティス
- https://d0.awsstatic.com/events/jp/2017/summit/slide/D2T1-1.pdf
- Randoopは、このドキュメントで見つけました。