Cómo encadenar trabajos

Introducción

WorkManager te permite crear y poner en cola una cadena de trabajo que especifica varias tareas dependientes. Además, define el orden en el que deberían ejecutarse. Esta función resulta particularmente útil cuando necesitas ejecutar varias tareas en un orden específico.

A fin de crear una cadena de trabajo, puedes usar WorkManager.beginWith(OneTimeWorkRequest) o WorkManager.beginWith(List<OneTimeWorkRequest>), que mostrará una instancia de WorkContinuation.

Luego, puedes usar WorkContinuation para agregar OneTimeWorkRequest dependientes mediante WorkContinuation.then(OneTimeWorkRequest) o WorkContinuation.then(List<OneTimeWorkRequest>).

Todas las invocaciones de WorkContinuation.then(...) muestran una instancia nueva de WorkContinuation. Si agregas una List de OneTimeWorkRequest, estas solicitudes pueden ejecutarse en paralelo.

Por último, puedes usar el método WorkContinuation.enqueue() para poner en cola tus cadenas de WorkContinuation.

Echemos un vistazo a un ejemplo en el que una aplicación ejecuta filtros en 3 imágenes (potencialmente en paralelo) y, luego, las comprime y las sube.

Kotlin

    WorkManager.getInstance(myContext)
        // Candidates to run in parallel
        .beginWith(listOf(filter1, filter2, filter3))
        // Dependent work (only runs after all previous work in chain)
        .then(compress)
        .then(upload)
        // Don't forget to enqueue()
        .enqueue()

    

Java

    WorkManager.getInstance(myContext)
        // Candidates to run in parallel
        .beginWith(Arrays.asList(filter1, filter2, filter3))
        // Dependent work (only runs after all previous work in chain)
        .then(compress)
        .then(upload)
        // Don't forget to enqueue()
        .enqueue();

    

Combinadores de entradas

Cuando usas cadenas de OneTimeWorkRequest, el resultado de las OneTimeWorkRequest principales se pasa como entradas a sus elementos secundarios. Por lo tanto, en el ejemplo anterior, los resultados de filter1, filter2 y filter3 se pasarían como entradas a la solicitud de compress.

A fin de administrar las entradas de varias OneTimeWorkRequest principales, WorkManager usa InputMerger.

WorkManager proporciona dos tipos diferentes de InputMerger:

  • OverwritingInputMerger intenta agregar todas las claves de todas las entradas en el resultado. En caso de conflictos, sobrescribe las claves definidas anteriormente.

  • ArrayCreatingInputMerger intenta combinar las entradas y crea arreglos cada vez que sea necesario.

En el ejemplo anterior, dado que deseamos preservar los resultados de todos los filtros de imágenes, deberíamos usar un ArrayCreatingInputMerger.

Kotlin

    val compress: OneTimeWorkRequest = OneTimeWorkRequestBuilder<CompressWorker>()
        .setInputMerger(ArrayCreatingInputMerger::class)
        .setConstraints(constraints)
        .build()

    

Java

    OneTimeWorkRequest compress =
        new OneTimeWorkRequest.Builder(CompressWorker.class)
            .setInputMerger(ArrayCreatingInputMerger.class)
            .setConstraints(constraints)
            .build();

    

Estados de trabajo y encadenado

Existen algunos aspectos que debes tener en cuenta cuando creas cadenas de OneTimeWorkRequest.

  • Las OneTimeWorkRequest dependientes solo están desbloqueadas (transición a ENQUEUED), cuando todas sus OneTimeWorkRequest principales se ejecutaron correctamente (es decir, mostraron Result.success()).

  • Cuando una OneTimeWorkRequest principal presenta errores (muestra Result.failure()), todas las OneTimeWorkRequest dependientes también se marcan como FAILED.

  • Cuando se cancela una OneTimeWorkRequest superior, todas las OneTimeWorkRequest dependientes también se marcan como CANCELLED.

Para obtener más información, consulta Cómo cancelar y detener el trabajo.