登录后无法获取令牌

时间:2019-02-08 19:29:57

标签: angular

该代码应该通过API通过电子邮件和密码登录用户,然后获取访问令牌,但事实并非如此。在本地存储中没有令牌。当我输入错误的密码时,它在控制台中显示错误,状态为401;当我输入正确的密码时,它没有显示任何错误,并且在网络选项卡中,使用正确密码的请求的状态也为200,因此我认为它的日志记录是进入但未获取令牌。

import { Component, OnInit } from '@angular/core';
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
import { ApiService } from '../api.service';
import { Router } from '@angular/router';

@Component({
  selector: 'app-login1',
  templateUrl: './login1.component.html',
  styleUrls: ['./login1.component.css']
})
export class Login1Component implements OnInit {
loggedIn = false;
loginForm: FormGroup;
  constructor(private api: ApiService, private route: Router, private formBuilder: FormBuilder) { }

  ngOnInit() {
    this.loginForm = this.formBuilder.group({
      email: ['', Validators.required],
      password: ['', Validators.required]
    })
  }

  onSubmit() {
    const user = {
      email: this.loginForm.controls.email.value,
      password: this.loginForm.controls.password.value
    };

    this.api.loginUser(user);
    this.api.isUserLoggedIn.subscribe( (val) => {
      this.loggedIn = val;
      this.route.navigate(['/dashboard']);
    });

  }

}

服务

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { BehaviorSubject } from 'rxjs';

@Injectable({
  providedIn: 'root'
})
export class ApiService {

  checkStatus = new BehaviorSubject<boolean>(false);
  isUserLoggedIn = this.checkStatus.asObservable();

  readonly loginUrl= 'https://*************';

  constructor(private http: HttpClient) { }

  checkLogin() {
    const token = localStorage.getItem('access_token');
    if(token) {
      this.checkStatus.next(true);
    } else {
      this.checkStatus.next(false);
    }
  }

  loginUser(user: any) {
    return this.http.post(this.loginUrl, user)
    .subscribe((checkUser: any) => {
      if(checkUser.access_token) {
        localStorage.setItem('access_token', checkUser.access_token);
        localStorage.setItem('user', JSON.stringify(checkUser.user));
        return true;
      }
    });
  }

}

2 个答案:

答案 0 :(得分:2)

您的代码看起来不错。天真的问题,您是否检查过API是否正确发送回“ checkUser.access_token”并且它不是未定义的?

此外,不建议在本地存储身份验证令牌。

  

浏览器本地存储(或会话存储)不安全。任何数据   存储在那里可能容易受到跨站点脚本的攻击。如果攻击者   窃取令牌,他们就可以访问您的API并向其发出请求。

通常在处理SPA时会在内存中使用。 Cookies也是一个有一些限制和注意点的选项。如果您使用node.js / express作为后端,我建议您使用https://github.com/expressjs/session,因为它以安全的方式设置会话访问令牌非常有帮助。

关于商店令牌,我建议阅读:https://auth0.com/docs/security/store-tokens

答案 1 :(得分:0)

您必须先等待loginUser才能尝试访问令牌

this.api.loginUser(user).subscribe(() => {
    this.api.isUserLoggedIn.subscribe( (val) => {
      this.loggedIn = val;
      this.route.navigate(['/dashboard']);
    });
});

说实话,我什至看不到订阅isUserLoggedIn的意义。相反,您可以使用loginUser方法中返回的值

this.api.loginUser(user).subscribe((val) => {
   this.loggedIn = val;
   if (val) {
      this.route.navigate(['/dashboard']);
   }
});
相关问题