弊社は、ApplivというアプリをiOS、Android向けに提供しています。 今回はこのうち、Androidのアプリのコードを1から書き直すという事をしたので、どんな風に変わったのかをご紹介したいと思います。

そもそもどんな状態だったのか?

作り直した、ということはそれなりに理由があった訳ですが、大まかに理由として

  • Activityに機能を突っ込みすぎて、メンテがしづらい
  • Activityのライフサイクルがあまり考慮されていないので、Activityを参照できない類いのクラッシュが割と多い(非同期まわりの処理)
  • テストが空っぽ。テスト書くとしても密結合な設計なので非常に書きづらい

だいたいこんな感じです。

既存部分に手を入れたいんだけれども、どこに影響があるか分からないから既存部分はそっとしておいて、既存処理の最後に新しい処理を入れて…ってことを繰り返してきたので、なんというか「コードが腐る」といった感じを目の当たりにした気がします。
弊社のAndroidアプリの開発は今回が初めてということもあり、割と「とりあえず作ったれ!」的な手探りな感じで作ってしまったので、とりあえず動きはするけれども今後を考えると非常にメンテナンスコストとリスクの高いものになってしまいました。

作り直し

というわけでアプリを作り直しました。
アプリを世に公開してからまだ半年くらいしか経ってない中での話だったので多少躊躇しましたが、むしろまだ機能の少ないときの方がやり直しがしやすかったので、なんとかまとまった時間を確保して作り直しに踏み切りました。

何を実現したいのか

とはいえ、何も考えずにコードを書き始めると、また今までと同じようなコードを生み出してしまうので、まずは今までやってきた中でApplivアプリの開発における特徴を捉えて、その上で最低限なにを実現したいのかというところを考えました。

これまで半年近く作ってきて感じた、Applivアプリの開発の特徴はこんな感じです。

  • ハイペースに新機能の追加が入る
  • 既存機能の仕様変更もしょっちゅう入る

要は1回作ってハイ終わりって事がほとんど無いので、新しい機能はスピーディーに作れないといけないし、さらに既存の機能も手を入れやすくないとやっていけないわけです。

その上で考えた、Applivアプリで実現したいことは、

  • メンテしやすいコードにしたい
  • テストしやすいコードにしたい
  • 極力クラッシュしないようにしたい
  • 新しい技術やライブラリなどを試しやすくしたい

この辺が実現できれば、開発が大幅にやりやすくなるなぁと思いました。

設計を考える

Android Clean Architecture

その上でどんな設計がApplivアプリにマッチするか色々探しましたが、結果としてAndroid Clean Architectureというものを参考にしました。
https://github.com/android10/Android-CleanArchitecture
これは、元々Clean Architectureとして提唱されていたものを、Android向けに最適化させたものになります。
Android Clean Architectureは、アプリの中を役割に応じて3層のレイヤーに分けることによって、Clean Architectureのコンセプトを実現させようとしています。

  • Presentation Layer(画面周りの機能)
  • Domain Layer(ビジネスロジック)
  • Data Layer(データ取得周りの機能)

これらのレイヤーはそれぞれに影響を与えないように独立し、レイヤー間のやりとりはインターフェースを使って行われます。

これを実現することで、画面周り、ビジネスロジック、データ取得周りのロジックがキレイに分かれるので、格段にメンテがしやすいコードになります。
実際に、現在のAndroidアプリではこの設計を取り入れているので、Activityの中にリポジトリからデータを取得するみたいなコードが出てくることはなくなりました。

RxJava

加えて、Androidアプリでは非同期の処理にRxJavaを使ったリアクティブプログラミングを採用しています。
RxJavaを採用するメリットは色々あると思うのですが、今回の場合は大きくこの2つかなと思います。

  • 非同期処理の管理がやりやすくなる
  • レイヤー間、クラス間をObservableでやりとりできる

詳細はまた別の機会にお話できればと思いますが、非同期処理の管理がやりやすくなることによって、ActivityやFragmentが破棄された後に非同期処理のコールバックが戻ってきたとしても制御がしやすくなります。

また、Observableはどのスレッドで処理を走らせるか明示的に設定できるオペレーションが存在するので、 クラス間をObservableでやりとりできることによって、それぞれのメソッド自体は自分自身が非同期に処理されるのか、同期的に処理されるのか個別に気にする必要が無くなります。

Android Clean ArchitectureとRxJava、この2つの要素を設計のベースとして取り入れる事によって、Applivアプリはエンジニアにとってとても扱いやすいプロダクトに生まれ変わったのです。

結局どうなった?

設計時に実現したいこととして挙げた4つですが、今回の設計見直しによっていずれも解消することが出来ました。

メンテしやすいコードにしたい

Android Clean Architectureを採用し、クラスの役割に応じて内部構造をレイヤー分けしたので、クラス同士の影響が限定的になりました。
さらに、どこにどの役割のコードがいるのか明確になったので、機能追加の場合、既存機能の改修の場合のどちらでも手を入れやすくなりました。

テストしやすいコードにしたい

1クラス、1メソッドで実現することが限定的でハッキリしているので、テストする際にも「何についてテストをすればいいのか」というのが明確になり、テストコードが書きやすくなりました。
加えて、今までは何か機能を修正する際には、コードを直しては実機でデバッグし、おかしければまたコードを直して実機でデバッグ…というのを繰り返していたので非常に効率が悪かったのですが、リファクタリング後はテストコードによってその機能がちゃんと動いているか確認できているため、実機でのデバッグ時間を大幅に減らすことができました。

極力クラッシュしないようにしたい

RxJavaのObservableによって、同期処理、非同期処理の管理がやりやすくなったので、不用意なクラッシュを避けられるようになりました。

新しい技術やライブラリなどを試しやすくしたい

1つのクラスや機能の影響箇所が限定的になったので、ライブラリの入れ替えや新しい技術も試しやすくなりました。

今回の作り直しで、初期の頃の「とりあえず作ったれ!」な失敗を経験して、きちんと設計を考えることの大切さを学ぶことが出来ました。
またそれだけでなく、「コードは放置しといたら腐る」ということも実感したので、日頃の開発サイクルの中にも既存のコードを見直すというプロセスも取り入れるようにしました。
具体的には、1日の業務時間のうち約1時間をコードメンテの時間に充てています。今作っている機能とは関係ない部分でも、テストはちゃんと書けているか、不要なコードは残ってないか、書き方的におかしくないかというのをその時間で見るようにしたので、既存のコードも鮮度を保つことが出来るようになりました。

まとめ

今回は、アプリの作り直したときに自分が考えていたことをまとめてみました。
あまり既存のモノを1から作り直すということは今までできなかったので、いい経験になったんじゃないかなと思います。
今回は技術的な所にあまりフォーカスして内容を広げられなかったので、次回以降でどんな技術を使ったのかご紹介できればと思います。

また、今回ご紹介したApplivアプリはこちらからダウンロードできますので、是非使ってみてください!
Get it on Google Play