【发布时间】:2020-10-20 06:58:18
【问题描述】:
我正在尝试在登录后将数据存储到 /profile。但是,我在登录后一直在控制台中收到这 2 个错误。
"VM276:1 GET http://localhost:4200/user/profile 401 (未授权)" 和“HttpErrorResponse {headers: HttpHeaders, status: 401, statusText: "Unauthorized"”。
由于我遵循不同的教程来解决这个问题,所以我知道我在令牌代码上犯了一些错误,我只是不知道如何修复它。我要感谢任何花时间提供帮助的人!这是我的 authentication.service.ts
import { Injectable } from '@angular/core';
import {HttpClient} from "@angular/common/http";
import {Observable, of} from 'rxjs';
import { map } from 'rxjs/operators';
import {Router} from '@angular/router';
export interface UserDetails{
username: string
email: string
password: string
exp: number
iat: number
}
interface TokenResponse{
token: string
}
export interface TokenPayload{
username: string
email: string
password: string
}
@Injectable({
providedIn: 'root'
})
export class AuthenticationService {
private token: string
constructor(private http: HttpClient, private router: Router) {}
private saveToken(token: string): void{
localStorage.setItem('usertoken', token)
this.token = token
}
private getToken(): string{
if(!this.token){
this.token = localStorage.getItem('usertoken')
}
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
}
}
public login(user: TokenPayload): Observable<any>{
const base = this.http.post('/user/login', user)
const request = base.pipe(
map((data: TokenResponse) => {
if(data.token){
this.saveToken(data.token)
}return data
})
)
return request
}
public register(user: TokenPayload) : Observable<any>{
const base = this.http.post('/user/register', user)
const request = base.pipe(
map((data: TokenResponse) => {
if(data.token){
this.saveToken(data.token)
}
return data
})
)
return request
}
public profile(): Observable<any>{
return this.http.get('/user/profile',{
headers: {Authorization: `${this.getToken()}`}
})
}
public logout(): void{
this.token = ''
window.localStorage.removeItem('usertoken')
this.router.navigateByUrl('/')
}
}
这是我的 profile.component.ts
export class ProfileComponent implements OnInit {
details: UserDetails
constructor(private auth: AuthenticationService) {}
ngOnInit() {
this.auth.profile().subscribe(
user => {
this.details = user
},
err => {
console.error(err)
}
)
}
}
这是我的 auth.js
const jwt = require("jsonwebtoken");
module.exports = function(req, res, next) {
const token = req.header("token");
if (!token) return res.status(401).json({ message: "Auth Error" });
try {
const decoded = jwt.verify(token, "randomString");
req.user = decoded.user;
next();
} catch (e) {
console.error(e);
res.status(500).send({ message: "Invalid Token" });
}
};
这是我的 /routes/user.js
// Filename : user.js
const express = require("express");
const {check, validationResult} = require("express-validator");
const bcrypt = require("bcryptjs");
const jwt = require("jsonwebtoken");
const router = express.Router();
const auth = require("../middleware/auth");
const User = require("../model/User");
/**
* @method - POST
* @param - /signup
* @description - User SignUp
*/
router.post(
"/register",
[
check("username", "Please Enter a Valid Username")
.not()
.isEmpty(),
check("email", "Please enter a valid email").isEmail(),
check("password", "Please enter a valid password").isLength({
min: 6
})
],
async (req, res) => {
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).json({
errors: errors.array()
});
}
const {
username,
email,
password
} = req.body;
try {
let user = await User.findOne({
email
});
if (user) {
return res.status(400).json({
msg: "User Already Exists"
});
}
user = new User({
username,
email,
password
});
const salt = await bcrypt.genSalt(10);
user.password = await bcrypt.hash(password, salt);
await user.save();
const payload = {
user: {
id: user.id
}
};
jwt.sign(
payload,
"randomString", {
expiresIn: 10000
},
(err, token) => {
if (err) throw err;
res.status(200).json({
token
});
}
);
} catch (err) {
console.log(err.message);
res.status(500).send("Error in Saving");
}
}
);
router.post(
"/login",
[
check("email", "Please enter a valid email").isEmail(),
check("password", "Please enter a valid password").isLength({
min: 6
})
],
async (req, res) => {
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).json({
errors: errors.array()
});
}
const { email, password } = req.body;
try {
let user = await User.findOne({
email
});
if (!user)
return res.status(400).json({
message: "User Does Not Exist"
});
const isMatch = await bcrypt.compare(password, user.password);
if (!isMatch)
return res.status(400).json({
message: "Incorrect Password!"
});
const payload = {
user: {
id: user.id
}
};
jwt.sign(
payload,
"randomString",
{
expiresIn: 3600
},
(err, token) => {
if (err) throw err;
res.status(200).json({
token
});
}
);
} catch (e) {
console.error(e);
res.status(500).json({
message: "Server Error"
});
}
}
);
/**
* @method - POST
* @description - Get LoggedIn User
* @param - /user/me
*/
router.get("/profile", auth, async (req, res) => {
try {
// request.user is getting fetched from Middleware after token authentication
const user = await User.findById(req.user.id);
res.json(user);
} catch (e) {
res.send({ message: "Error in Fetching user" });
}
});
module.exports = router;
【问题讨论】: