In my Viewmodel class I do the next code:
init {
viewModelScope.launch(Dispatchers.IO) {
val homepageItemsCall = async { getHomepageItems() }
val carouselItemsCall = async { getCarouselItems() }
homepageItemsCall.await()
carouselItemsCall.await()
checkFavoriteStatus(homeItemsTest)
carouselItems.postValue(carouselItemsTest)
}
}
This is how my homepageItemsCall looks:
private fun getHomepageItems() = viewModelScope.launch(Dispatchers.IO) {
restService.getHomepage().getResult(
success = { value ->
homeItemsTest = value
},
genericError = { _, message ->
error.postValue(message)
},
networkError = {
error.postValue(TranslationManager.getString(TKeys.LOGIN_NETWORK_ERROR))
}
)
}
My expectation was like this:
- I create a coroutine on ViewmodelScope that is going to execute code in init block.
- since I am using async await, my code will not be executed until my API calls are done. This means both of my API calls will go to success/failure and after that, my code can go to the next line: "checkFavoriteStatus(homeItemsTest)".
But it doesn't work like that. Program goes to checkFavoriteStatus(homeItemsTest) line before my API calls are done even though I used async await. I thought that async await suspends/blocks coroutine that is executing async code (in this case, coroutine that is executing my whole init block..? Did I get something wrong?
And if yes, what is the best way to wait for my API calls to finish and then go to the next code by using coroutines?
Edit these are getHomePage and getResult functions:
suspend fun <T> ResultWrapper<T>.getResult(
success: suspend (value: T) -> Unit,
genericError: (suspend (code: Int?, message: String?) -> Unit)? =
null,
networkError: (suspend () -> Unit)? = null,
error: (suspend () -> Unit)? = null
) {
when (this) {
is ResultWrapper.Success -> {
success(value)
}
is ResultWrapper.GenericError -> {
genericError?.let { it(code, errorMessage) }
}
is ResultWrapper.NetworkError -> {
networkError?.let { it() }
}
}
if (this is ResultWrapper.NetworkError || this is ResultWrapper.GenericError)
error?.let { it() }
}
suspend fun getHomepage() = safeApiCall(Dispatchers.IO) {
apiClient.getHomepageElements()
}