2

Scenario:

Web app built with Angular 5, apollo-angular and apollo-client.

Have a component that subscribes to data with projects. OnInit() I call apollo.watchQuery() as specified in the docs. So far, so good! The subscribe gets the data when going to the component and also when returning values in the mutation queries of the same model! Great!

The problem is, when I click around in my app, doing lots of CRUD operations with apollo, I experience that the app gets slower and slower. One thing I noticed is that if I navigate to another component, and then back to previosly mentioned Project Component, in my Apollo Chrome Dev Tools I can see that the previous active WatchQuery for projects (no 19 in the image below) stays put and another one (no 35) is added.

Could this be a problem? That the redundant active WatchQueries take up unnecessary memory in the client session, making the app go slower and slower, or is this normal? Should you manually terminate watchedQueries in the component's OnDestroy method and in that case, how do I do this (couldn't see anything mentioned about this in the docs)?

Redundant watchQueries

Patrik Nilsson
  • 243
  • 1
  • 3
  • 9

1 Answers1

1

Yes, you need to unsubscribe watchQueries, I had the exact same issue. But simple .query() are fine.
I am not sure about performances, but I think it can be an issue when you have a lot of them. In my app, a watchQuery in a destroyed component was still doing some stuff, and was causing unexpected behaviors.

The best way to unsubscribe, is by using takeUntil operator from RxJS, and a subject that you complete in OnDestroy method.
See this anwser: https://stackoverflow.com/a/41177163/3859915

Example (with apollo 2.0 and RxJS lettable operators):

import { Subject } from 'rxjs/Subject';
import { takeUntil } from 'rxjs/operators';

export class MyComponent implements OnInit, OnDestroy {
    private ngUnsubscribe: Subject<void> = new Subject<void>();

    ngOnInit() {
        this.apollo.watchQuery({...})
            .valueChanges
            .pipe(takeUntil(this.ngUnsubscribe))
            .subscribe(response => {
                ...
            });
    }

    ngOnDestroy() {
        this.ngUnsubscribe.next();
        this.ngUnsubscribe.complete();
    }
}
Samy
  • 1,651
  • 1
  • 11
  • 12