C.OG
C.OG

Reputation: 6529

Is there any difference between accessing a subject directly on a class or using a getter

Lets say I have a service that exposes a subject:

import { Injectable } from "@angular/core";
import { BehaviorSubject } from "rxjs";

@Injectable()
export class StateService {
  private mySubject = new BehaviorSubject<string>("test");
  mySubject$ = this.mySubject.asObservable();

  constructor() {}

  updateSubject(value: string) {
    this.mySubject.next(value);
  }

  get mySubject2$() {
    return this.mySubject.asObservable();
  }
}

In my component:

import { Component } from "@angular/core";
import { StateService } from "./state.service";

@Component({
  //...
})
export class AppComponent {
  name = this.state.mySubject$;
  name2 = this.state.mySubject2$;

  constructor(private state: StateService) {}
}

Are there any differences apart from stylistic in terms of using an accessor to return the subject or accessing it directly via a property on the class?

Upvotes: 0

Views: 782

Answers (1)

jonrsharpe
jonrsharpe

Reputation: 122096

There are two differences:

  1. When you invoke the get accessor, it calls Subject#asObservable to create a new observable for each consumer, whereas the property is a single observable. An observable can have multiple subscribers, so it's slightly less efficient to create multiple observables.

  2. When you use a public property, unless you explicitly mark it readonly, consumers can replace the observable, so that subsequent access wouldn't get the observable linked to the subject the instance is managing.

In your case, I would probably use:

import { Injectable } from "@angular/core";
import { BehaviorSubject } from "rxjs";

@Injectable()
export class StateService {
  private mySubject = new BehaviorSubject<string>("test");
  readonly mySubject$ = this.mySubject.asObservable();

  updateSubject(value: string) {
    this.mySubject.next(value);
  }
}

Upvotes: 8

Related Questions