Dmytro Danylyk
12/03/2018, 5:08 AMoshai
12/03/2018, 6:58 AMbdawg.io
12/03/2018, 7:03 AMwithContext
instead of witchContext
(unless that's a new method I haven't come across yet)networkClient
on Dispatchers.Default
instead of <http://Dispatchers.IO|Dispatchers.IO>
?Tolriq
12/03/2018, 7:42 AMCoroutineScope
directly. I would use SupervisorJob
to avoid parent Job cancellation. And to avoid recreating a job use coroutineScope.cancelChildren
bdawg.io
12/03/2018, 7:49 AMcancelChildren
@Tolriq hahaDmytro Danylyk
12/03/2018, 7:51 AMdave08
12/03/2018, 8:36 AMDmytro Danylyk
12/03/2018, 8:44 AMlogin
.dave08
12/03/2018, 8:47 AMsuspend
and blocking...Dmytro Danylyk
12/03/2018, 8:49 AMsuspend fun login(): Result = withContext(Dispatcher.Main) {
view.showLoading()
val result = withContext(<http://Dispatcher.IO|Dispatcher.IO>) {
networkClient.login(...)
}
view.hideLoading()
return result
}
dave08
12/03/2018, 8:51 AMTolriq
12/03/2018, 8:58 AMDmytro Danylyk
12/03/2018, 9:03 AMTolriq
12/03/2018, 9:04 AMDmytro Danylyk
12/03/2018, 9:08 AMTolriq
12/03/2018, 9:09 AMDmytro Danylyk
12/03/2018, 9:10 AMtry { work.await() }
catch(e: Exception { }
Tolriq
12/03/2018, 9:11 AMDmytro Danylyk
12/03/2018, 9:12 AMTolriq
12/03/2018, 9:12 AMDmytro Danylyk
12/03/2018, 10:10 AMTolriq
12/03/2018, 10:12 AMDmytro Danylyk
12/03/2018, 11:09 AMlouiscad
12/03/2018, 2:11 PMasync
and await
calls inside a coroutineScope { … }
lambda, and catch any exception/throwable outside of this very scope:
try {
coroutineScope {
val mayFailAsync1 = async {
mayFail1()
}
val mayFailAsync2 = async {
mayFail2()
}
useResult(mayFailAsync1.await(), mayFailAsync2.await())
}
} catch (e: IOException) {
// handle this
} catch (e: AnotherException) {
// handle this too
}
gildor
12/03/2018, 2:28 PMwithContext(<http://Dispatcher.IO|Dispatcher.IO>) { networkClient.login(...) }
Not sure that this is a good example even with IO dispatcher.
Usage of blocking API of networking library is already a bad practice itself (blocking additional thread, no cancellation) and such example does encourage this.
If you replace networkClient.login() to something like someBlockibgCall()
it would be more explicitpakoito
12/03/2018, 2:35 PMhandleErrorWith
operator is beyond me.gildor
12/03/2018, 2:37 PMhandleErrorWith
?louiscad
12/03/2018, 2:37 PMpakoito
12/03/2018, 2:39 PMuseResult(mayFailAsync1.await(), mayFailAsync2.await())
.handleErrorWith { when (it) is { ... } }
louiscad
12/03/2018, 2:40 PMcoroutineScope { … }
, so it is plain unsafe.pakoito
12/03/2018, 2:40 PMlouiscad
12/03/2018, 2:52 PMcoroutineScope { … }
call.pakoito
12/03/2018, 2:57 PMlouiscad
12/03/2018, 3:10 PMcoroutineScope { … }
, what you call the "subscope", is automatically cancelled if the CoroutineContext
it was called from is cancelled. And, yes, each time you want to do parallelization with async
(and await
), you have to make sure you have a local scope where you can recover from the outside, but in practice, you do not do parallelization so often as calling suspend functions sequentially.pakoito
12/03/2018, 3:26 PMJorge Castillo
12/03/2018, 8:38 PMlouiscad
12/03/2018, 8:42 PMDmytro Danylyk
12/04/2018, 12:37 AMIf you replace networkClient.login() to something like👍it would be more explicitsomeBlockibgCall()
pakoito
12/04/2018, 12:51 AMIO
already. Now we have to comply with the same behavior bridging Deferred. It's possible, just a moving target at the moment :)Jorge Castillo
12/04/2018, 2:14 PMpakoito
12/04/2018, 2:43 PMlouiscad
12/04/2018, 10:46 PMAlexey Pushkarev
12/06/2018, 6:57 PMDmytro Danylyk
12/06/2018, 10:30 PMCoroutineScope
so launch will be executed using that scope.