我正在使用JWT
令牌进行身份验证并将其存储在本地存储中,现在想在其中添加CSRF
令牌,是否可以仅以角度激活CSRF
?
随着JWT令牌的生成,是否可以随机生成CSRF
并将其存储?
我正在尝试以下操作
authentication.service.ts
import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Observable } from 'rxjs/Observable';
import { map } from 'rxjs/operators/map';
import { Router } from '@angular/router';
export interface UserDetails {
_id: string;
email: string;
name: string;
exp: number;
iat: number;
}
interface TokenResponse {
token: string;
}
export interface TokenPayload {
email: string;
password: string;
name?: string;
}
@Injectable()
export class AuthenticationService {
private token: string;
constructor(private http: HttpClient, private router: Router) {}
private saveToken(token: string): void {
localStorage.setItem('mean-token', token);
this.token = token;
}
private getToken(): string {
if (!this.token) {
this.token = localStorage.getItem('mean-token');
}
return this.token;
}
public getUserDetails(): UserDetails {
const token = this.getToken();
let payload;
if (token) {
payload = token.split('.')[1];
payload = window.atob(payload);
return JSON.parse(payload);
} else {
return null;
}
}
public isLoggedIn(): boolean {
const user = this.getUserDetails();
if (user) {
return user.exp > Date.now() / 1000;
} else {
return false;
}
}
private request(method: 'post'|'get', type: 'login'|'register'|'profile', user?: TokenPayload): Observable<any> {
let base;
if (method === 'post') {
base = this.http.post(`/api/${type}`, user);
} else {
base = this.http.get(`/api/${type}`, { headers: { Authorization: `Bearer ${this.getToken()}` }});
}
const request = base.pipe(
map((data: TokenResponse) => {
if (data.token) {
this.saveToken(data.token);
}
return data;
})
);
return request;
}
public register(user: TokenPayload): Observable<any> {
return this.request('post', 'register', user);
}
public login(user: TokenPayload): Observable<any> {
return this.request('post', 'login', user);
}
public profile(): Observable<any> {
return this.request('get', 'profile');
}
public logout(): void {
this.token = '';
window.localStorage.removeItem('mean-token');
this.router.navigateByUrl('/');
}
}
auth.interceptor.ts
import { Injectable, Injector } from '@angular/core';
import { HttpInterceptor, HttpEvent, HttpRequest, HttpHandler, HttpXsrfTokenExtractor } from '@angular/common/http';
import { Observable } from 'rxjs/Observable';
@Injectable()
export class HttpXsrfInterceptor implements HttpInterceptor {
constructor(private tokenExtractor: HttpXsrfTokenExtractor) {
}
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
const headerName = 'X-XSRF-TOKEN';
let token = this.tokenExtractor.getToken() as string;
if (token !== null && !req.headers.has(headerName)) {
req = req.clone({ headers: req.headers.set(headerName, token) });
}
return next.handle(req);
}
}
app.module.ts
import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { HttpClientModule, HttpClientXsrfModule, HTTP_INTERCEPTORS } from '@angular/common/http';
import { FormsModule } from '@angular/forms';
import { RouterModule, Routes } from '@angular/router';
import { AppComponent } from './app.component';
import { ProfileComponent } from './profile/profile.component';
import { LoginComponent } from './login/login.component';
import { RegisterComponent } from './register/register.component';
import { HomeComponent } from './home/home.component';
import { AuthenticationService } from './authentication.service';
import { AuthGuardService } from './auth-guard.service';
import { HttpXsrfInterceptor } from './auth.interceptor';
const routes: Routes = [
{ path: '', component: HomeComponent },
{ path: 'login', component: LoginComponent },
{ path: 'register', component: RegisterComponent },
{ path: 'profile', component: ProfileComponent, canActivate: [AuthGuardService] }
];
@NgModule({
declarations: [
AppComponent,
ProfileComponent,
LoginComponent,
RegisterComponent,
HomeComponent
],
imports: [
BrowserModule,
FormsModule,
HttpClientModule,
HttpClientXsrfModule.withOptions({
cookieName: 'My-Xsrf-Cookie',
headerName: 'My-Xsrf-Header'
}),
RouterModule.forRoot(routes),
],
providers: [
{ provide: HTTP_INTERCEPTORS, useClass: HttpXsrfInterceptor, multi: true },
AuthenticationService,
AuthGuardService
],
bootstrap: [AppComponent]
})
export class AppModule { }