Geoff
Geoff

Reputation: 6629

Angular2 fire listen to node changes throws an error

The code below was working and it should listen for changes in a node and execute a function but now am getting an error:

ncaught TypeError: Object(...) is not a function
at SwitchMapSubscriber.eval [as project] (changes.js:7)

So, in my angular2 component I have:

private subscriptions = new Subscription();

registered: AngularFireList<any>;
constructor(private _af: AngularFireDatabase){
     this.registered = _af.list('/registered');
 }

ngOnInit() {
    this.subscriptions.add(
        this.registered.valueChanges().subscribe(
            res => {
                console.log("the value has changed");
            }
        )
    );
}

So where am I going wrong as getting the error above which point to:

angular2fire/database/list/changes

What I need my code to do is to listen to whenever there is a change in a firebase node and log to the console

The subscriptions have also been defined by:

    private subscriptions = new Subscription();

Adding it to the subscriptions then I can use onDestroy lifecycle and prevent memory leaks as shown below

    ngOnDestroy() {
      this.subscriptions.unsubscribe();
    }

Upvotes: 6

Views: 170

Answers (2)

Niladri Basu
Niladri Basu

Reputation: 10604

This is a popular issue these days. Please upgrade rxjs 5 to version 6.

This happens due to some breaking changes in AngularFire. Once upgraded the function should perform as expected.

Upgrade using: npm install rxjs@6 rxjs-compat@6 --save (Recomended)

Or rollback (Not recomended) using:

npm uninstall angularfire2
npm install [email protected]
npm uninstall firebase
npm install [email protected]

See the rxjs official migration doc for how-to's and more details on the changes between 5 and 6.

Upvotes: 2

ggradnig
ggradnig

Reputation: 14149

It seems you don't have a list for your subscriptions, but only a single subscription stored in subscriptions. Try changing it to an array like this:

private subscriptions: Subscription[] = [];

registered: AngularFireList<any>;
constructor(private _af: AngularFireDatabase){
     this.registered = _af.list('/registered');
 }

ngOnInit() {
    this.subscriptions.push(
        this.registered.valueChanges().subscribe(
            res => {
                console.log("the value has changed");
            }
        )
    );
}

ngOnDestroy() {
   this.subscriptions.forEach((s) => s.unsubscribe());
}

With Subscription.add you actually add TeardownLogic to an existing subscription. This can be used when you have additional cleaning up to do.

If you know that you will only have one subscription, use the assignment operator = instead of the add() function, like this:

private subscription: Subscription;

registered: AngularFireList<any>;
constructor(private _af: AngularFireDatabase){
     this.registered = _af.list('/registered');
 }

ngOnInit() {
    this.subscription =
        this.registered.valueChanges().subscribe(
            res => {
                console.log("the value has changed");
            }
     );
}

ngOnDestroy() {
   this.subscription.unsubscribe();
}

Upvotes: 0

Related Questions