コンポジションのトレース

多くの場合、トレースはパフォーマンスの問題を初めて調査するときに最適な情報源です。これによって、何が問題であり、どこから調べ始めるべきかについて、仮説を立てることができます。

Android でサポートされているトレースには、システム トレースとメソッド トレースの 2 つのレベルがあります。

システム トレースはトレース用に特別にマークされた領域のみを追跡するため、オーバーヘッドが少なく、アプリのパフォーマンスに大きく影響することはありません。システム トレースは、コードの特定のセクションの実行にかかっている時間を確認するのに便利です。

メソッド トレースは、アプリ内のすべての関数呼び出しを追跡します。これは非常に高コストであるため、アプリのパフォーマンスに大きな影響を与えますが、何が起こっているのか、どのような関数がどれぐらいの頻度で呼び出されているのかを全体的に把握できます。

デフォルトでは、システム トレースには個別のコンポーズ可能な関数は含まれません。メソッド トレースで使用できます。

現在、システム トレース内にコンポーズ可能な関数を表示するための新しいシステム トレース機能をテストしています。この機能により、システム トレースレベルの煩わしさの低さと、メソッド トレースレベルのコンポジションの詳細を実現できます。

コンポジションのトレースをセットアップする

プロジェクトで再コンポジションのトレースを試すには、少なくとも次のバージョンに更新する必要があります。

  • Android Studio Flamingo
  • Compose UI: 1.3.0
  • Compose Compiler: 1.3.0

トレースを実行するデバイスまたはエミュレータも、API レベル 30 以上である必要があります。

さらに、Compose Runtime Tracing に新しい依存関係を追加する必要があります。

implementation("androidx.compose.runtime:runtime-tracing:1.0.0-beta01")

この依存関係により、再コンポジションを含むシステム トレースを取得すると、コンポーズ可能な関数が自動的に表示されます。

システム トレースを行う

システム トレースを行い、新しい再コンポジションのトレースの実際の動作を確認する手順は次のとおりです。

  1. プロファイラを開きます。

    Android Studio - プロファイリングを開始する
    図 2. Android Studio - プロファイリングを開始する
  2. [CPU のタイムライン] をクリックします。

    Android Studio Profiler - CPU のタイムライン
    図 3. Android Studio Profiler - CPU のタイムライン
  3. トレースする UI にアプリを移動し、[System Trace] と [Record] を選択します。

    トレース オプション - システム トレース
    図 4. トレース オプション - システム トレース
  4. アプリを使用すると、再コンポーズが行われ、記録が停止されます。トレースが処理されて表示されると、再コンポジションのトレースでコンポーザブルを確認できるようになります。キーボードとマウスを使用して、トレースでズームおよびパンできます。トレースの操作に慣れていない場合は、トレースを記録するのドキュメントをご覧ください。

    システム トレース
    図 5. システム トレース

    グラフ内のコンポーザブルをダブルクリックすると、そのソースコードに移動します。

  5. [Flame Chart] では、ファイルと行番号とともにコンポーザブルを確認することもできます。

    フレーム チャート
    図 6. フレーム チャート

注意点

APK サイズのオーバーヘッド

この機能のオーバーヘッドはできる限り最小限に抑えることを目指していましたが、Compose コンパイラによって APK に埋め込まれたトレース文字列により、Compose アプリの APK サイズが増加します。このようなサイズの増加は、アプリで Compose をあまり使用しない場合は小さく、完全な Compose アプリの場合は大きくなることがあります。また、これらのトレース文字列は、上記のようにトレースツールで確認できるように難読化されていません。バージョン 1.3.0 以降では、Compose コンパイラがこれらをすべてのアプリに挿入します。

製品版ビルドでトレース文字列を削除するには、次の ProGuard ルールを追加します。

-assumenosideeffects public class androidx.compose.runtime.ComposerKt {

   boolean isTraceInProgress();

   void traceEventStart(int,int,int,java.lang.String);

   void traceEventStart(int,java.lang.String);

   void traceEventEnd();

}

これらの関数は将来変更される可能性がありますが、変更については、Compose のリリースノートに記載されます。

APK サイズのコストは発生しますが、これらを維持することにより、プロファイリングされる APK が、アプリユーザーによって実行される APK と同じであることが保証されます。

正確なタイミング

パフォーマンス テストのように正確なプロファイリングを行うには、プロファイル可能なアプリに従ってアプリを profileablenon-debuggable にする必要があります。

ターミナルからトレースをキャプチャする

ターミナルからコンポジション トレースをキャプチャできます。そのためには、通常は Android Studio によって自動的に行われる手順を実行する必要があります。

依存関係を追加する

まず、アプリに依存関係を追加します。

implementation("androidx.tracing:tracing-perfetto:1.0.0")
implementation("androidx.tracing:tracing-perfetto-binary:1.0.0")

レコード コマンドを生成する

  1. Perfetto を使用してレコード コマンドを生成します。
  2. 次の例のように、track_event データソースのセクションを手動で追加します。

    adb shell perfetto \
      -c - --txt \
      -o /data/misc/perfetto-traces/trace \
    <<EOF
    buffers: {
        size_kb: 63488
        fill_policy: RING_BUFFER
    }
    buffers: {
        size_kb: 2048
        fill_policy: RING_BUFFER
    }
    data_sources: {
        config {
            name: "track_event"
        }
    }
    duration_ms: 10000
    flush_period_ms: 30000
    incremental_state_config {
        clear_period_ms: 5000
    }
    EOF

トレースをキャプチャする

  1. アプリを起動し、トレースするセクションを準備します。
  2. ブロードキャストを発行してアプリでトレースを有効にします。

    # set app package variable, e.g. com.google.samples.apps.nowinandroid.debug
    # can be found through `adb shell ps -ef` or `adb shell cmd package list packages`
    package=<your app process>
    
    # issue a broadcast to enable tracing
    adb shell am broadcast \
    -a androidx.tracing.perfetto.action.ENABLE_TRACING \
    $package/androidx.tracing.perfetto.TracingReceiver
    
  3. 先ほど作成した録画コマンドを開始します。

トレースを開く

  1. adb pull <location>: デバイスのトレース(レコード コマンドで指定された場所)。

  2. Perfetto で開きます。

Jetpack Macrobenchmark を使用してトレースをキャプチャする

パフォーマンスを測定するには、Jetpack Macrobenchmark を使用します。結果としてトレースを提供します。Macrobenchmark でコンポジションのトレースを有効にするには、次の操作を行う必要があります。

  1. 次の依存関係を Macrobenchmark テスト モジュールに追加します。

    implementation("androidx.tracing:tracing-perfetto:1.0.0")
    implementation("androidx.tracing:tracing-perfetto-binary:1.0.0")
    
  2. ベンチマークを実行する前に、androidx.benchmark.fullTracing.enable=true 計測引数を追加します。Macrobenchmark インストルメンテーション引数の詳細については、Macrobenchmark インストルメンテーション引数をご覧ください。

フィードバック

この機能についてのフィードバック、バグ、ご要望がございましたら、ぜひお寄せください。フィードバックは、Issue Tracker から送信できます。