Я пытаюсь создать охрану маршрута, который поддерживает безопасность некоторых загруженных модулей, у меня есть служба аутентификации с BehaviorSubject, которая содержит текущего пользователя и токен JWT
Когда я вызываю охрану, он сначала получаетзначение по умолчанию для текущего пользователя и только при попытке отправить его позволяет пользователю добраться до маршрута.
auth.service.ts:
import { Injectable } from '@angular/core';
import { HttpClient, HttpErrorResponse, HttpResponse, HttpHeaders } from '@angular/common/http';
import { Observable, BehaviorSubject } from 'rxjs';
import { map, skip, takeLast, last } from 'rxjs/operators';
import { User } from '../shared/user';
import { environment } from '../../environments/environment';
@Injectable()
export class AuthService {
private loginUserToken: BehaviorSubject<string>;
private currentUser: BehaviorSubject<User>;
constructor(private http: HttpClient) {
// service init
this.loginUserToken = new BehaviorSubject(undefined);
this.currentUser = new BehaviorSubject(undefined);
this.loginUserToken.next(this.getTokenFromLocalStorege());
if (this.loginUserToken.value != null) {
this.getUserFromToken();
}
}
/**
* getLoginUser
*/
public getLoginUserAsObservable() {
return this.currentUser.asObservable();
}
public getLoginUserTokenAsObservable() {
return this.loginUserToken.asObservable();
}
public async login(user: User): Promise<any> {
// tslint:disable-next-line:no-shadowed-variable
return new Promise<any>(async (resolve: any, reject: any) => {
try {
const result: any = await this.http.post(`${environment.server}/api/auth/login`, user).toPromise();
if (result.massageCode === 1) {
reject('bedUsername');
} else if (result.massageCode === 2) {
reject('bed password');
} else {
this.loginUserToken.next(result.token);
this.getUserFromToken();
this.saveTokenToLocalStorege(result.token);
resolve();
}
} catch (error) {
reject('error');
}
});
}
public getUserFromToken(): void {
const headers = new HttpHeaders({
'x-access-token': this.loginUserToken.value
});
this.http.get(`${environment.server}/api/auth/userFromToken`, { headers }).toPromise()
.then((data: User) => {
this.currentUser.next(data);
})
.catch((error) => {
console.log(error);
});
}
public isLogin(): Promise<boolean> {
return new Promise((resolve, reject) => {
this.currentUser.asObservable()
.subscribe((data) => {
if (data) {
resolve(true);
} else {
resolve(false);
}
}).unsubscribe();
});
}
public saveTokenToLocalStorege(token: string): void {
localStorage.setItem('chanToken', token);
}
public getTokenFromLocalStorege(): string {
return localStorage.getItem('chanToken');
}
public removeTokenFromLocalStrege(): void {
localStorage.removeItem('chanToken');
}
}
auth.guaed.ts:
import { Injectable } from '@angular/core';
import { CanActivate, CanLoad, ActivatedRouteSnapshot, RouterStateSnapshot, Router } from '@angular/router';
import { Observable } from 'rxjs';
import { AuthService } from '../auth.service';
import { Route } from '@angular/compiler/src/core';
import { last, map } from 'rxjs/operators';
@Injectable()
export class AuthGuard implements CanLoad {
constructor(private authSerivce: AuthService, private router: Router) { }
canLoad(route: Route): boolean | Observable<boolean> | Promise<boolean> {
console.log('use gruad');
return this.authSerivce.isLogin();
}
}