allan.conda
03/04/2021, 4:02 PMallan.conda
03/04/2021, 4:03 PMreturn coroutineScope {
val books = async(defaultDispatcher) {
booksRepository.getAllBooks()
}
val authors = async(defaultDispatcher) {
authorsRepository.getAllAuthors()
}
BookAndAuthors(books.await(), authors.await())
}
and this
return withContext(defaultDispatcher) {
val books = async {
booksRepository.getAllBooks()
}
val authors = async {
authorsRepository.getAllAuthors()
}
BookAndAuthors(books.await(), authors.await())
}
The latter is what I naturally do when I need parallel loading behavior,
I’m curious if this is considered bad practice.allan.conda
03/04/2021, 4:04 PMallan.conda
03/04/2021, 4:07 PMTony Kazanjian
03/04/2021, 9:51 PMcoroutineScope
in the business layer class instead of passing in an externalScope
managed by the application? I have something like this:
class LoginInteractor(private val repository: NueveRepository, dispatcher: CoroutineDispatcher = Dispatchers.Main){
private val coroutineScope = CoroutineScope(Job() + dispatcher)
@ExperimentalCoroutinesApi
fun loginUser(
needsRefresh: Boolean = false,
userEmail: String = String.empty,
userPassword: String = String.empty,
loginResult: (Result<Unit>) -> Unit = {}
) {
coroutineScope.launch {
// executes api call and returns the loginResult for the view event (i.e. going to the next composable)
// then, calls a suspend function that stores user info in a DataStore
This seems to work fine, as the user info is written to DataStore when navigation happens to the new composable. Is there anything wrong with this approach?Manuel Vivo
03/08/2021, 7:10 AMwithContext
, that’s definitely not consider a bad practice
2. That’s fine too, only inject Dispatchers iff you need them. If the repo is only proxying to Room or Retrofit, there’s no need to use a Dispatchers in there
3. For that, I wrote about it here https://manuelvivo.dev/coroutines-cancellation-exceptions-3. You can catch the exceptions at the collection point or lower from the hierarchy. There isn’t really a rule of thumb for this, it depends on the requirements and the use case. Do what you think that feels right.Manuel Vivo
03/08/2021, 7:14 AMLoginInteractor
is that it cannot be cancelled from outside. So, if the class needs to be garbage-collected because it’s no longer needed. It’ll be in memory as long as a coroutine created by that scope is active. On the other hand, if you inject the scope, the class that control the interactor’s lifecycle can cancel the injected coroutineScope to not waste resources.
Hope this helps!allan.conda
03/08/2021, 7:23 AMManuel Vivo
03/08/2021, 7:23 AMManuel Vivo
03/08/2021, 7:23 AMallan.conda
03/08/2021, 7:24 AM