处理Angular4 Http Obserable响应的最佳实践

时间:2017-05-18 17:06:02

标签: angular rxjs

我有编写C#和Angular1代码的经验,但Angular2 +和RxJ对我来说是新的。

我刚刚编写了一个Angular4登录组件,我觉得我已经通过在observable的map函数中缓存login方法的结果来编写代码气味。

我有一个LoginComponent调用登录的AuthenticationService:

  login(username: string, password: string): Observable<User> {
return this.http
  .post('/api/users/login', { username: username, password: password })
  .map((response: Response) => {

    let loginResult = response.json();
    this.user = loginResult.user as User

    localStorage.setItem(tokenStorageName, loginResult.token);

    return this.user;
  })
  .catch(this.handleError);

}

在地图功能中保存状态感觉很奇怪,因为据我所知,它应该只是一个翻译功能。我想缓存从登录结果返回的用户和​​令牌,这样如果我想要用户数据,我就不必再拨打另一个服务电话。

以下是登录组件的逻辑:

  login() {
this.isLoading = true;
this.authenticationService.login(this.model.username, this.model.password)
  .subscribe(
  result => {
    let returnUrl = this.activatedRoute.snapshot.queryParams['returnUrl'] || '/'
    this.router.navigate([returnUrl]);
  }, error => {
    if (error != null && error.code == unauthorizedCode) {
      this.error = 'Username or password incorrect';
    }
    else {
      this.error = 'Error logging in';
    }
    this.isLoading = false;
  });

对于LoginComponent在AuthenticationService或UserCache上调用setUser,感觉不合适。

有人可以给我一些关于最佳实践的建议吗?

2 个答案:

答案 0 :(得分:0)

尝试类似:

login(username: string, password: string): Observable<User> {
    let o = this.http
        .post('/api/users/login', { username: username, password: password})
    //uncomment if you have multiple subscribers, otherwise http request is executed multiple times
        //.share()
    ;

    o.subscribe(
        (response: Response) => {
            this.user = loginResult.user as User;
            localStorage.setItem(tokenStorageName, loginResult.token);
        },
        (response: Response) => this.handleError(response)
    );

    return o.map(response: Response =>  response.json());
}

答案 1 :(得分:0)

Todd Motto通过Twitter发表了一个很好的例子:

https://twitter.com/toddmotto/status/865531009638440961

&#34;这是一个非常方便的单一状态存储的地方 - 你可以用以下代码完成你的代码: .do(next =&gt; / *用这个值做/ *)&#34;