Webアプリケーションの開発を開始し、フロントエンドフレームワークとしてAngular 2を選択しました。私は現在、ユーザー認証のためにAuth0を試しています。 問題は次のとおりです。 ランディングページのログイン - >リダイレクト機能を実装しようとしています。ウェブサイトを開いた直後に、ユーザーのトークンがlocalStorage
にあるかどうかを確認して、ログインウィジェットを表示するか、ホームページにリダイレクトするかのいずれかを選択する必要があります。しかし、私はこの非常に厄介なバグに遭遇しました:Auth0とAngular 2:ログインウィジェットを使用したログインとルーティングに失敗しました
私がログインすると、ページがリフレッシュされ、再びウィジェットが表示されます。何らかの理由でtokenNotExpired()
がfalse
を返します。同じ資格情報で再度ログインするには - ページが更新され、ログインウィジェットが消え、ログにtokenNotExpired()
が返ってきて、今度はtrue
が返されますが、私のリダイレクトはまだ動作しません。私が今自分のベースアドレスhttp://localhost:4200
を入力するだけで、私はhome
に首尾よくリダイレクトされ、tokenNotExpired()
はtrue
を返します。
私はそれをデバッグしようとしましたが、何の不運もありません - どこが失敗しているのかわかりません。
私の経験が不足しているので、私はリダイレクト機能をコーディングする方法には基本的に問題があると確信しています。私は非常に親切に助けを感謝し、これにしばらく座っている。
私は冗長部分を省略したコードの抜粋を含めています。 main.tsにブートストラップすることでAuthサービスをグローバルに注入しています。
app.routes.ts:
import {provideRouter, RouterConfig} from "@angular/router";
import {AuthGuard} from './secure/auth.guard';
import {AdminGuard} from "./secure/admin.guard";
import {UserHomeComponent} from "./main/user-cpl/user-home.component";
import {AdminHomeComponent} from "./main/admin-cpl/admin-home.component";
import {LoginPageComponent} from "./login/login-page.component";
const APP_ROUTES: RouterConfig = [
{ path: 'home', canActivate: [AuthGuard],
children: [
{ path: '', component: UserHomeComponent },
{ path: 'admin', component: AdminHomeComponent, canActivate: [AdminGuard] },
] },
{ path: 'login', component: LoginPageComponent },
{ path: '', redirectTo: 'home', pathMatch: 'full' },
{ path: '**', redirectTo: 'home', pathMatch: 'full' }
];
export const APP_ROUTES_PROVIDER = [
provideRouter(APP_ROUTES)
];
ログイン-page.component.ts:
import {Component, OnInit} from '@angular/core';
import {ROUTER_DIRECTIVES, Router} from '@angular/router';
import {Auth} from '../secure/auth.service';
@Component({
moduleId: module.id,
selector: 'login-page-component',
template: `
<router-outlet></router-outlet>
`,
directives: [ROUTER_DIRECTIVES]
})
export class LoginPageComponent implements OnInit {
constructor(private auth: Auth, private router: Router) {
}
ngOnInit():any {
console.log('LOGGED IN - ' + this.auth.loggedIn());
if (this.auth.loggedIn()) {
if (this.auth.isAdmin()) {
this.router.navigate(['/home/admin']);
} else if (!this.auth.isAdmin()) {
this.router.navigate(['/home']);
}
} else {
this.auth.login();
}
}
}
auth.service.ts:
import {Injectable} from '@angular/core';
import {tokenNotExpired} from 'angular2-jwt';
declare var Auth0Lock: any;
@Injectable()
export class Auth {
// Configure Auth0
lock = new Auth0Lock('omitted', 'omitted', {
closable: false
});
//Store profile object in auth class
userProfile: any;
constructor() {
// Set userProfile attribute if already saved profile
this.userProfile = JSON.parse(localStorage.getItem('profile'));
// Add callback for lock `authenticated` event
this.lock.on("authenticated", (authResult) => {
localStorage.setItem('id_token', authResult.idToken);
// Fetch profile information
this.lock.getProfile(authResult.idToken, (error, profile) => {
if (error) {
// Handle error
alert(error);
return;
}
localStorage.setItem('profile', JSON.stringify(profile));
this.userProfile = profile;
});
});
}
login() {
this.lock.show({
callbackUrl: 'http://localhost:4200/home'
});
}
logout() {
localStorage.removeItem('profile');
localStorage.removeItem('id_token');
this.userProfile = undefined;
}
loggedIn() {
return tokenNotExpired();
}
isAdmin() {
return this.userProfile && this.userProfile.app_metadata
&& this.userProfile.app_metadata.roles
&& this.userProfile.app_metadata.roles.indexOf('admin') > -1;
}
}
auth.guard.ts:
import {Injectable} from '@angular/core';
import {Router, ActivatedRouteSnapshot, RouterStateSnapshot} from '@angular/router';
import {CanActivate} from '@angular/router';
import {Auth} from './auth.service';
@Injectable()
export class AuthGuard implements CanActivate {
constructor(private auth: Auth, private router: Router) {
}
canActivate(next: ActivatedRouteSnapshot, state: RouterStateSnapshot) {
if (this.auth.loggedIn()) {
console.log('AUTH GUARD PASSED');
return true;
} else {
console.log('BLOCKED BY AUTH GUARD');
this.router.navigate(['/login']);
return false;
}
}
}
admin.guard.ts:それは、単一のページのアプリですので、あなたが設定でredirect: false
を設定する必要があります
import {Injectable} from '@angular/core';
import {Router, ActivatedRouteSnapshot, RouterStateSnapshot} from '@angular/router';
import {CanActivate} from '@angular/router';
import {Auth} from './auth.service';
@Injectable()
export class AdminGuard implements CanActivate {
constructor(private auth: Auth, private router: Router) {}
canActivate(next: ActivatedRouteSnapshot, state: RouterStateSnapshot) {
if (this.auth.isAdmin()) {
return true;
} else {
return false;
}
}
}
'auth.login()であなたの属性は' callbackURL'でなければなりません。 OAuthでは大文字と小文字が区別されます。 – ghg565
@ ghg565はい、私はそれを変更しましたが、影響はありません。また、どこでもリダイレクトするためにcallbackURLを使用せず、代わりにログインページに戻り、最初に資格情報を保存しないことに気付きました。 – praktikantas