Dans notre projet, nous devons obtenir des données (qui seront stockées) avant de faire des opérations. Dans le cas où les données ont été obtenues il y a plus de 15 minutes, nous devons les actualiser.Corotines Kotlin & Anko: retour en dehors async
Nous utilisons des coroutines Kotlin + Anko pour ce faire. L'idée (en supposant que les données aient été obtenues à un moment donné) est la suivante:
La méthode est appelée et vérifie quand nous avons les données. Si c'était moins de 15 minutes, le retourne. Si ce n'est pas le cas, procurez-vous-le de manière asynchrone (c'est une opération de réseau), stockez-le et renvoyez-le. Puisque nous ne pouvons rien faire avant d'obtenir les données actualisées, l'actualisation doit être synchrone (bien que l'opération réseau soit elle-même asynchrone).
Nous avons ce code:
fun Context.retrieveInfo(api: Api?): User? {
try {
// For sake of simplification the real conditional check is removed
if (time > 15) {
val context = this
val asyncUser = async(UI) {
val obtainData: Deferred<Data?> = bg {
api?.obtainData(sphelper.getDefaultUser(context))
}
val obtainedData = storeAndRetrieve(obtainData.await(), context)
[email protected] obtainedData
}
// ???????
} else {
val input = ObjectInputStream(this.openFileInput("data.dat"))
return input.readObject() as Data
}
} catch (e: Exception) {
return null
}
}
Comment pouvons-nous faire fonctionner attendre le résultat en dehors de la async (UI) bloquer? Ce retour est nécessaire, mais nous n'avons aucune idée de ce que nous devrions y mettre. Nous avons essayé avec la méthode getCompleted() de l'objet Deferred (return asyncUser.getCompleted()) mais il finit par s'écraser car il renvoie null.
Merci!
J'ai essayé la version simplifiée et CountDownLatch et les deux fonctionnent très bien. Je vous remercie! –
J'ai lu que runBlocking est à des fins de test, pas idéal pour les produits finis. –