Behaviour subject initial value null?

AngularTypescriptRxjs

Angular Problem Overview


private customer: Subject<Object> = new BehaviorSubject<Object>(null);

setCustomer(id, accountClassCode) {
    this.customer.next({'id': id, 'accountClassCode': accountClassCode});
}

getCustomer() {
    return this.customer.asObservable();
}

I'm using this part of code but I'm getting an error that can not find id of null. Is there any solution to get initial value that is not null?

Angular Solutions


Solution 1 - Angular

The purpose of BehaviorSubject is to provide initial value. It can be null or anything else. If no valid initial value can be provided (when user id isn't known yet), it shouldn't be used.

ReplaySubject(1) provides a similar behaviour (emits last value on subscription) but doesn't have initial value until it is set with next.

It likely should be

private customer: Subject<Object> = new ReplaySubject<Object>(1);

Solution 2 - Angular

Try structuring this way your service:

Service:

@Injectable()
export class MyService {
    customerUpdate$: Observable<any>;

    private customerUpdateSubject = new Subject<any>();

    constructor() {
        this.customerUpdate$ = this.customerUpdateSubject.asObservable();
    }

    updatedCustomer(dataAsParams) {
        this.customerUpdateSubject.next(dataAsParams);
    }
}

Remember to add MyService to providers.

Where you update your client (if this is the case), you do something like this:

Component (The one that triggers):

constructor(private myService: MyService) {
        // I'll put this here, it could go anywhere in the component actually
        // We make things happen, Client has been updated
        // We store client's data in an object
        this.updatedClient = this.myObjectWithUpdatedClientData;  // Obj or whatever you want to pass as a parameter
        this.myService.updatedCustomer(this.updatedClient);
    }

Component (The one that is Subscribed):

this.myService.customerUpdate$.subscribe((updatedClientData) => {
            // Wow! I received the updated client's data
            // Do stuff with this data!
        }
    );

From what I understood, you are trying to pass data from 1 component to another. You get your Client's data and send it over your App to another component, right? That's why I posted this solution.

If you are interested in other types of subscriptions, read this:

https://stackoverflow.com/questions/43118769/angular-2-special-observables-subject-behaviour-subject-replaysubject

Solution 3 - Angular

I have found many cases where I want the simplicity of ReplaySubject(1) but also want the value property of BehaviorSubject, i.e. it stores your most recent value for retrieval without having to subscribe. And using BehaviorSubject was always annoying given the need for an initial value that gets broadcast, a condition I rarely wanted. To that end I created my own CurrentSubject.

import { ReplaySubject } from "rxjs";

export class CurrentSubject<T> extends ReplaySubject<T> {
    value: T;

    set(value?: T) {
        this.value = value;
        this.next(value);
    }
}

I wanted to override the next method but I couldn't get that to work for some reason, so I settled on a method called set. My override attempt looked like this...

export class CurrentSubject<T> extends ReplaySubject<T> {
    value: T;

    next(value?: T) {
        this.value = value;
        super.next(value);
    }
}

I don't know why overriding didn't work.

Solution 4 - Angular

Since the object can be null, a better choice is to infer the type like this

 private customer = new BehaviorSubject<Customer|null>(null);

Solution 5 - Angular

Another way is to use pipe to filter until a non-null value is received. It can be done with takeWhile also.

.pipe(filter(val => !!val)).subscribe(x => {});

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionNoneView Question on Stackoverflow
Solution 1 - AngularEstus FlaskView Answer on Stackoverflow
Solution 2 - AngularSrAxiView Answer on Stackoverflow
Solution 3 - AngularcrowmagnumbView Answer on Stackoverflow
Solution 4 - AngularBellashView Answer on Stackoverflow
Solution 5 - AngularSridhar ChiduralaView Answer on Stackoverflow