A menudo, las apps necesitan hacer más de una cosa a la vez. Las APIs de Android proporcionan muchas formas diferentes de hacerlo. Elegir la opción correcta es muy importante. Una opción puede ser adecuada para una situación, pero muy incorrecta para otra. Elegir las APIs incorrectas puede afectar el rendimiento o la eficiencia de los recursos de tu app, lo que puede agotar la batería y degradar el rendimiento del dispositivo del usuario en su totalidad. En algunos casos, elegir el enfoque incorrecto podría impedir que tu app aparezca en Play Store.
En este documento, se explican las diferentes opciones disponibles y se te ayuda a elegir la correcta para tu situación.
Terminología
Algunos términos importantes relacionados con las tareas en segundo plano se pueden usar de varias maneras contradictorias. Por este motivo, es importante definir nuestras condiciones.
Si una app se ejecuta en segundo plano, el sistema le aplica una serie de restricciones. (por ejemplo, en la mayoría de los casos, una app en segundo plano no puede iniciar servicios en primer plano).
A los efectos de este documento, usaremos el término "tarea" para indicar una operación que realiza una app fuera de su flujo de trabajo principal. Para garantizar la alineación en la comprensión, lo dividimos en tres categorías principales de tipos de tareas: trabajo asíncrono, las APIs de programación de tareas y los servicios en primer plano.
Elige la opción correcta
En la mayoría de los casos, puedes determinar las APIs correctas para usar en tu tarea si averiguas la categoría (trabajo asíncrono, las APIs de programación de tareas o los servicios en primer plano) a la que pertenece la tarea.
Si aún tienes dudas, puedes usar los diagramas de flujo que proporcionamos, que agregan más matices a la decisión. Cada una de estas opciones se describe con más detalle más adelante en este documento.
Hay dos situaciones principales que se deben tener en cuenta para las tareas en segundo plano:
- La tarea que inicia el usuario mientras la app está visible
- La tarea se inicia en respuesta a un evento, ya sea interno o externo.
Estos dos escenarios tienen sus propios árboles de decisión.
Trabajo asíncrono
En muchos casos, una app solo necesita realizar operaciones simultáneas mientras se ejecuta en primer plano. Por ejemplo, una app podría necesitar realizar un cálculo lento. Si hiciera el cálculo en el subproceso de IU, el usuario no podría interactuar con la app hasta que terminara el cálculo, lo que podría generar un error de ANR. En un caso como este, la app debe usar una opción de trabajo asíncrono.
Entre las opciones de trabajo asíncrono comunes, se incluyen las corrutinas de Kotlin y los subprocesos de Java. Puedes encontrar más información en la documentación sobre trabajo asíncrono. Es importante tener en cuenta que, a diferencia de las APIs de tareas en segundo plano, no se garantiza que el trabajo asíncrono finalice si la app deja de estar en una etapa del ciclo de vida válida (por ejemplo, si la app sale del primer plano).
APIs de programación de tareas
Las APIs de programación de tareas son una opción más flexible cuando necesitas realizar tareas que deben continuar incluso si el usuario abandona la app. En la mayoría de los casos, la mejor opción para ejecutar tareas en segundo plano es usar WorkManager, aunque en algunos casos puede ser apropiado usar la API de JobScheduler
de la plataforma.
WorkManager es una biblioteca potente que te permite configurar trabajos simples o complejos según sea necesario. Puedes usar WorkManager para programar tareas que se ejecuten en momentos específicos o especificar las condiciones en las que se debe ejecutar la tarea. Incluso puedes configurar cadenas de tareas para que cada una se ejecute a su vez y pase sus resultados a la siguiente. Para comprender todas las opciones disponibles, lee la lista de funciones de WorkManager.
Estos son algunos de los casos más comunes para las tareas en segundo plano:
- Cómo recuperar datos del servidor de forma periódica
- Cómo recuperar datos de sensores (por ejemplo, datos del contador de pasos)
- Obtener datos de ubicación periódicos (se te debe otorgar el permiso
ACCESS_BACKGROUND_LOCATION
en Android 10 o versiones posteriores) - Subir contenido según un activador de contenido, como las fotos que crea la cámara
Servicios en primer plano
Los servicios en primer plano ofrecen una forma potente de ejecutar tareas de inmediato que no deben interrumpirse. Sin embargo, los servicios en primer plano pueden generar una carga pesada en el dispositivo y, a veces, tienen implicaciones de privacidad y seguridad. Por estos motivos, el sistema impone muchas restricciones sobre cómo y cuándo las apps pueden usar los servicios en primer plano. Por ejemplo, un servicio en primer plano debe ser perceptible para el usuario y, en la mayoría de los casos, las apps no pueden iniciar servicios en primer plano cuando están en segundo plano. Para obtener más información, consulta la documentación de los servicios en primer plano.
Existen dos métodos para crear un servicio en primer plano. Puedes declarar tu Service
y especificar que el servicio es un servicio en primer plano llamando a Service.startForeground()
. Como alternativa, puedes usar WorkManager para crear un servicio en primer plano, como se explica en la compatibilidad con trabajadores de larga duración.
Sin embargo, es importante saber que un servicio en primer plano creado por WorkManager debe cumplir con las mismas restricciones que cualquier otro servicio en primer plano.
WorkManager solo proporciona algunas APIs de conveniencia para facilitar la creación de un servicio en primer plano.
APIs alternativas
El sistema ofrece APIs alternativas que están diseñadas para tener un mejor rendimiento en casos de uso más específicos. Si existe una API alternativa para tu caso de uso, te recomendamos que uses esa API en lugar de un servicio en primer plano, ya que debería ayudar a que tu app tenga un mejor rendimiento. En la documentación de los tipos de servicios en primer plano, se indica cuando hay una API alternativa adecuada para usar en lugar de un tipo de servicio en primer plano en particular.
Estos son algunos de los casos más comunes para usar APIs alternativas:
- Usar transferencias de datos iniciadas por el usuario para realizar descargas o cargas grandes, en lugar de crear un servicio en primer plano de sincronización de datos
- Usar el administrador de dispositivos complementarios para la vinculación Bluetooth y la transferencia de datos, en lugar de usar un servicio en primer plano del dispositivo conectado
- Usar el modo de pantalla en pantalla para reproducir video, en lugar de crear un servicio en primer plano de reproducción multimedia
Tareas que inicia el usuario
Si una app necesita realizar tareas en segundo plano y el usuario inicia la operación mientras la app está visible, responde estas preguntas para encontrar el enfoque correcto.
¿La tarea debe seguir ejecutándose mientras la app se ejecuta en segundo plano?
Si la tarea no necesita seguir ejecutándose mientras la app está en segundo plano, debes usar el trabajo asíncrono. Hay varias opciones para realizar trabajos asíncronos. Lo importante es comprender que todas estas opciones dejan de funcionar si la app pasa a segundo plano. (También se detienen si se cierra la app). Por ejemplo, una app de redes sociales podría querer actualizar su feed de contenido, pero no necesitaría terminar la operación si el usuario salió de la pantalla.
¿La experiencia del usuario será mala si la tarea se aplaza o se interrumpe?
Es importante considerar si la experiencia del usuario se vería perjudicada si se pospone o cancela una tarea. Por ejemplo, si una app necesita actualizar sus recursos, es posible que el usuario no note si la operación se realiza de inmediato o en medio de la noche mientras el dispositivo se está recargando. En casos como este, debes usar las opciones de trabajo en segundo plano.
¿Es una tarea breve y fundamental?
Si la tarea no se puede retrasar y se completará rápidamente, puedes usar un servicio en primer plano con el tipo shortService
. Estos servicios son más fáciles de crear que otros servicios en primer plano y no requieren tantos permisos. Sin embargo, los servicios cortos deben completarse en tres minutos.
¿Hay una API alternativa solo para este fin?
Si la tarea no es invisible para el usuario, la solución correcta puede ser usar un servicio en primer plano. Estos servicios se ejecutan de forma continua una vez que se inician, por lo que son una buena opción cuando interrumpir la tarea tendría una mala experiencia del usuario. Por ejemplo, una app de seguimiento de entrenamiento podría usar sensores de ubicación para permitir que los usuarios registren su ruta de trote en un mapa. No querrás hacer esto con una opción de trabajo en segundo plano, ya que, si la tarea se pausa, el seguimiento se detendrá de inmediato. En una situación como esta, un servicio en primer plano es lo más lógico.
Sin embargo, como los servicios en primer plano pueden usar muchos recursos del dispositivo, el sistema impone muchas restricciones sobre cuándo y cómo se pueden usar. En muchos casos, en lugar de usar un servicio en primer plano, puedes usar una API alternativa que controle la tarea por ti con menos problemas. Por ejemplo, si tu app necesita realizar una acción cuando el usuario llega a una ubicación determinada, la mejor opción es usar la API de geovallado en lugar de hacer un seguimiento de la ubicación del usuario con un servicio en primer plano.
Tareas en respuesta a un evento
A veces, una app necesita realizar tareas en segundo plano en respuesta a un activador, como los siguientes:
- Mensajes de transmisión
- Mensajes de Firebase Cloud Messaging (FCM)
- Alarmas establecidas por la app
Puede ser un activador externo (como un mensaje de FCM) o una respuesta a una alarma establecida por la app. Por ejemplo, un juego podría recibir un mensaje de FCM que le indique que actualice algunos recursos.
Si puedes asegurarte de que la tarea finalizará en unos segundos, usa el trabajo asíncrono para realizarla. El sistema le permitirá a tu app unos segundos para realizar esas tareas, incluso si estaba en segundo plano.
Si la tarea tardará más de unos segundos, es posible que sea apropiado iniciar un servicio en primer plano para controlarla. De hecho, incluso si tu app está en segundo plano, es posible que se le permita iniciar un servicio en primer plano si el usuario activó la tarea y esta se encuentra en una de las exenciones aprobadas de las restricciones de inicio en segundo plano. Por ejemplo, si una app recibe un mensaje de FCM de prioridad alta, puede iniciar un servicio en primer plano, incluso si se ejecuta en segundo plano.
Si la tarea tardará más de unos segundos, usa las APIs de programación de tareas.