Michal Fudala
12/13/2018, 5:02 PMc2
method hang here ?Dico
12/13/2018, 5:17 PMrunBlocking
has a dispatcher that wraps a single threaded event loopasync
call is waiting on the producer()
invocation to become available, which in turn is waiting on the thread to become available that is used by async
Michal Fudala
12/13/2018, 5:59 PMrunBlocking(newFixedThreadPoolContext(10, "a") { ... }
?Dico
12/13/2018, 6:02 PMMichal Fudala
12/13/2018, 6:09 PMDico
12/13/2018, 6:10 PMgildor
12/14/2018, 5:48 AMasync { producer() }.await()
which starts new coroutine (async) and async itself creates another one and waits for child coroutine work result to avoid leaks. If you really need channels that can be consumed globally, just use GlobalScope:
async { GlobalScope.producer() }.await()
Dico
12/14/2018, 8:45 AMproduce
can't be started because it's been scheduled on this particular dispatcher with one thread. Thus, async
needs to suspend first.
async
can only complete when produce
started and invoked close()
gildor
12/14/2018, 8:46 AMDico
12/14/2018, 8:46 AMrunBlocking
because this wouldn't block otherwise, on default dispatcher for examplegildor
12/14/2018, 8:46 AMDico
12/14/2018, 8:47 AMgildor
12/14/2018, 8:47 AMDico
12/14/2018, 8:48 AMgildor
12/14/2018, 8:48 AMproducer()
is a new coroutine that never finishes (because nobody consumes value from channel)async {}
is scopeDico
12/14/2018, 8:48 AMgildor
12/14/2018, 8:48 AMDico
12/14/2018, 8:49 AMgildor
12/14/2018, 8:51 AMDico
12/14/2018, 8:52 AMclose()
on the channelgildor
12/14/2018, 8:53 AMDico
12/14/2018, 8:53 AMsend
will suspend and thus close()
is not reached unless the value is consumedgildor
12/14/2018, 8:53 AMclose()
is useless in general. because it will be closed when produce block returnDico
12/14/2018, 8:54 AMgildor
12/14/2018, 8:54 AMDico
12/14/2018, 8:54 AMgildor
12/14/2018, 8:55 AMDico
12/14/2018, 8:56 AMgildor
12/14/2018, 8:56 AMDico
12/14/2018, 8:56 AMawait()
waits on the channel to prevent you making ones unnecessarilygildor
12/14/2018, 8:56 AMDico
12/14/2018, 8:57 AMgildor
12/14/2018, 8:57 AMYou mean it’s good thatYes, this is child/parent relationships that doesn’t allow to start async background task in nowhere. At least you should be explicit and use GlobalScopewaits on the channel to prevent you making ones unnecessarilyawait()
async { produce {} }
as async { launch {} }
, so you don’t want to start launch coroutine and do not wait for result