Reputation: 1318
In Ktor, I am hoping to implement some way to reference key value pairs inside a coroutineContext, without dragging references to objects around in method parameters. Based on https://proandroiddev.com/demystifying-coroutinecontext-1ce5b68407ad I have written my reference classes:
class MyElement(override val key: CoroutineContext.Key<*>, val value: String) : CoroutineContext.Element
class MyKey: CoroutineContext.Key<MyElement>
... // inside routing:
val key: CoroutineContext.Key<MyElement> = MyKey()
val ele = MyElement(key, "myJWT")
withContext(coroutineContext + ele) {
val notNullEle : MyElement = coroutineContext[ele.key] as MyElement // not null
logger.info(notNullEle.value) // "myJWT"
val shouldNotBeNullEle = coroutineContext[MyKey()]// NULL!
}
val shouldBeNull = coroutineContext[ele.key] // is and should be null
val shouldBeNull2 = coroutineContext[MyKey()] // is and should also be null
When I send ele.key
to coroutineContext[ele.key]
I get the right element, but when I send a new instance of MyKey along, I get null, so the instance of MyElement is clearly mapped to the instance of the key. That does not work well for my purposes however, as I was hoping to get the instance of MyElement using the class of MyKey, since I would like to be able to, for instance, get the value in a HttpClient in the service layer without having to pass ele.key
all the way down the chain. Is it possible?
What I am asking is basically the same as How to make request-bound data globally available in Ktor? which is unfortunately unanswered.
Upvotes: 1
Views: 2193
Reputation: 25573
As described in the article you linked, you could consider the CoroutineContext
to be a Map
with CoroutineContext.Key
as its keys.
Given this premise the problem you are having is clear, ele.key != MyKey()
or the keys are not equivalent by definition, so they will not return the same entry within the context Map.
This is the reason why most CoroutineContext.Key
implementations are object
, because that implements the equals
method based on the object singleton. You will either need to also use object
or correctly implement equals
and hashCode
.
Upvotes: 6