Études de cas

Comment WHOOP a réduit de plus de 90 % les sessions de wakelock partiel excessives

Temps de lecture : 4 min

Lorsque vous créez une application Android pour un wearable, le vrai travail commence lorsque l'écran s'éteint. WHOOP aide ses membres à comprendre comment leur corps réagit à l'entraînement, à la récupération, au sommeil et au stress. Pour les nombreux membres WHOOP sur Android, la synchronisation et la connectivité fiables en arrière-plan sont ce qui rend ces informations possibles.

Plus tôt cette année, Google Play a lancé une nouvelle métrique dans Android Vitals : les verrouillages partiels excessifs de l'écran. Cette métrique mesure le pourcentage de sessions utilisateur au cours desquelles l'utilisation cumulative des wakelocks non exemptés dépasse deux heures sur une période de 24 heures. L'objectif de cette métrique est de vous aider à identifier et à résoudre les éventuelles sources de décharge de la batterie, ce qui est essentiel pour offrir une expérience utilisateur de qualité.

À partir du 1er mars 2026, les applications qui ne respectent toujours pas le seuil de qualité pourront être exclues des surfaces de découverte de Google Play. Un avertissement peut également s'afficher sur la fiche Google Play Store, indiquant que l'application peut consommer plus de batterie que prévu.

Selon Mayank Saini, ingénieur Android senior chez WHOOP, cela a permis à l'équipe de relever le niveau d'efficacité d'Android. En effet, Android Vitals avait signalé que le pourcentage de wakelocks partiels excessifs de l'application était de 15 %, ce qui dépassait le seuil recommandé de 5 %.

mayank.png

L'équipe a considéré la métrique Android Vitals comme un signal clair indiquant que le travail en arrière-plan maintenait le processeur en éveil plus longtemps que nécessaire. Cela leur permettrait de continuer à offrir une excellente expérience utilisateur tout en réduisant le temps d'exécution en arrière-plan inutile et en maintenant une connectivité et une synchronisation Bluetooth fiables et rapides.

Identifier le problème

Pour savoir par où commencer, l'équipe s'est d'abord tournée vers Android Vitals pour mieux comprendre quels verrous de réveil affectaient la métrique. En consultant le tableau de bord Android Vitals sur les wakelocks partiels excessifs, ils ont pu identifier le principal contributeur aux wakelocks partiels excessifs comme l'un de leurs workers WorkManager (identifié dans le tableau de bord comme androidx.work.impl.background.systemjob.SystemJobService). Pour prendre en charge l'expérience "toujours activée" de WHOOP, l'application utilise WorkManager pour les tâches en arrière-plan telles que la synchronisation périodique et la diffusion de mises à jour récurrentes sur le wearable. 

L'équipe savait que WorkManager acquérait un wakelock lors de l'exécution de tâches en arrière-plan, mais elle n'avait pas de visibilité sur la façon dont l'ensemble de son travail en arrière-plan (au-delà de WorkManager) était distribué jusqu'à l'introduction de la métrique "wakelocks partiels excessifs" dans Android Vitals.

Le tableau de bord ayant identifié WorkManager comme principal contributeur, l'équipe a pu concentrer ses efforts sur l'identification du worker qui contribuait le plus et s'efforcer de résoudre le problème.

Utiliser des métriques et des données internes pour mieux identifier la cause

WHOOP avait déjà configuré une infrastructure interne pour surveiller les métriques WorkManager. Ils surveillent périodiquement :

  1. Durée d'exécution moyenne : combien de temps le nœud de calcul s'exécute-t-il ?
  2. Délai d'expiration : à quelle fréquence le nœud de calcul expire-t-il au lieu de se terminer ?
  3. Nouvelles tentatives : à quelle fréquence le nœud de calcul effectue-t-il de nouvelles tentatives si le délai d'attente de la tâche est dépassé ou si elle a échoué ?
  4. Annulations : à quelle fréquence la tâche a-t-elle été annulée ?

En suivant plus que les réussites et les échecs des collaborateurs, l'équipe peut évaluer l'efficacité de son travail.

Les métriques internes ont signalé une durée d'exécution moyenne élevée pour quelques nœuds de calcul, ce qui leur a permis d'affiner encore davantage leur enquête. 

En plus de leurs métriques internes, l'équipe a également utilisé l'outil d'inspection des tâches en arrière-plan d'Android Studio pour inspecter et déboguer les workers qui l'intéressaient, en se concentrant plus particulièrement sur les wakelocks associés, afin de s'aligner sur la métrique signalée dans Android Vitals.

Enquête : distinguer les variantes de workers

WHOOP utilise la planification ponctuelle et périodique pour certains nœuds de calcul. Cela permet à l'application de réutiliser la même logique Worker pour des tâches identiques avec les mêmes critères de réussite, qui ne diffèrent que par le timing.

Grâce à leurs métriques internes, ils ont pu affiner leur recherche pour cibler un employé spécifique, mais ils n'ont pas pu déterminer si le bug s'était produit lorsque l'employé était ponctuel, périodique ou les deux. Ils ont donc déployé une mise à jour pour utiliser la méthode setTraceTag de WorkManager afin de faire la distinction entre les variantes ponctuelles et périodiques du même Worker.

Ces informations supplémentaires leur permettraient d'identifier précisément la variante de Worker (périodique ou ponctuelle) qui contribue le plus aux sessions avec des verrouillages partiels excessifs. Toutefois, l'équipe a été surprise de constater que les données ne montraient pas de différence significative entre les deux variantes.

Manmeet Tuteja, ingénieur Android II chez WHOOP, a déclaré que cette répartition nous avait également aidés à confirmer que le problème se produisait dans les deux variantes, ce qui nous a permis d'écarter la configuration de la planification et de nous orienter vers un problème de logique métier partagé dans l'implémentation du worker.

manmeet.png

En savoir plus sur le comportement des employés et corriger la cause première

Sachant qu'ils devaient examiner la logique dans le worker,  l'équipe a réexaminé le comportement des workers qui avaient été signalés lors de son enquête. Plus précisément, ils recherchaient les cas où le travail pouvait être bloqué et ne pas se terminer.

Tout cela a permis d'identifier la cause première des wakelocks excessifs :

CoroutineWorker conçu pour attendre qu'une connexion au capteur WHOOP soit établie avant de continuer. 

Si le travail a commencé sans capteur connecté, whoopSensorFlow (qui indique si le capteur est connecté) était défini sur null. Le SensorWorker n'a pas traité cela comme une condition de sortie anticipée et a continué à s'exécuter, en attendant indéfiniment une connexion. Par conséquent, WorkManager détenait un wakelock partiel jusqu'à ce que le délai d'expiration de la tâche soit atteint, ce qui entraînait une utilisation élevée du wakelock en arrière-plan et une replanification fréquente et indésirable de SensorWorker.

Pour résoudre ce problème, l'équipe WHOOP a mis à jour la logique du worker afin de vérifier l'état de la connexion avant de tenter d'exécuter la logique métier principale.

Si le capteur n'est pas disponible, le worker se ferme, ce qui évite un scénario de délai avant expiration et libère le wakelock. L'extrait de code suivant montre la solution :

class SensorWorker(appContext: Context, params: WorkerParameters): CoroutineWorker(appContext, params) {
   override suspend fun doWork(): Result {
      ...
      // Check the sensor state and perform work or return failure
       return whoopSensorFlow.replayCache
            .firstOrNull()
            ?.let { cachedData ->
                processSensorData(cachedData)
                Result.success()
            } ?: run {
                Result.failure()
            }
}

Réduction de 90% des sessions avec un nombre excessif de wakelocks partiels

Après avoir déployé le correctif, l'équipe a continué à surveiller le tableau de bord Android Vitals pour confirmer l'impact des modifications. 

Au final, WHOOP a constaté que le pourcentage excessif de wakelock partiel est passé de 15% à moins de 1% seulement 30 jours après avoir implémenté les modifications apportées à son Worker. 

partialWake.png

Grâce à ces modifications, l'équipe a constaté moins d'instances de tâches expirant sans être terminées, ce qui a entraîné une diminution des durées d'exécution moyennes. 

Voici les conseils de l'équipe WHOOP aux autres développeurs qui souhaitent améliorer l'efficacité de leur travail en arrière-plan :

sarthak.png

Commencer

Si vous souhaitez essayer de réduire le nombre excessif de wakelocks partiels de votre application ou d'améliorer l'efficacité des workers, consultez la métrique sur le nombre excessif de wakelocks partiels de votre application dans Android Vitals et la documentation sur les wakelocks pour découvrir d'autres bonnes pratiques et stratégies de débogage. 

Écrit par :

Lire la suite