I have user data service. Purpose of the data service is to broadcast user data and share data among different components. If one component makes the change to the user other components should know about it. It is working fine in other components. For example, I update location of user in Location component and its available everywhere. I have signin component where I am sending user credentials to API and receive user data. I assign received data to my broadcast user object but it doesnt reflect in my checkout component.
user-data.service.ts
import { Injectable } from '@angular/core';
import { BehaviorSubject } from 'rxjs/BehaviorSubject';
import {User} from '../entities/user';
import { Observable } from 'rxjs/Observable';
@Injectable()
export class UserDataService {
private _user: BehaviorSubject<User>;
broadCastUser: Observable<User>;
constructor() {
this._user = new BehaviorSubject<User>(new User());
this.broadCastUser = this._user.asObservable();
}
updateUser (newUser) {
this._user.next(newUser);
}
}
sign-in.component.ts
// removing unnecessary code
private _user: User;
ngOnInit() {
// Getting user info so far
this._userDataService.broadCastUser.subscribe(user => this._user = user);
}
signin () {
const body = {
UserId : this.emailAddress.value,
Password : this.password.value
};
this._spinner.show();
this._signInService.signIn(body).subscribe(
(user) => {
this._spinner.hide();
// Handling error because API response is 200 Ok. Wrong API implementation.
const userId = user[0].UserId;
if (userId === 0) {
this._isPasswordWrong = true;
} else {
this._user = user[0];
this._user.isSignedIn = true;
this._router.navigate(['/checkout']);
}
}
);
}
Please notice the line in sign in method this._user = user[0];. If I print the user properties immidiately after this line then I see they are updated. But when I go to checkout component then they are not updated. They are either old values or undefined.
I will provide all the code if required. But feels this is enough.
I am not sure whether it is the ideal solution or not but the app is working the way it supposed to work.
I added private update method to sign-in.component.ts and call it inside signIn() in place of this._user = user[0];
I took a hint from @Leon comments and came to this solution.
signin () {
const body = {
UserId : this.emailAddress.value,
Password : this.password.value
};
this._spinner.show();
this._signInService.signIn(body).subscribe(
(user) => {
this._spinner.hide();
// Handling error because API response is 200 Ok. Wrong API implementation.
const userId = user[0].UserId;
if (userId === 0) {
this._isPasswordWrong = true;
} else {
this.updateUser (user[0]);
this._router.navigate(['/checkout']);
}
}
);
}
new update ()
private updateUser (user: User) {
let newUser = new User();
newUser = user;
newUser.cart = this._user.cart;
newUser.address = this._user.address;
newUser.isSignedIn = true;
this._userDataService.updateUser(newUser);
}
I am open and ready to accept a better answer. If I found one, I will post it here.