アプリはリリースして終わりというわけでなく、むしろリリース後からが長い。すぐにアップデートをできないことからも、リリース後に不具合が発生していないか継続的に監視・調査する必要がある。ユーザーがアプリの機能を正常に利用できない状況は、アプリのみならずコンテンツの価値を損ねる。そのためにも早急に把握し修正を施さなければならない。
リリース後には予想だにしなかったような様々な不具合の可能性が起きうる。例えば、アプリに潜在的に含まれていたバグ、OS のバージョンによるものや端末に依存するもの、API のレスポンスの返り値が不正なことで起きたもの、広告や計測に使用しているライブラリに起因するもの、連携アプリのアップデートによるものなどがある。
問題を把握し、日々のアプリの改善サイクルの中で不具合に対応する。そのためにも、いつ、どこで、何が、どのくらいの頻度で起きているのかを分析するための手段を用意する。優先順位の判断、解決の手がかりとなるログを集めることが重要である。
顕在化していない問題を知る
日経のアプリでは改善リクエストという、ユーザーがご意見ご要望を送信する機能が設けてある。ご意見ご要望がポストされると slack のチャンネルに通知が来る。投稿には、ユーザーのご意見、アプリのバージョン情報、OS/デバイス情報、IP アドレス、会員 ID…のような情報が含まれている。平時には改善の要望を吸い上げるため、またバグを把握するための手がかりとして利用している。そして異常時には複数のユーザーから投稿があるため緊急速報として機能する。
ログから問題を読み取る
Fatal なエラーの検知には Crashlytics を使用している。Crash が激増した場合に Fabric から通知が送られてくるので異常事態を速やかに察知することができる。ログに含まれる StackTrace を元にして、次のリリース時に修正コミットを積んでいく。
Non-Fatal なエラーの把握には3つのツールを活用している。まずは Crashlytics で、logException メソッドを仕込む。Timber.plant で Tree クラスを継承した ReportingTree をセットする。Timber メソッドが実行されるタイミングで Tree の Throwable を引数にもつ log メソッドが呼ばれる。ここに logException メソッドを仕込むことで、Timber でのデバッグログ計測とレポートの収集を同時に行うことができる。Crashlytics には Custom Key をセットすることができるので状況を細かに把握することができる。このキーの上限は最大 64KB で、各ペアの上限は 1KB なので大きな情報は送れない。
そこで、内製のロガーを併用している。ログは改善リクエストと同じく Slack に通知される。AWS に用意されたエンドポイントに、必要なデータをセットしポストする。API のレスポンスエラーなど、送付したいデータが大きいことが予想される場合にあると便利である。
ANR はアプリが落ちているわけでないため Crashlytics による検知ができない。しかし、ユーザーからはアプリのフリーズは落ちた状態と同義に捉えられる。Android Vitals に Trace Log が上がり、StackTrace と同様にアプリのどこでユーザーが止まっているかを確認できる。アプリは落ちていないがアプリを操作できない状態に変わりがないため優先して対応すべきだ。
サービスを提供していく中で必ず不具合は発生する。いざ起きたときに、迅速に不具合の存在を把握できるようにする。そして、解決するための当たりをつける手段を確保することが改善サイクルを充実させる。
参考:https://speakerdeck.com/srym/journey-to-99-percent-crash-free