Armin Dervić
Armin Dervić

Reputation: 205

Observable value doesn't update

I'm trying to get notification token value from fcm service to my component, but token observable doesn't update after i fetch token from plugin.

This is my fcm.service.ts I fetch the token in my app component.

      private notificationToken = new BehaviorSubject<string>(null);
      sharedNotificationToken$ = this.notificationToken.asObservable();
  
      // This is called in the app component
      PushNotifications.addListener('registration',
        (token: Token) => {
          console.log('token: ', token) // here token has value
          this.notificationToken.next(token.value);
        }
      );

And when I try to get token value from another component, it returns null (initial observable value).

        ngOnInit(){
          this.fcmService.sharedNotificationToken$.subscribe(token => {
          // here token is NULL
          this.notificationToken = token;
       })
     }

Upvotes: 0

Views: 1186

Answers (1)

VVS
VVS

Reputation: 293

The reason you get null is because you set your BehaviorSubject to null by doing this:

   private notificationToken = new BehaviorSubject<string>(null);

Behavior Subject: New subscribers get the last published value OR initial value immediately upon subscription.

Subject: A subscriber will only get published values thereon-after the subscription is made.

Replay Subject: New subscribers get all previously published value(s) immediately upon subscription.

Async Subject - Emits latest value to observers upon completion.

Here is the documentation for subjects.

In the following example, the BehaviorSubject is initialized with the value 0 which the first Observer receives when it subscribes. The second Observer receives the value 2 even though it subscribed after the value 2 was sent.

import { BehaviorSubject } from 'rxjs';

// New behavior subject initialized with 0 as default value
const subject = new BehaviorSubject(0);
 
// Subscribes to the subject to log observerA
subject.subscribe({
  next: (v) => console.log(`observerA: ${v}`)
});
 
// set subject value to 1
subject.next(1);

// set subject value to 2
subject.next(2);
 
// subscribe to subject and log observerB
subject.subscribe({
  next: (v) => console.log(`observerB: ${v}`)
});
 
// set subject value to 3
subject.next(3);
 
// Output Console Logs
// observerA: 0
// observerA: 1
// observerA: 2
// observerB: 2
// observerA: 3
// observerB: 3

Further more on the topic of instances of your service:

If you add a service only to @NgModule({ providers: [YourService] }) and no where else, then there will always be one instance of YourService in the whole application.

However this is only true when the @NgModule() decorator is on a non lazy loaded module. The Providers of lazy loaded modules can be imported with a forRoot to ensure the service will be a singleton.

If you add services to @Component({ providers: [...] }) then you will have as many instances as there are instances of the component.

Upvotes: 3

Related Questions