https://kotlinlang.org logo
#coroutines
Title
# coroutines
a

Andrea Giuliano

11/17/2020, 11:59 AM
Hi folks, I’m working with coroutines and I’ve a question about how to implement a coroutine factory. My use case: I’m implementing an interface 
MetricEmitter
 where consumers can simply call 
emitMetric(observation)
 . Under the hood this 
MetricEmitter
 will spin up an actor responsible for ingesting those metric observations. From the external consumer of this 
MetricEmitter
 I just want to expose methods such as: • `metricEmitter.initialize()`: which will spin up the actor and ticker • `metricEmitter.emitMetric()`: which will ingest the observation • `metricEmitter.close()`: which will flush remaining metrics and tear down the actor My problem is that in the 
initialize()
 function, when I try creating the actor, it requires me to provide a 
CoroutineScope
. If I use 
coroutineScope { actor<Msg>{... }
 this code block will freeze the whole execution since it will complete when the actor terminates. That’s not what I want. I’ve managed to solve the issue by passing a coroutineScope as argument of 
metricEmitter.initialize(scope: CoroutineScope)
 but not sure if this is a smell/antipattern. Any idea how to solve/remodel the solution?
z

Zach Klippenstein (he/him) [MOD]

11/17/2020, 3:46 PM
It is very standard practice to explicitly pass scope to functions that launch coroutines then return immediately. Eg shareIn, stateIn
a

Andrea Giuliano

11/17/2020, 3:47 PM
ok, I thought it could be somehow an antipattern since you can completely detach from structured concurrency, thanks @Zach Klippenstein (he/him) [MOD]
t

travis

11/17/2020, 3:53 PM
Perhaps another option is to construct your
MetricEmitter
via a
CoroutineScope
extension function?
fun CoroutineScope.metricEmitter(...)
Possibly implicitly calling your
initialize
?
z

Zach Klippenstein (he/him) [MOD]

11/17/2020, 3:59 PM
Well, that’s true, but nothing is stopping you from detaching anyway if you really want to. The scope you pass in should have its lifecycle managed appropriately, either through structured concurrency or by being explicitly canceled.
👍 1
6 Views