2017-12-12 9 views
1

Die Dokumentation und Beispiele rund um die Verwendung von auth0 mit eckigen 2 Hash-Routing (z. B. http://somdomain.com/#/someroute) ist ziemlich spärlich und veraltet.Wie richte ich Auth0 mit Angular 2 useHash ein: true?

Es gibt mehrere Probleme Adresse:

  1. auth0 librarylistens für eine Änderung der URL-Fragment. Leider schluckt angular die URL-Fragmentänderung, weil es denkt, dass es sich um eine Route handelt.

  2. Das URL-Fragment beginnt mit #access_token=... und Winkel wirft einen Fehler, da access_token nicht als Route registriert ist.

  3. Auch wenn Sie eine Route access_token registrieren, möchten Sie sie nicht als Route anzeigen, daher müssen Sie die Navigation abbrechen.

Was sind alles, was man tun muss, um es tatsächlich einzurichten?

Antwort

0

Zuerst werden Sie brauchen auth0-lock

npm install --save auth0-lock 

Als Nächstes werden Sie einen Authentifizierungsdienst benötigen. Der folgende Authentifizierungsdienst implementiert login() und .

Bevor Sie diese Methoden aufrufen, stellen Sie sicher, dass Sie den Dienst mit registerAuthenticationWithHashHandler konfigurieren. Dies kann in App.Component.ts

// AuthService.ts 
import { environment } from './../environments/environment'; 
import { Injectable } from '@angular/core'; 
import { Router, RouterEvent } from '@angular/router'; 
import 'rxjs/add/operator/filter'; 
import 'rxjs/add/operator/take'; 
import { AuthCallbackComponent } from './../app/auth-callback/auth-callback.component'; 
import { AuthenticationCallbackActivateGuard } from '../app/auth-callback/auth-callback-activate-guard'; 
import Auth0Lock from 'auth0-lock'; 

@Injectable() 
export class AuthService { 

    private lock: Auth0Lock; 

    constructor(public router: Router) { 

    this.lock = new Auth0Lock(
     environment.auth0.clientID, 
     environment.auth0.domain, 
     { 
     oidcConformant: true, 
     autoclose: true, 
     auth: { 
      autoParseHash: false, 
      redirectUrl: environment.auth0.redirectUri, 
      responseType: 'token id_token', 
      audience: environment.auth0.audience, 
      params: { 
      scope: 'openid' 
      } 
     } 
     } 
    ); 

    } 

    public login(): void { 
    this.lock.show(); 
    } 

    // Call this method in app.component.ts 
    // if using path-based routing 
    public registerAuthenticationHandler(): void { 
    this.lock.on('authenticated', (authResult) => { 
     if (authResult && authResult.accessToken && authResult.idToken) { 
     this.setSession(authResult); 
     this.router.navigate(['/']); 
     } 
    }); 
    this.lock.on('authorization_error', (err) => { 
     this.router.navigate(['/']); 
     console.log(err); 
     alert(`Error: ${err.error}. Check the console for further details.`); 
    }); 
    } 

    // Call this method in app.component.ts 
    // if using hash-based routing 
    public registerAuthenticationWithHashHandler(): void { 

    this.registerAuthenticationHandler(); 
    this.workaroundHashAccessTokenRoute(); 

    this.router.events.take(1).subscribe(event => { 

     if (!(event instanceof RouterEvent)) { 
     return; 
     } 

     this.lock.resumeAuth(window.location.hash, (err, authResult) => { 
     if (authResult && authResult.idToken) { 
      this.lock.emit('authenticated', authResult); 
     } 

     if (authResult && authResult.error) { 
      this.lock.emit('authorization_error', authResult); 
     } 
     }); 

    }); 
    } 

    private workaroundHashAccessTokenRoute() { 

    /* workaround useHash:true with angular2 router 
    ** Angular mistakenly thinks "#access_token" is a route 
    ** and we oblige by creating a fake route that can never be activated 
    */ 
    const routes = this.router.config; 
    routes.splice(0, 0, { 
     path: 'access_token', 
     component: AuthCallbackComponent, 
     canActivate: [AuthenticationCallbackActivateGuard] 
    }); 
    this.router.resetConfig(routes); 
    } 

    private setSession(authResult): void { 
    // Set the time that the access token will expire at 
    const expiresAt = JSON.stringify((authResult.expiresIn * 1000) + new Date().getTime()); 
    localStorage.setItem('access_token', authResult.accessToken); 
    localStorage.setItem('id_token', authResult.idToken); 
    localStorage.setItem('expires_at', expiresAt); 
    } 

    public logout(): void { 
    // Remove tokens and expiry time from localStorage 
    localStorage.removeItem('access_token'); 
    localStorage.removeItem('id_token'); 
    localStorage.removeItem('expires_at'); 
    // Go back to the home route 
    this.router.navigate(['/']); 
    } 

    public isAuthenticated(): boolean { 
    // Check whether the current time is past the 
    // access token's expiry time 
    const expiresAt = JSON.parse(localStorage.getItem('expires_at')); 
    return new Date().getTime() < expiresAt; 
    } 
} 

erfolgen Die registerAuthenticationWithHashHandler eine Dummy-Route erstellt namens „access_token“, und es wird durch eine Regel geschützt AuthenticationCallbackActivateGuard genannt, die immer false zurück.

// auth-callback-activate-guard.ts 
import { Injectable } from '@angular/core'; 
import { CanActivate } from '@angular/router'; 
import { Location } from '@angular/common'; 
import { Router } from '@angular/router'; 

@Injectable() 
export class AuthenticationCallbackActivateGuard implements CanActivate { 

    constructor(private router: Router, private location: Location) { } 

    canActivate() { 
    return false; 
    } 
} 

Hier sind die Teile, die Sie für die Dummy-Routen benötigen:

// auth-callback/auth-callback.components.ts 
import { Component, OnInit } from '@angular/core'; 

@Component({ 
    selector: 'app-auth-callback', 
    templateUrl: './auth-callback.component.html', 
    styleUrls: ['./auth-callback.component.scss'] 
}) 
export class AuthCallbackComponent implements OnInit { 

    constructor() { } 

    ngOnInit() { 
    } 

} 

Registrieren von Authentifizierungsdienst in App.Component.ts

// app/app.component.ts 
import { Component } from '@angular/core'; 
import { AuthService } from '../services/auth.service'; 

@Component({ 
    selector: 'app-root', 
    templateUrl: './app.component.html', 
    styleUrls: ['./app.component.css'] 
}) 
export class AppComponent { 
    title = 'app'; 

    constructor(private auth: AuthService) { 
    auth.registerAuthenticationWithHashHandler(); 
    } 
} 
Verwandte Themen