Jes*_*ssy 5 observable angular
您好,有一个非常简单的函数,可以调用端点来检索我的用户,我在标头中使用它来显示连接的用户,但不想在每次渲染标头时都调用端点。
所以我正在尝试这样的事情:
public getUser(): User {
if (!this.user) {
this.http.get<User>(environment.apiRoot + '/me').subscribe(res => {
this.setUser(res);
return this.user.value;
}, err => {
});
} else {
return this.user.value;
}
}
Run Code Online (Sandbox Code Playgroud)
具有以下setUser功能:
public setUser(u: User): void {
if (!this.user) {
this.user = new BehaviorSubject(u);
} else {
this.user.next(u);
}
}
Run Code Online (Sandbox Code Playgroud)
还有BehaviorSubject: private user: BehaviorSubject<User>;
在我的标头组件中,我这样称呼它ngOnInit:
this.user = this.appState.getUser();
console.log(this.user);
Run Code Online (Sandbox Code Playgroud)
但console.log中的用户始终是未定义的,为什么它不等待函数中的订阅getUser?
您有一个使用混合反应式和命令式编程来调用的异步函数。当涉及异步函数时,您应该继续使用反应式方法,而不是尝试确定某个代码何时完成,而只是等待它完成,然后调用回调或负责的处理程序。
在您的代码中,该getUser()函数是一个async函数,因为您有内部http.get()调用。将http.get()返回一个Observable,您subscribe不必在函数内使用它。observable相反,您应该做的是从函数中返回内部,以及subscribe您真正需要它的地方。
我们可以像下面这样重写您的getUser函数(请注意,不需要命令式setUser函数)
public getUser(): Observable<User> {
return this.http.get<User>(environment.apiRoot + '/me');
}
Run Code Online (Sandbox Code Playgroud)
并在您的外部范围内订阅它,例如
this.appState.getUser().subscribe(user => {
console.log(user)
});
Run Code Online (Sandbox Code Playgroud)
更进一步来说,这也使得在模板中使用可观察量变得更加容易。
假设您将返回的可观察值分配给变量 ,user$您甚至不必订阅它!
只要让用户喜欢
this.user$ = this.appState.getUser();
获取您的 observable,然后在您的模板中使用async管道让 Angular 自动订阅和取消订阅。
<span>Hello, my name is {{user$ | async}}!</span>
| 归档时间: |
|
| 查看次数: |
28779 次 |
| 最近记录: |