Async authguard в угловых 6 - PullRequest
0 голосов
/ 05 июня 2018

Я хотел бы предоставить проверку подлинности на стороне сервера, прежде чем дать доступ к определенному маршруту в angular.

У меня есть AuthGuard, который реализует CanActivate, и сервис AuthService.У authService уже есть private loggedIn: BehaviorSubject<boolean> = new BehaviorSubject<boolean>(null); , на которые подписываются представления, чтобы узнать, вошел ли пользователь в систему или нет.Я действительно не знаю, если мой подход неверен, но, похоже, он не работает.

Это то, что я имею в auth.guard.ts:

canActivate(next: ActivatedRouteSnapshot, state: RouterStateSnapshot) : Observable<boolean> {
    return this.authService.isAuthenticated().map((isLoggedIn) => {
        if (isLoggedIn) {
            return true;
        } else {
            this.router.navigate(['/login']);
            return false;
        }
    })
}

, и этоauth.service.ts:

    @Injectable()
export class AuthService {
    private loggedIn: BehaviorSubject<boolean> = new BehaviorSubject<boolean>(null);

    constructor(
        private router: Router,
        private http: HttpClient
    ) {

    }

    get isLoggedIn() {
        return this.loggedIn.asObservable();
    }

    isAuthenticated() : Observable<boolean> {
        const headers = new HttpHeaders().set("X-Requested-With", "XMLHttpRequest");

        return this.http.get('/user', {headers: headers}).map(
            response => {
                if (response['username']) {
                    this.loggedIn.next(true);
                    return true;
                } else {
                    return false;
                }
            }
        )
    }

Ответы [ 2 ]

0 голосов
/ 16 июля 2018

Вот подход для RXJS6, добавлена ​​переменная _isAuthenticated в сервисе аутентификации для запроса состояния сервера именно тогда, когда флаг отключен.Я надеюсь, что это поможет другим.

Убедитесь, что canActivate возвращает простой логический или наблюдаемый.Обработчик маршрута подписывается на данную наблюдаемую информацию и реагирует на первое логическое значение, поступающее из потока создания ценности.

auth.guard.ts

import { Injectable } from '@angular/core';
import { Router, CanActivate } from '@angular/router';

import { Observable } from 'rxjs/';
import { map, finalize } from 'rxjs/operators';
import { DataService } from '../data.service';
import { AuthenticationService } from './authentication.service';

@Injectable()
export class AuthenticationGuard implements CanActivate {

  constructor(private router: Router,
              private dataService: DataService,
              private authenticationService: AuthenticationService) { }

  canActivate(): any {
    const isAuthenticated = this.authenticationService.isAuthenticated();

    // All good
    if ( isAuthenticated ) {
      return true;

    // Hmm, let's verify the user first
    } else {
      return this.authenticationService.isSessionAlive()
        .pipe(
          map(res => {

            // No valid session; let's move to the login page
            if ( res === false ) {
              this.router.navigate(['/login'], { replaceUrl: true });
            }

            return res;
          })
        );
    }
  }

}

auth.service.ts (I'mиспользуя rxjs 6)

import { Injectable } from '@angular/core';
import { Observable } from 'rxjs';
import { DataService } from '@app/core';

@Injectable()
export class AuthenticationService {

  private _isAuthenticated = false;

  constructor(
    private dataService: DataService
  ) {}

  isAuthenticated(): boolean {
    return this._isAuthenticated;
  }

  isSessionAlive(): Observable<any> {
    return Observable.create((observer) => {
      this.dataService.SessionIsAlive()
        .subscribe((res) => {
          this._isAuthenticated = true;
          observer.next(res.success); // your server response
        }, (err) => {
          this._isAuthenticated = false;
          observer.next(false);
          // observer.error(err); // won't work here you need to use next
        });
    });
  }
}
0 голосов
/ 05 июня 2018

Вы можете сделать несколько изменений следующим образом:

Ваш сервис,

@Injectable()
export class LoginService {
  public isUserLoggedIn: boolean;
  constructor(
    private router: Router,
    private auth: AuthService) {
    this.isUserLoggedIn = false;
  }

  public loginService(data): void {
    this.auth.isAuthentication(data)
    .subscribe((response) => {
      if (response) {
        this.isUserLoggedIn = true;             
      }else {
        this.router.navigate(['login']);
      }
    });
  }

 public getUserLoggedIn() {
   return this.isUserLoggedIn;
}

, а затем

@Injectable()
export class AuthGuard implements CanActivate {
  constructor(private login: LoginService) { }
  canActivate(
    next: ActivatedRouteSnapshot,
    state: RouterStateSnapshot): Observable<boolean> | Promise<boolean> | boolean {
    return this.login.getUserLoggedIn();
  }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...