Jetpack の App Startup の使用と欠陥、および Android-Startup の改良版

2020 年 10 月 28 日、JetPack | App Startup 1.0.0 が ついに正式リリースを迎えました。

アプリケーション起動ライブラリは、アプリケーションの起動時にコンポーネントを初期化する簡単かつ効率的な方法を提供します。ライブラリ開発者とアプリケーション開発者の両方が、アプリケーションの起動を使用して起動シーケンスを簡素化し、初期化順序を明示的に設定できます。

初期化が必要なコンポーネントごとに個別のコンテンツ プロバイダーを定義する代わりに、App Startup を使用すると、単一のコンテンツ プロバイダーを共有するコンポーネント初期化子を定義できます。これにより、アプリケーションの起動時間を大幅に短縮できます。

目次


予備知識

この記事の内容には次の前提条件/関連知識が含まれますので、ご用意しましたので、お楽しみください~


1. アプリのスタートアップを使用する理由?

このセクションでは、App Startup が使用される理由、つまり App Startup が解決する問題について説明します。

ContentProvider 起動メカニズムに基づいて Context を取得する非侵襲的な方法: 「Android | ContentProvider を使用して侵入せずに Context を取得する」ここで簡単に要約します。

  • 1. セカンドパーティのライブラリやサードパーティのライブラリでは、初期化のためにコンテキストを取得する必要があることがよくあります。
  • 2. ContentProvider はアプリケーションの起動時に初期化されるため、 LeakCanary 2.4Application#onCreate()などの多くのライブラリは ContentProvider の起動メカニズムを使用して初期化します

AppWatcherInstaller.java

internal sealed class AppWatcherInstaller : ContentProvider() {

    internal class MainProcess : AppWatcherInstaller()

    internal class LeakCanaryProcess : AppWatcherInstaller()

    override fun onCreate(): Boolean {
        val application = context!!.applicationContext as Application
        AppWatcher.manualInstall(application)
        return true
    }

    // 其他方法直接 return 
}
  • 3. このアプローチのリスクは、ContentProvider が多すぎて、起動する ContentProvider が多すぎるとアプリケーションの起動時間が長くなるということです。

  • 4. AppStartup のアプローチは、初期化に使用されるすべての ContentProvider をマージし、ContentProvider の作成を減らし、グローバル管理を提供することです。


2. 使用手順

このセクションでは、App Startup を使用する手順をまとめてみましょう。依存関係は次のとおりです。

build.gradle

implementation "androidx.startup:startup-runtime:1.0.0"

2.1 コンポーネントのInitializerインターフェイスを実装する

Initializerこのインターフェイスは、Startup によってカプセル化されたコンポーネント インターフェイスであり、コンポーネントの初期化ロジックと初期化シーケンス (つまり、依存関係) を指定するために使用されます。

Initializer.java

public interface Initializer<T> {

    1、初始化操作,返回的初始化结果将被缓存
    @NonNull
    T create(@NonNull Context context);

    2、依赖关系,返回值是一个依赖组件的列表
    @NonNull
    List<Class<? extends Initializer<?>>> dependencies();
}
  • 1.create(...)初期化操作:返された初期化結果はキャッシュされ、contextパラメーターは Application です。
  • 2.dependencies()依存関係:戻り値は依存コンポーネントのリストですが、他のコンポーネントに依存する必要がない場合は空のリストを返します。アプリの起動によって現在のコンポーネントが初期化されると、依存コンポーネントが確実に初期化されます。

2.2 自動初期化

前述したように、App Startup は初期化に使用されるすべての ContentProvider をマージします。マージされた ContentProvider は、たとえば次のように宣言するInitializationProvider必要があるものです。AndroidManifest

<provider
    android:name="androidx.startup.InitializationProvider"
    android:authorities="${applicationId}.androidx-startup"
    android:exported="false"
    tools:node="merge">
    <meta-data
        android:name="com.example.ExampleLoggerInitializer"
        android:value="androidx.startup" />
</provider>

主なポイントは次のとおりです。

  • 1. コンポーネント名はandroidx.startup.InitializationProvider;である必要があります。
  • android:exported="false"2.他のアプリケーションによるこのコンポーネントへのアクセスを制限するには、ステートメントが必要です。
  • android:authorities3.携帯電話全体で一意である必要があり、通常 ${applicationId} をプレフィックスとして使用します。
  • 4.競合するノードが正しく解決されることtools:node="merge"を保証するために宣言する必要があります。manifest merger tool
  • 5. メタデータは、nameコンポーネントの Initializer 実装クラスの完全修飾名valueですandroidx.startup

ヒント:ではなくandroidx.startupに設定する理由は何ですか? キーと値のペアは一意ですが重複は許可されるためです。valuenamenamevalue

AndroidManifestでコンポーネントを宣言した後、App Startup が自動的に初期化を実行する方法については、セクション 3 で述べました

2.3 手動初期化

コンポーネントを遅延ロードする必要がある場合 (時間のかかるタスク)、手動の初期化を実行できます。手動初期化が必要なイニシャライザは、で宣言する必要はなくAndroidManifest、他のコンポーネントに依存する必要もありません。手動初期化は、以下を呼び出すことで実行できます。

AppInitializer.getInstance(context)
.initializeComponent(ExampleLoggerInitializer::class.java)

initializeComponent()初期化結果はアプリの起動にキャッシュされ、呼び出しを繰り返しても初期化が繰り返されることはないことに注意してください。App Startupの手動初期化部分のソースコード解析については、セクション3で述べました

2.4 自動初期化のキャンセル

一部のライブラリがセクション 2.2の方法を使用して自動初期化されるように構成されており、遅延読み込みを実行したい場合は、manifest merger toolマージ ルールを使用して、このライブラリに対応するイニシャライザを削除する必要があります。詳細は次のとおりです。

<provider
    android:name="andro

おすすめ

転載: blog.csdn.net/MYBOYER/article/details/124035680