WorkRequest の定義

スタートガイドでは、シンプルな WorkRequest を作成してキューに登録する方法を説明しました。

このガイドでは、WorkRequest をカスタマイズして、以下のような一般的なユースケースに対処する方法について説明します。

  • ネットワークの可用性などのタスクの制約に対処する
  • タスクの実行の遅延が最小限になるよう保証する
  • タスクの再試行とバックオフを処理する
  • タスクの入力と出力を処理する
  • タグ付けによってタスクをグループ化する

処理の制約

Constraints を処理に追加することによって実行可能なタイミングを指定できます。

たとえば、デバイスがアイドル状態かつ充電状態のときにのみ処理を実行するように指定できます。

次のコードは、制約を OneTimeWorkRequest に追加する方法を示しています。サポートされている制約の完全なリストについては、Constraints.Builder のリファレンス ドキュメントをご覧ください。

Kotlin


    // Create a Constraints object that defines when the task should run
    val constraints = Constraints.Builder()
            .setRequiresDeviceIdle(true)
            .setRequiresCharging(true)
            .build()

    // ...then create a OneTimeWorkRequest that uses those constraints
    val compressionWork = OneTimeWorkRequestBuilder<CompressWorker>()
            .setConstraints(constraints)
            .build()

    

Java

    // Create a Constraints object that defines when the task should run
    Constraints constraints = new Constraints.Builder()
        .setRequiresDeviceIdle(true)
        .setRequiresCharging(true)
         .build();

    // ...then create a OneTimeWorkRequest that uses those constraints
    OneTimeWorkRequest compressionWork =
                    new OneTimeWorkRequest.Builder(CompressWorker.class)
         .setConstraints(constraints)
         .build();
    

複数の制約が指定されている場合、それらがすべて満たされている場合にのみタスクが実行されます。

タスクの実行中に制約が満たされなくなると、WorkManager がワーカーを停止します。その後、制約が満たされるとタスクが再試行されます。

初期遅延

処理に制約がない場合、または処理がキューに登録されたときにすべての制約が満たされている場合、システムはすぐにタスクを実行できます。タスクをすぐに実行しない場合、最小限の初期遅延の後に処理を開始するよう指定できます。

次の例は、タスクがキューに登録されてから 10 分以上経過してからタスクを実行するように設定する方法を示しています。

Kotlin


    val uploadWorkRequest = OneTimeWorkRequestBuilder<UploadWorker>()
            .setInitialDelay(10, TimeUnit.MINUTES)
            .build()

    

Java


    OneTimeWorkRequest uploadWorkRequest = new OneTimeWorkRequest.Builder(UploadWorker.class)
            .setInitialDelay(10, TimeUnit.MINUTES)
            .build();

    

再試行とバックオフに関するポリシー

WorkManager でタスクを再試行する必要がある場合、ワーカーから Result.retry() を返すことができます。

処理のスケジュールを再設定するには、デフォルトのバックオフ遅延とバックオフ ポリシーを使用します。バックオフ遅延では、処理を再試行するまでに待機する最小時間を指定します。バックオフ ポリシーでは、以降の再試行のバックオフ遅延が経時的にどの程度増加するかを定義します(デフォルト値は EXPONENTIAL です)。

以下に、バックオフ遅延とバックオフ ポリシーのカスタマイズ例を示します。

Kotlin


    val uploadWorkRequest = OneTimeWorkRequestBuilder<UploadWorker>()
            .setBackoffCriteria(
                    BackoffPolicy.LINEAR,
                    OneTimeWorkRequest.MIN_BACKOFF_MILLIS,
                    TimeUnit.MILLISECONDS)
            .build()

    

Java


    OneTimeWorkRequest uploadWorkRequest =
        new OneTimeWorkRequest.Builder(UploadWorker.class)
            .setBackoffCriteria(
                    BackoffPolicy.LINEAR,
                    OneTimeWorkRequest.MIN_BACKOFF_MILLIS,
                    TimeUnit.MILLISECONDS)
            .build();
    

タスクの入出力の定義

タスクでは、入力パラメータとしてデータを渡すか、結果としてデータを返す必要があります。たとえば、画像のアップロードを処理するタスクでは、入力としてアップロードする画像の URI が必要になります。また、出力としてアップロードした画像の URL が必要になることもあります。

入力と出力の値は Key-Value ペアとして Data オブジェクトに格納されます。次のコードは、WorkRequest に入力データを設定する方法を示しています。

Kotlin


    // workDataOf (part of KTX) converts a list of pairs to a [Data] object.
    val imageData = workDataOf(Constants.KEY_IMAGE_URI to imageUriString)

    val uploadWorkRequest = OneTimeWorkRequestBuilder<UploadWorker>()
            .setInputData(imageData)
            .build()

    

Java


    Data imageData = new Data.Builder
                    .putString(Constants.KEY_IMAGE_URI, imageUriString)
                    .build();

    OneTimeWorkRequest uploadWorkRequest = new OneTimeWorkRequest.Builder(UploadWorker.class)
            .setInputData(imageData)
            .build()
    

Worker クラスは、Worker.getInputData() を呼び出すことによって入力引数にアクセスできます。

同様に、Data クラスを使用して戻り値を出力できます。Data オブジェクトを返すには、次に示すように、Result.success() または Result.failure()Result にオブジェクトを含めます。

Kotlin

    class UploadWorker(appContext: Context, workerParams: WorkerParameters)
        : Worker(appContext, workerParams) {

        override fun doWork(): Result {

                // Get the input
                val imageUriInput = getInputData().getString(Constants.KEY_IMAGE_URI)
                // TODO: validate inputs.
                // Do the work
                val response = uploadFile(imageUriInput)

                // Create the output of the work
                val outputData = workDataOf(Constants.KEY_IMAGE_URL to response.imageUrl)

                // Return the output
                return Result.success(outputData)

        }
    }

    

Java

    public class UploadWorker extends Worker {

        public UploadWorker(
            @NonNull Context context,
            @NonNull WorkerParameters params) {
            super(context, params);
        }

        @Override
        public Result doWork() {

            // Get the input
            String imageUriInput = getInputData().getString(Constants.KEY_IMAGE_URI)
            // TODO: validate inputs.
            // Do the work
            Response response = uploadFile(imageUriInput)

            // Create the output of the work
            Data outputData = new Data.Builder
                    .putString(Constants.KEY_IMAGE_URL, response.imageUrl)
                    .build();

            // Return the output
            return Result.success(outputData)
        }
    }
    

処理へのタグ付け

タグ文字列を WorkRequest オブジェクトに割り当てることによってタスクを論理的にグループ化できます。グループ化することで、特定のタグが付けられたすべてのタスクを操作できます。

たとえば WorkManager.cancelAllWorkByTag(String) は、特定のタグが付けられているタスクをすべてキャンセルします。また、WorkManager.getWorkInfosByTagLiveData(String) は、指定したタグが付けられているすべてのタスクのステータスが格納された LiveData を返します。

次のコードは、WorkRequest.Builder.addTag(String) を使用して「cleanup」タグをタスクに追加する方法を示しています。

Kotlin

    val cacheCleanupTask =
            OneTimeWorkRequestBuilder<CacheCleanupWorker>()
        .setConstraints(constraints)
        .addTag("cleanup")
        .build()
    

Java

    OneTimeWorkRequest cacheCleanupTask =
            new OneTimeWorkRequest.Builder(CacheCleanupWorker.class)
        .setConstraints(constraints)
        .addTag("cleanup")
        .build();