Estoy tratando de hacer un inicio de sesión muy simple en mi aplicación Ionic 4. Cuando un usuario inicia sesión, configuro un token en el almacenamiento. Esto está funcionando.

Estoy usando un Auth Guard para verificar una página en la aplicación, por lo que si el token está configurado en el almacenamiento, el usuario puede ver la página. De lo contrario, se les redirige a la página de inicio de sesión.

Mi problema es que estoy completamente atrapado en el infierno asincrónico; Simplemente no puedo entenderlo. Estoy tratando de hacer una verificación simple: ¿el token está almacenado o no? si es así, devuelva verdadero, si no, devuelva falso.

El problema que estoy experimentando es que, incluso después de iniciar sesión con éxito y almacenar el token, cuando intento acceder a la página restringida, todavía me redirigen a la página de inicio de sesión; Supongo que se debe a que no utilizo correctamente async en mi guardia.

¿Qué estoy haciendo mal?

import { Injectable } from '@angular/core';
import { Router, CanActivate, ActivatedRouteSnapshot } from '@angular/router';
import { Storage } from '@ionic/storage';

@Injectable({
    providedIn: 'root'
})
export class AuthGuard implements CanActivate {

    authenticated: boolean;

    constructor(
        private router: Router,
        private storage: Storage
    ) {
        this.getToken();
    }

    canActivate(route: ActivatedRouteSnapshot): boolean {

        if (this.authenticated) {
            return true;
        }

        this.router.navigate(['/login']);
        return false;
    }

    async getToken() {
        await this.storage.get('token').then(res => {
            if (res) {
                this.authenticated = true;
            } else {
                this.authenticated = false;
            }
        });
    }
}
1
timgavin 5 oct. 2019 a las 05:06

1 respuesta

La mejor respuesta

Creo que el problema es que está comprobando el almacenamiento en el constructor y cuando se inicializó el servicio, se desconectó, así que this.authenticated siempre es false. Lo que debe hacer en su lugar es hacer esta verificación cada vez que navegue por la ruta.

Prueba este código

import { Injectable } from '@angular/core';
import { Router, CanActivate, ActivatedRouteSnapshot } from '@angular/router';
import { Storage } from '@ionic/storage';

@Injectable({
  providedIn: 'root'
})
export class AuthGuard implements CanActivate {

  constructor(
    private router: Router,
    private storage: Storage
  ) {
  }

  canActivate(route: ActivatedRouteSnapshot): Promise<boolean> {

    return this.storage.get('token').then(res => {
      if (res) {
        return true;
      }

      this.router.navigate(['/login']);
      return false;
    });
  }
}
6
Archit Garg 5 oct. 2019 a las 04:24