機能ロールアウトのパフォーマンス モニタリング

機能ロールアウトのパフォーマンス モニタリング

この Codelab について

subject最終更新: 10月 31, 2022
account_circle作成者: Raymond Lam, Yalun Qin

1. 概要

この Codelab では、機能のロールアウト中にアプリのパフォーマンスをモニタリングする方法を学びます。このサンプルアプリには基本的な機能があり、Firebase Remote Config フラグに基づいて異なる背景画像が表示されるように設定されています。トレースの計測を使用してアプリのパフォーマンスをモニタリングし、アプリに構成変更をロールアウトして、その影響をモニタリングし、パフォーマンスを改善する方法を学びます。

学習内容

  • Firebase Performance Monitoring をモバイルアプリに追加して、すぐに使用できる指標(アプリの起動時間、フレームの遅延やフリーズなど)を取得する方法
  • カスタム トレースを追加してユーザー ジャーニーのクリティカル コードパスを把握する方法
  • Performance Monitoring ダッシュボードを使用して指標を把握し、機能のロールアウトなどの重要な変更をトラッキングする方法
  • 主要指標をモニタリングするためのパフォーマンス アラートを設定する方法
  • Firebase Remote Config の変更をロールアウトする方法

前提条件

  • Android Studio 4.0 以降
  • API レベル 16 以降を搭載した Android Emulator。
  • Java バージョン 8 以降
  • Firebase Remote Config の基本的な理解

2. サンプル プロジェクトを設定する

コードをダウンロードする

次のコマンドを実行して、この Codelab のサンプルコードのクローンを作成します。これにより、マシンに codelab-perf-rc-android というフォルダが作成されます。

$ git clone https://github.com/FirebaseExtended/codelab-feature-rollout-performance.git

マシンに Git がない場合は、GitHub からコードを直接ダウンロードすることもできます。

firebase-perf-rc-android-start フォルダのプロジェクトを Android Studio にインポートします。ランタイム例外が表示されたり、google-services.json ファイルがないことを示す警告が表示されたりする可能性があります。次のセクションで修正します。

この Codelab では、Firebase Assistant プラグインを使用して、Android アプリを Firebase プロジェクトに登録し、Android プロジェクトに必要な Firebase 構成ファイル、プラグイン、依存関係を追加します。これらはすべて Android Studio から行えます

アプリを Firebase に接続する

  1. [Android Studio]/[Help] > [Check for updates] に移動して、Android Studio と Firebase Assistant の最新版を使用していることを確認します。
  2. [Tools] > [Firebase] を選択して、[Assistant] ペインを開きます。

c0e42ef063d21eab.png

  1. [Performance Monitoring] を選択してアプリに追加し、[Performance Monitoring を使ってみる] をクリックします。
  2. [Connect to Firebase] をクリックして Android プロジェクトを Firebase に接続します。(ブラウザで Firebase コンソールが開きます)
  3. Firebase コンソールで [プロジェクトを追加] をクリックし、Firebase プロジェクト名を入力します。(Firebase プロジェクトがすでにある場合は、その既存のプロジェクトを選択することもできます)。[続行] をクリックして利用規約に同意し、Firebase プロジェクトと新しい Firebase アプリを作成します。

次に、新しい Firebase アプリを Android Studio プロジェクトに接続するためのダイアログが表示されます。

51a549ebde2fe57a.png

  1. [接続] をクリックします。
  2. Android Studio を開きます。[アシスタント] ペインに、アプリが Firebase に接続されていることを示す確認メッセージが表示されます。

40c24c4a56a45990.png

Performance Monitoring をアプリに追加する

Android Studio の [Assistant] ペインで、[Add Performance Monitoring to your app] をクリックします。

[変更を承認] ダイアログが表示されます。[変更を承認] をクリックすると、Android Studio がアプリを同期し、必要な依存関係がすべて追加されます。

3046f3e1f5fea06f.png

最後に、Android Studio の [アシスタント] ペインに、すべての依存関係が正しく設定されたことを示す成功メッセージが表示されます。

62e79fd18780e320.png

追加の手順として、デバッグ ロギングを有効にするには、「(省略可)デバッグ ロギングを有効にする」の手順に沿って操作します。同じ手順は公開ドキュメントでも確認できます。

3. アプリを実行する

これで、アプリのモジュール(アプリレベル)ディレクトリに google-services.json ファイルが表示され、アプリがコンパイルされるようになります。Android Studio で、[Run] > [Run 'アプリ'] をクリックして、Android エミュレータでアプリをビルドして実行します。

アプリの実行時に、次のようなスプラッシュ画面が表示されます。

ffbd413a6983b205.png

数秒後、デフォルトの画像を含むメインページが表示されます。

d946cab0df319e50.png

バックグラウンドで行われていること

スプラッシュ画面は SplashScreenActivity で実装され、次の処理を行います。

  1. onCreate() では、Firebase Remote Config の設定を初期化し、この Codelab の後半で Remote Config ダッシュボードで設定する設定値を取得します。
  2. executeTasksBasedOnRC() で、seasonal_image_url フラグの構成値を読み取ります。構成値で URL が指定されている場合は、イメージが同期的にダウンロードされます。
  3. ダウンロードが完了すると、アプリは MainActivity に移動し、finish() を呼び出して SplashScreenActivity を終了します。

MainActivity で、seasonal_image_url が Remote Config で定義されている場合、この機能が有効になり、ダウンロードされた画像がメインページの背景として表示されます。指定しなかった場合は、デフォルトの画像(上記)が表示されます。

4. Remote Config を設定する

アプリが実行されたら、新しい機能フラグを設定できます。

  1. Firebase コンソールの左側のパネルで [エンゲージメント] セクションを見つけ、[Remote Config] をクリックします。
  2. [構成を作成] ボタンをクリックして構成フォームを開き、パラメータキーとして seasonal_image_url を追加します。
  3. [説明を追加] をクリックし、次のように説明を入力します。Shows a seasonal image (replaces default) in the main page when the restaurant list is empty.
  4. [新規追加] -> [条件値] -> [新しい条件を作成] をクリックします。
  5. 条件名に「Seasonal image rollout」と入力します。
  6. [Applies if...] セクションで、[User in random percentile <= 0%] を選択します。(後でロールアウトする準備ができるまで、この機能は無効のままにしておきます)。
  7. [条件を作成] をクリックします。この条件は、後で新機能をユーザーにロールアウトする際に使用します。

7a07526eb9e81623.png

  1. [最初のパラメータの作成フォーム] を開き、[Value for Seasonal image rollout] フィールドを見つけます。季節の画像をダウンロードする URL を入力します。https://images.unsplash.com/photo-1552691021-7043334e0b51
  2. デフォルト値は空の文字列のままにします。つまり、URL からダウンロードされた画像ではなく、コードベースのデフォルト画像が表示されます。
  3. [保存] をクリックします。

99e6cd2ebcdced.png

新しい構成がドラフトとして作成されていることがわかります。

  1. [変更を公開] をクリックし、上部で変更を確認してアプリを更新します。

39cd3e96d370c7ce.png

5. データの読み込み時間のモニタリングを追加する

アプリは MainActivity を表示する前に一部のデータをプリロードし、スプラッシュ画面を表示してこのプロセスを非表示にします。ユーザーがこの画面で長時間待たされるのは好ましくありません。通常は、スプラッシュ画面が表示されている時間をモニタリングすることをおすすめします。

Firebase Performance Monitoring には、まさにそのための方法が用意されています。カスタムコード トレースを計測可能にすると、アプリ内の特定のコードのパフォーマンス(データの読み込み時間や新機能の処理時間など)をモニタリングできます。

スプラッシュ画面が表示されている時間をトラッキングするには、SplashScreenActivity にカスタムコード トレースを追加します。SplashScreenActivity は、スプラッシュ画面を実装する Activity です。

  1. splash_screen_trace という名前のカスタムコード トレースを初期化して作成し、開始します。

SplashScreenActivity.java

// ...
import com.google.firebase.perf.FirebasePerformance;
import com.google.firebase.perf.metrics.Trace;
// ...

public class SplashScreenActivity extends AppCompatActivity {

   
private static final String TAG = "SplashScreenActivity";
   
private static final String SEASONAL_IMAGE_URL_RC_FLAG = "seasonal_image_url";

   
// TODO: Initialize splash_screen_trace
   
private final Trace splashScreenTrace = FirebasePerformance.startTrace("splash_screen_trace");
   
   
// ...
}
  1. SplashScreenActivityonDestroy() メソッドでトレースを終了します。

SplashScreenActivity.java

@Override
protected void onDestroy() {
    super.onDestroy();

    // TODO: Stop the splash_screen_trace here
    splashScreenTrace.stop();
}

新しい機能は画像をダウンロードして処理するため、2 つ目のカスタム コード トレースを追加して、この機能が SplashScreenActivity に追加した時間を追跡します。

  1. splash_seasonal_image_processing という名前のカスタムコード トレースを初期化して作成し、開始します。

SplashScreenActivity.java

private void executeTasksBasedOnRC(FirebaseRemoteConfig rcConfig) {
    String seasonalImageUrl = rcConfig.getString(SEASONAL_IMAGE_URL_RC_FLAG);
    Log.d(TAG, SEASONAL_IMAGE_URL_RC_FLAG + ": " + seasonalImageUrl);

    if (!seasonalImageUrl.isEmpty()) {
        // TODO: Start the splash_seasonal_image_processing here
        final Trace seasonalImageProcessingTrace = FirebasePerformance
            .startTrace("splash_seasonal_image_processing");

        // ...
    }
}
  1. RequestListeneronLoadFailed() メソッドと onResourceReady() メソッドの両方でトレースを終了します。

SplashScreenActivity.java

Glide.with(SplashScreenActivity.this.getApplicationContext())
    .asBitmap()
    .load(seasonalImageUrl)
    .signature(new ObjectKey(Utils.getCacheUUID()))
    .listener(new RequestListener<Bitmap>() {
        @Override
        public boolean onLoadFailed(
            @Nullable GlideException e,
            Object model, Target<Bitmap> target,
            boolean isFirstResource) {

            // TODO: Stop the splash_seasonal_image_processing here
            seasonalImageProcessingTrace.stop();

            launchMainActivity();
            return true;
        }

        @Override
        public boolean onResourceReady(Bitmap resource, Object model,
            Target<Bitmap> target, DataSource dataSource,
            boolean isFirstResource) {

            // TODO: Stop the splash_seasonal_image_processing here
            seasonalImageProcessingTrace.stop();

            launchMainActivity();
            return true;
        }
     })
     .preload();

スプラッシュ画面の所要時間(splash_screen_trace))と新機能の処理時間(splash_seasonal_image_processing)を追跡するカスタム コード トレースを追加したので、Android Studio でもう一度アプリを実行します。Logging trace metric: splash_screen_trace を含むロギング メッセージと、トレース時間が表示されます。新しい機能をまだ有効にしていないため、splash_seasonal_image_processing のログ メッセージは表示されません。

6. トレースにアトリビュートを追加する

カスタムコード トレースでは、Performance Monitoring によってデフォルトの属性(アプリのバージョン、国、デバイスなどの一般的なメタデータ)が自動的にログに記録され、Firebase コンソールでトレースするデータをフィルタできます。カスタム属性を追加してモニタリングすることもできます。

アプリに 2 つのカスタムコード トレースを追加して、スプラッシュ画面の表示時間と新機能の処理時間をモニタリングしました。これらの時間に影響する要因としては、表示される画像がデフォルト画像であるか、URL からダウンロードする必要があるかなどがあります。画像をダウンロードする URL が変更される可能性もあります。

そのため、これらのカスタムコード トレースに、季節限定の画像の URL を表すカスタム属性を追加しましょう。これにより、後でこれらの値で所要時間データをフィルタできます。

  1. executeTasksBasedOnRC メソッドの先頭に、splash_screen_trace のカスタム属性(seasonal_image_url_attribute)を追加します。

SplashScreenActivity.java

private void executeTasksBasedOnRC(FirebaseRemoteConfig rcConfig) {
    String seasonalImageUrl = rcConfig.getString(SEASONAL_IMAGE_URL_RC_FLAG);
    Log.d(TAG, SEASONAL_IMAGE_URL_RC_FLAG + ": " + seasonalImageUrl);

    // TODO: Add a custom attribute "seasonal_image_url_attribute" to splash_screen_trace
    if (seasonalImageUrl.isEmpty()) {
        splashScreenTrace.putAttribute("seasonal_image_url_attribute", "unset");
    } else {
        splashScreenTrace.putAttribute("seasonal_image_url_attribute", seasonalImageUrl);
    }

    // ...
}
  1. startTrace("splash_seasonal_image_processing") 呼び出しの直後に、splash_seasonal_image_processing に同じカスタム属性を追加します。

SplashScreenActivity.java

if (!seasonalImageUrl.isEmpty()) {
    // TODO: Start the splash_seasonal_image_processing here
    final Trace seasonalImageProcessingTrace = FirebasePerformance
        .startTrace("splash_seasonal_image_processing");

    // TODO: Add a custom attribute "seasonal_image_url_attribute" to splash_seasonal_image_processing
    seasonalImageProcessingTrace
        .putAttribute("seasonal_image_url_attribute", seasonalImageUrl);

    // ...
}

カスタム トレース(splash_screen_tracesplash_seasonal_image_processing)の両方にカスタム属性(seasonal_image_url_attribute)を追加したので、Android Studio で再度アプリを実行します。Setting attribute 'seasonal_image_url_attribute' to 'unset' on trace 'splash_screen_trace'. Remote Config パラメータ seasonalImageUrl がまだ有効になっていないため、属性値が unset になっているというログ メッセージが表示されます。

Performance Monitoring SDK は、トレースデータを収集して Firebase に送信します。データは Firebase コンソールのパフォーマンス ダッシュボードで確認できます。このダッシュボードについては、Codelab の次のステップで詳しく説明します。

7. Performance Monitoring ダッシュボードを構成する

機能をモニタリングするようにダッシュボードを構成する

Firebase コンソールで、Friendly Eats アプリがあるプロジェクトを選択します。

左側のパネルで [リリースとモニタリング] セクションを見つけて、[パフォーマンス] をクリックします。

指標ボードに最初のデータポイントが表示され、パフォーマンス ダッシュボードが表示されます。Performance Monitoring SDK は、アプリからパフォーマンス データを収集し、収集後数分以内に表示します。

f57e5450b70034c9.png

この指標ボードでは、アプリの主な指標を追跡できます。デフォルトのビューにはアプリの起動時間トレースの所要時間が表示されますが、最も重要な指標を追加することもできます。追加した新機能をトラッキングしているため、カスタムコード トレース splash_screen_trace の所要時間を表示するようにダッシュボードをカスタマイズできます。

  1. 空の [指標を選択] ボックスのいずれかをクリックします。
  2. ダイアログ ウィンドウで、トレースタイプとして [カスタム トレース] を選択し、トレース名として「splash_screen_trace」を選択します。

1fb81f4dba3220e0.png

  1. [指標を選択] をクリックすると、splash_screen_trace の所要時間がダッシュボードに追加されます。

同じ手順で、重要な他の指標を追加して、時間の経過とともに、またリリースごとにパフォーマンスがどのように変化するかを簡単に確認できます。

1d465c021e58da3b.png

指標ボードは、ユーザーが経験した主要な指標のパフォーマンスを追跡するための強力なツールです。この Codelab では、狭い期間の小さなデータセットを使用しているため、機能のロールアウトのパフォーマンスを把握するのに役立つ他のダッシュボード ビューを使用します。

8. 機能をリリースする

モニタリングを設定したので、Firebase Remote Config の変更(前述の seasonal_image_url))をロールアウトする準備が整いました。

変更をロールアウトするには、Firebase コンソールの Remote Config ページに戻り、ターゲティング条件のユーザー割合を増やします。通常、新機能は少数のユーザーにロールアウトし、問題がないことを確認してから範囲を拡大します。この Codelab では、アプリのユーザーはあなただけなので、パーセンタイル値を 100% に変更できます。

  1. ページ上部の [条件] タブをクリックします。
  2. 先ほど追加した Seasonal image rollout 条件をクリックします。
  3. パーセンタイル値を 100% に変更します。
  4. [Save Condition] をクリックします。
  5. [変更を公開] をクリックして変更を確定します。

70f993502b27e7a0.png

Android Studio に戻り、エミュレータでアプリを再起動して、新しい機能を確認します。スプラッシュ画面の後に、新しい空の状態のメイン画面が表示されます。

b0cc91b6e48fb842.png

9. パフォーマンスの変化を確認する

次に、Firebase コンソールのパフォーマンス ダッシュボードを使用して、スプラッシュ画面の読み込みのパフォーマンスを確認しましょう。この Codelab のステップでは、ダッシュボードのさまざまな部分を使用してパフォーマンス データを表示します。

  1. メインの [ダッシュボード] タブで、トレース テーブルまで下にスクロールし、[カスタム トレース] タブをクリックします。この表には、先ほど追加したカスタムコード トレースに加えて、標準のトレースも表示されます。
  2. 新機能を有効にしたので、画像のダウンロードと処理に要した時間を測定したカスタムコード トレース splash_seasonal_image_processing を探します。トレース内の [Duration] 値から、このダウンロードと処理にかなりの時間がかかることがわかります。

439adc3ec71805b7.png

  1. splash_seasonal_image_processing のデータが取得されているため、このトレースの所要時間を [ダッシュボード] タブの上部にある指標ボードに追加できます。

前回と同様に、空の [指標を選択] ボックスのいずれかをクリックします。ダイアログ ウィンドウで、トレースタイプ [カスタム トレース] とトレース名 [splash_seasonal_image_processing] を選択します。最後に、[指標を選択] をクリックして、この指標を指標ボードに追加します。

7fb64d2340410576.png

  1. 違いをさらに確認するには、splash_screen_trace のデータを確認します。指標ボードで splash_screen_trace カードをクリックし、[指標の詳細を表示] をクリックします。

b1c275c30679062a.png

  1. 詳細ページの左下に、前に作成したカスタム属性を含む属性のリストが表示されます。カスタム属性 seasonal_image_url_attribute をクリックすると、右側に各季節限定画像の URL のスプラッシュ画面の長さが表示されます。

8fa1a69019bb045e.png

  1. スプラッシュ画面の表示時間の値は、上記のスクリーンショットとは多少異なる可能性がありますが、URL から画像をダウンロードする場合は、デフォルトの画像(「unset」で表されます)を使用する場合よりも長い時間にする必要があります。

この Codelab では、この長時間の理由は単純ですが、実際のアプリではそうはならないでしょう。収集される時間データは、さまざまなデバイスから取得され、さまざまなネットワーク接続条件でアプリが実行されます。これらの条件は、想定よりも悪くなる可能性があります。これが実際の状況であれば、この問題をどのように調査するかを見てみましょう。

  1. ページ上部の [パフォーマンス] をクリックして、[ダッシュボード] メインタブ 640b696b79d90103.png に戻ります。
  2. ページ下部にあるトレース テーブルで、[ネットワーク リクエスト] タブをクリックします。この表には、images.unsplash.com/** URL パターンを含む、アプリからのすべてのネットワーク リクエストが URL パターンに集約されて表示されます。このレスポンス時間の値を、画像のダウンロードと処理にかかる合計時間(splash_seasonal_image_processing トレースの時間)と比較すると、画像のダウンロードに多くの時間が費やされていることがわかります。

6f92ce0f23494507.png

パフォーマンスに関する検出結果

Firebase Performance Monitoring を使用して、新しい機能を有効にしたエンドユーザーに次のような影響があることを確認しました。

  1. SplashScreenActivity での滞在時間が長くなりました。
  2. splash_seasonal_image_processing の時間が非常に長い。
  3. この遅延は、画像のダウンロードの応答時間と、画像に必要な対応する処理時間によるものです。

次のステップでは、機能をロールバックしてパフォーマンスへの影響を軽減し、機能の実装を改善する方法を特定します。

10. 機能をロールバックする

スプラッシュ画面でユーザーの待ち時間を長くすることは望ましくありません。Remote Config の主な利点の 1 つは、ユーザーに別のバージョンをリリースしなくても、ロールアウトを一時停止したり元に戻したりできることです。これにより、問題(前回のステップで検出したパフォーマンスの問題など)に迅速に対応し、不満を抱くユーザーの数を最小限に抑えることができます。

迅速な緩和策として、ロールアウトのパーセンタイル値を 0 にリセットして、すべてのユーザーにデフォルトの画像を再度表示します。

  1. Firebase コンソールの Remote Config ページに戻ります。
  2. ページ上部の [条件] をクリックします。
  3. 先ほど追加した Seasonal image rollout 条件をクリックします。
  4. パーセンタイル値を 0% に変更します。
  5. [Save Condition] をクリックします。
  6. [変更を公開] をクリックして変更を確定します。

18c4f1cbac955a04.png

Android Studio でアプリを再起動すると、元の空の状態のメイン画面が表示されます。

d946cab0df319e50.png

11. パフォーマンスの問題を解決する

前の Codelab で、スプラッシュ画面の画像のダウンロードがアプリの遅延の原因になっていることを確認しました。ダウンロードした画像を詳しく見ると、画像の元の解像度が 2 MB を超えていることがわかります。パフォーマンスの問題を簡単に解決するには、画質を適切な解像度に下げて、画像のダウンロード時間を短縮します。

Remote Config 値を再度ロールアウトする

  1. Firebase コンソールの Remote Config ページに戻ります。
  2. seasonal_image_url パラメータの [編集] アイコンをクリックします。
  3. [Value for Seasonal image rollout] を https://images.unsplash.com/photo-1552691021-7043334e0b51?w=640 に更新し、[Save] をクリックします。

828dd1951a2ec4a4.png

  1. ページ上部の [条件] タブをクリックします。
  2. [季節限定画像のロールアウト] をクリックし、パーセンタイル値を 100% に戻します。
  3. [Save Condition] をクリックします。

1974fa3bb789f36c.png

  1. [変更を公開] ボタンをクリックします。

12. 修正をテストしてアラートを設定する

アプリをローカルで実行する

別のダウンロード イメージ URL を使用するように新しい構成値を設定して、アプリを再度実行します。スプラッシュ画面が表示される時間が短くなったことがわかります。

b0cc91b6e48fb842.png

変更のパフォーマンスを確認する

Firebase コンソールのパフォーマンス ダッシュボードに戻り、指標を確認します。

  1. 今回は、トレース表を使用して詳細ページに移動します。トレース表の下部にある [カスタム トレース] タブで、カスタム トレース splash_seasonal_image_processing をクリックして、時間の指標の詳細ビューをもう一度表示します。

2d7aaca03112c062.png

  1. カスタム属性 seasonal_image_url_attribute をクリックして、カスタム属性の内訳をもう一度表示します。URL にカーソルを合わせると、縮小サイズの画像の新しい URL と一致する値(https://images.unsplash.com/photo-1552691021-7043334e0b51?w=640(末尾に ?w=640 が付加))が表示されます。この画像に関連付けられた時間の値は、前の画像の値よりもかなり短く、ユーザーにとっても許容できるものです。

10e30c037a4237a2.png

  1. スプラッシュ画面のパフォーマンスを改善したので、トレースがしきい値を超えたときに通知されるようにアラートを設定できます。パフォーマンス ダッシュボードを開き、[splash_screen_trace] のオーバーフロー メニュー(3 つのドット)アイコンをクリックして、[アラート設定] をクリックします。

4bd0a2a1faa14479.png

  1. 切り替えボタンをクリックして [Duration] アラートを有効にします。しきい値を表示された値より少し高く設定して、splash_screen_trace がしきい値を超えるとメールが届くようにします。
  1. [保存] をクリックして、アラートを作成します。トレース テーブルまでスクロールし、[カスタム トレース] タブをクリックして、アラートが有効になっていることを確認します。

2bb93639e2218d1.png

13. お疲れさまでした

これでFirebase Performance Monitoring SDK を有効にしてトレースを収集し、新機能のパフォーマンスを測定しました。新機能のリリースに関する主要なパフォーマンス指標をモニタリングし、パフォーマンスの問題が見つかった場合は迅速に対応しました。これらはすべて、Remote Config で構成を変更し、パフォーマンスの問題をリアルタイムでモニタリングすることで可能になりました。

学習した内容

  • アプリに Firebase Performance Monitoring SDK を追加する
  • 特定の機能を測定するためにコードにカスタムコード トレースを追加する
  • 新しい機能を制御/ロールアウトするための Remote Config パラメータと条件値を設定する
  • パフォーマンス モニタリング ダッシュボードを使用してロールアウト中の問題を特定する方法
  • アプリのパフォーマンスが設定したしきい値を超えたときに通知するパフォーマンス アラートを設定する

詳細