Androidアプリを開発する上で賢いLogの出力方法(とその確認の仕方)

今までずっとLog.d("test",”デバッグメッセージだよ”);みたいな感じでLogを出力し、Logcatで確認しながらプログラミングしていたのですが、とあるサンプルを見ていた時にこんなコードに出くわしました。

    private static final String TAG = "DigitalWatchFaceConfig";

        if (Log.isLoggable(TAG, Log.DEBUG)) {
            Log.d(TAG, "onConnected: " + connectionHint);
        }

プログラムを実行しても、このログはlogcatに出力されません。

「なんでだ?」と思って調べているうちに、この方法はAndroidアプリ開発していく上で賢い選択なのだなということが分かってきました。

ベストプラクティスなのかどうかまでは分かりませんが、少なくともいきなりLog.d()で出力したり、アプリ内でprivate boolean isDebug = true;みたいにしてデバッグログを出力させるよりは賢いなと思いました。

参考サイト

[Log.isLoggable – API Refference](https://developer.android.com/reference/android/util/Log.html#isLoggable(java.lang.String, int))

ログレベルを制御する – TechBooster

ログの出力はアプリのパフォーマンスを下げる

ログの出力はアプリのパフォーマンスに影響します。少なくともStringオブジェクトを作ってそれを出力するわけですからね。

リリース時にはLog出力する部分を全部削除するのが一番いいのでしょうが、さすがにそれは手間が大きすぎます。それにリリースしたからといって開発が終わるわけでもなく、メンテのためにまた1からLogを出力するように直すのはあまりにも馬鹿らしいです。

Logを使わず開発するのはそもそも無理です。

Log.isLoggableによるチェック

Log.isLoggableによるチェックは、端末に設定されているログ出力レベルを判定しています。デフォルトでは全てのタグについてINFOが設定されています。

つまり最初のコードのようなLog.DEBUGでチェックをかけるとfalseが返ってくるのでログが出力されません。

ログ出力レベルの変更

ではどうやってログが出力されるようにすればいいのかというと、ターミナルでadb shell setpropコマンドを使います。

adb shell stop
adb shell setprop log.tag.設定したいタグ名 ログレベル
adb shell start

最初の例のログを出力させようと思ったらadb shell setprop log.tag.DigitalWatchFaceService DEBUGとターミナルから打ち込んでやればOKです。(ちなみにadb shellで端末にログインしてからであれば、いきなりsetpropから初めてOKです)

ログ出力レベルの確認

タグごとのログ出力レベルを確認するには、adb shell getprop log.tag.タグ名を使います。何も設定していない状態であれば空白が返って来ます。setpropで設定してやると、現在設定されているログ出力レベルが返って来ます。

ログレベルの優先度

VERBOSE > DEBUG > INFO > WARN > ERROR > ASSERTとなっています。デフォルトではINFOになっているので、isLoggable()はINFO,WARN,ERROR,ASSERTでtrueを返します。

setpropでVERBOSEを設定するとあらゆるレベルでtrueが返るようになります。setprop SUPPRESSとすると逆にあらゆるレベルでfalseが返るようになります。

再起動したら元に戻る

ちなみに設定する端末が開発専用であれば問題ないでしょうが、日常的に使っている端末の場合はログ出力レベルをINFOに戻すのを忘れないようにしましょう。(パフォーマンスに影響するため)

別に忘れても再起動すれば元に戻る(設定が消える)ので気にしなくてもいいかもしれません。

ちなみに「再起動の度に設定するのは面倒くさい」という場合には、/data/local.propで設定することもできるようですが、どうやって設定するのかは分かりません。多分root権限ないとできないんじゃないかと思います。(やってみたけどPermission deniedって言われました)

リリース予定がないならいきなりLog.d()でも構わないのでしょうが、リリースを視野に入れているアプリならこういった方法でログを出力するように設定しておくとユーザに優しいと思います。

Amazonのほしいものリストを公開しています。仕事で欲しいもの、単なる趣味としてほしいもの、リフレッシュのために欲しいものなどを登録しています。 寄贈いただけると泣いて喜びます。大したお礼はできませんが、よりよい情報発信へのモチベーションに繋がりますので、ご検討いただければ幸いです。