Hi! We just released a canary version of our app w...
# apollo-kotlin
e
Hi! We just released a canary version of our app with Apollo 3 🎉 , and while nothing went terribly wrong, we noticed a slightly higher Application Not Responding rate coming from low-end devices, that all point to
DefaultApolloStore.readFragment()
(full stacktrace in thread). We call this function using a
Dispatchers.Main.immediate
scope. Just to validate my understanding, Apollo doesn't do anything about running this method in the background, thus the ANR, and we should use some other dispatcher instead. Does that sound about right?
Stacktrace:
Copy code
io.sentry.android.core.ApplicationNotResponding: Application Not Responding for at least 5000 ms.
    at java.lang.Object.wait(Object.java)
    at java.lang.Thread.parkFor$(Thread.java:2137)
    at sun.misc.Unsafe.park(Unsafe.java:358)
    at java.util.concurrent.locks.LockSupport.park(LockSupport.java:190)
    at java.util.concurrent.locks.AbstractQueuedSynchronizer.parkAndCheckInterrupt(AbstractQueuedSynchronizer.java:868)
    at java.util.concurrent.locks.AbstractQueuedSynchronizer.doAcquireShared(AbstractQueuedSynchronizer.java:993)
    at java.util.concurrent.locks.AbstractQueuedSynchronizer.acquireShared(AbstractQueuedSynchronizer.java:1307)
    at java.util.concurrent.locks.ReentrantReadWriteLock$ReadLock.lock(ReentrantReadWriteLock.java:729)
    at com.apollographql.apollo3.cache.normalized.internal.Lock.read(Lock.kt:11)
    at com.apollographql.apollo3.cache.normalized.internal.DefaultApolloStore.readFragment
    at com.apollographql.apollo3.cache.normalized.ApolloStore$DefaultImpls.readFragment$default(ApolloStore.kt:58)
m
Yes, that is correct. The ApolloStore APIs are blocking APIs. It's unfortunate that they are
suspend
, that's certainly something we'll want to change.
Or maybe we need it to be effectively
suspend
but then we need a way to specify the default dispatcher
Or SQLDelight removed all the default dispatchers recently, might be safer to just require the caller to pass the dipatcher (but it's going to be more verbose for sure)
e
Ah, I missed the doc, sorry 🙈 But yeah, the fact that is a suspend function was the main cause for confusion.
ApolloClient
already has a dispatcher defined, wouldn't it make sense to have the same one used by the store? Or do you think that there is a case for having a different one?
m
It's an API issue
ApolloStore
can be created without an
ApolloClient
. Not really sure what the use case for this is but it's possible so we'd have to "bind/propagate" the Dispatcher somehow
It's the exact same issue we have with
CustomScalarAdapters
actually,
ApolloStore
doesn't know anything of the
CustomScalarAdapters
in your ApolloClient
It's nicely decoupled but it's also verbose because you have to pass the
CustomScalarAdapters
all around
e
I see, makes sense. The "bind/propagate" solution would sound nice 😄
m
Yep, we'll work on something. You can follow https://github.com/apollographql/apollo-kotlin/issues/3823 for updates