apollo-ios icon indicating copy to clipboard operation
apollo-ios copied to clipboard

GraphQLQueryWatcher retained by ApolloStore

Open AnthonyMDev opened this issue 6 years ago • 11 comments

I might be missing something here, but it seems to me like a GraphQLQueryWatcher that is not cancelled explicitly is retained by the ApolloStore and will continue to receive updates, even if the object that created the watcher (by calling watch()) releases it.

Do I need to be ensuring that I manually cancel() my GraphQLQueryWatcher every time I'm done with it? It would be nice if, when I have no retain on the watcher, it automatically cancels.

If I'm missing something and it already works this way, then please let me know and close this!

Thanks

AnthonyMDev avatar Apr 23 '19 18:04 AnthonyMDev

Hi @AnthonyMDev,

I have same issue do you find any solution?

Thanks

niraj1991 avatar Jun 12 '19 06:06 niraj1991

Yeah not having to manually cancel would certainly be ideal, but I don't think that's how things are set up at the moment. I'll have to see how plausible that is, though I don't have an ETA for you at the moment.

designatednerd avatar Jul 15 '19 13:07 designatednerd

It seems to me like the solution would just be having the watcher call cancel() on itself in it's own deinit block.

AnthonyMDev avatar Jul 24 '19 20:07 AnthonyMDev

If it's being retained by the Apollo store, wouldn't deinit never get called?

designatednerd avatar Jul 24 '19 20:07 designatednerd

Ahhhh I looked at this last quite a while ago. I forgot about that part. Yes, we would need to figure that out.

AnthonyMDev avatar Jul 24 '19 21:07 AnthonyMDev

Sounds like it's time for some good old DisposeBags.

Sent with GitHawk

casey-chow avatar Jul 25 '19 04:07 casey-chow

@casey-chow That...might be difficult given that we don't (and don't intend to) use Rx on this project 😃

designatednerd avatar Jul 25 '19 12:07 designatednerd

Would be a breaking change, but making the store not retain the watcher, and require the developer to retain a reference to the watcher for as long as it's needing the watcher could work, right?

koenpunt avatar Aug 21 '19 15:08 koenpunt

I also expected that query watcher would unsubscribe itself once I release all references to it. Maybe documentation needs to stress this even more, with a - warning: .

One can create a dedicated object to unsubscribe query watcher from Apollo store upon it's deallocation. That simplified the code in my project a bit.

final class ApolloWatcherHandle<Query>: QueryWatcher where Query: Apollo.GraphQLQuery {
    
    private let watcher: GraphQLQueryWatcher<Query>
    
    init(watcher: GraphQLQueryWatcher<Query>) {
        self.watcher = watcher
    }
    
    deinit {
        watcher.cancel()
    }
}

wnagrodzki avatar Feb 28 '20 14:02 wnagrodzki

Probably not a bad idea to throw something into the docs on this for now. I do think long term it'd be nice to be able to auto-unsubscribe but this is way down the backlog, alas.

designatednerd avatar Feb 28 '20 18:02 designatednerd

I actually really like @wnagrodzki 's solution here.

This may be fixed now by @gpambrozio's PR #1826. But if not, @wnagrodzki gave me the idea of making the watcher that the store retains opaque and exposing a wrapper that handles cancellation on deinit.

AnthonyMDev avatar Jun 14 '21 16:06 AnthonyMDev