Androidでレガシーコードを書き続けないためのたった1つの方法

答え:テストできるように作る

 

周りでAndroid開発してる話を聞くのですが、どうもテストがしづらかったり、修正が大変だったりする模様。ここを直してあそこがバグるみたいな。

本屋で参考になりそうな本を探すも、入門系かリファレンス系が殆どで、「どういう設計にするべきか?」とか「Android Test」とかAndroid向けフレームワークの話がさっぱり無い。そんな状況なので、入門書片手にアプリを書き始めた人は、ViewとLogicを始め、色々なものが適切に分けられてないコードを作り、テストの無いレガシーコードが量産されていくのかな、と。

 

そういう分けで最初の結論になります。

ちょうど、ちょっとしたAndroidアプリを書いてみようと思ってたので、ここら辺を参考に実際のアプリに先立っていくつかのフレームワークを組み合わせたAndroid-Development-Suiteを作成。

いわゆるサンプルアプリですねw

これをcloneするなり何なりして使えば、テストがある状態、書ける状態から戦いを挑めるはず><

既存コードにテストを入れるときの参考にも一応なるはず。

https://github.com/koduki/Android-Development-Suite

 

内容的には、まずはビルド基盤としてmavenを導入。

どうもEclipse上で全部やるのがトレンドな気はしますが、CIはじめ自動化を考えるならビルドツールは必須ですよね。というかIDE完結とか自動化する気無いだろ...

ant + ivyやgradleとかも悩みましたが、機能とよく使われてるという点を考慮してmavenを選択。

通常ビルドやテストはもちろん、Androidへのデプロイやリリース用にproguradや署名かけることも可能です。

リリースビルドに署名をするときのkeystoreやパスワードは、直接pom.xmlではなく、~/.m2/settings.xmlに書くようにしています。てか、ここに独自程度のプロパティ書けたんですね。知らなかったです。便利。

また、JDK7から、keytoolの仕様が変わってしまい、Androidと互換性のある署名を作れないので、JDK6から実施するようにしてください。

 

Eclipseのみの開発でテスト用とリリース用でコードを直接書き換えてたあなたもこれで幸せになれますね!

ただ、一部、私のmaven力が足らなくて、シェルにしてしまったので、誰か教えてください>< もしくはpull request大歓迎!

 

次に入れたのがandroid-binding。こいつはAndroidでMVVM(MVP)モデルを実現するためのもの。古典的なMVCモデルやWebでお馴染みのMVC Model2だと、プレゼンテーションロジックをどこに書くかいつも悩むので、MVVMでやって見ることに。まあ、マイクロソフトとかが前からやってる感じのやつですね。これでActivityがごちゃごちゃさせずに、POJOでテスト出来るところが増えるはず! ViewModelはPOJOですので。

 

土台系としてはDIも導入。Google GuiceAndroid版のroboguice。ネットワーク周りとか副作用のあるテストをモックに切り替えるのが目的。しかし、設定ファイルじゃないので、ビルドオプションで簡単に実装変えるわけにもいかず、結果変な実装に。この辺はもっと良い方法を考えないと。

 

DIを入れたからにはMockツールもということでMockitoを入れました。EasyMockベースのAndroidMockというのもありますが、Mockitoも最新版はAndroid対応なので、評判のよさげなMockitoに。

なにげにこの手のツールを初めて使ったんですけど、かなり便利。ネットワーク系をラップできるのは強力なので、他のところにもどんどん入れてこうと思います。

ちなみに、サンプルで作ったテストケースが少し無理矢理というか、ふつうにUnitTestを書けば十分なのは、まあ、サンプルという事でw

 

で、最後に実機やエミュレータに対する結合テスト用にCabash-Android

最初はSelenium(NativeDriver)を使おうとしてたんですけど、結構めんどくさかったので、他のを探して見ることに。そしたらなんとCucumberが使えるじゃないですか、奥さん!

というわけで、迷わず導入。NativeDriverより導入するのも記述するのも簡単だし、スクリーンショットも取れるのでいうことなしですね! まだ、できない操作があるかまでは確認できてないけど、その辺は使いながらおいおい。

Cucumberなので、テストケースをそのままテスト仕様書としても使用可能なのがGoodです。

 

あと、もちろんmavenを使ってるのでプロファイルで、いくつか環境を切り分けれるようにしています。

mockをインクルードするdevelopmentプロファイル、mockを使わないproductionプロファイル、Proguard等をかけるreleaseプロファイル。resourcesディレクトリをprofileに対して別にしてるので、環境依存とかはここに吸収する感じで。

これで、CIで回すと、ひたすらツイートされ続けるという残念な状況も解決です。

 

と、こんな感じで、Webアプリ作るならこの辺入れるだろー、というのと同程度のものを導入して覽ました。ORMはまだ入れてないので、なんか入れようとは思います。Android初心者の私が作ったものなので、色々考慮不足が有りそうですが、これをベースにアプリを作ってFB を重ねていきたいですねー。

 

参考: