我正在嘗試在nodejs中構建一個簡單的web令牌protected api。我一直在關注本教程authenticate a node js api with json web tokens,並一直在我的應用中實施這些步驟。我現在有一個允許我獲取/發佈/放置/刪除的api運行,併爲用戶生成webtoken並以純文本形式顯示它(用於開發目的)。我正在使用節點restful api的,但我有一些麻煩理解如何實際驗證客戶端是否發送webtoken在他們的請求,允許這些get/post/put/delete請求之前。使用Json Web令牌的Node-Restful
這是我的路由器。在那裏我定義允許的請求:
const express = require('express')
const router = express.Router()
// Models - Load models here
var userModel = require('./models/User')
// Controllers - Load controllers here
const userController = require('./controllers/userController')
// Routes - Define routes here
router.post('api/authenticate', userController.authenticate) //Route that generates the webkey and shows it in the response
// Configure the endpoint that node-restful will expose. Here I want to first check if the user is sending his or her api key. Before allowing these methods.
userModel.methods(['get', 'put', 'post', 'delete'])
userModel.register(router, '/api/users')
// Export the router object
module.exports = router
這裏是我的userController生成令牌。
// Dependencies
const User = require('../models/User')
const jwt = require('jsonwebtoken')
const config = require('../config.js')
module.exports = {
authenticate: function(req, res, next) {
// find the user
User.findOne({username: req.body.name}, function(err, user) {
if (err) throw err;
if (!user) {
res.json({
success: false,
message: 'Authentication failed. User not found.' });
} else if (user) {
// check if password matches
if (user.password != req.body.password) {
res.json({
success: false,
message: 'Authentication failed. Wrong password.' });
} else {
// if user is found and password is right
// create a token
var token = jwt.sign(user, config.secret, {
expiresIn: 60*60*24 // expires in 24 hours
});
// return the information including token as JSON
res.json({
success: true,
message: 'Enjoy your token!',
token: token
});
}
}
})
}
}
這裏是我的用戶模型。
// Dependencies
const restful = require('node-restful')
const mongoose = restful.mongoose
// Schema
const userSchema = new mongoose.Schema({
username: String,
password: String,
email: String
})
// Return the model as a restful model to allow it being used as a route.
module.exports = restful.model('User', userSchema)
是否有某種方式可以保護這些端點,使用與我目前使用的相同的語法來公開它們?我相信我會定義方法之前,請檢查網絡令牌:
userModel.methods(['get', 'put', 'post', 'delete'])
userModel.register(router, '/api/users')
如果我只是刪除方法本身,用戶將無法獲得頁面,並顯示一個:「不能GET/api/users「錯誤。如果我想顯示自定義錯誤怎麼辦?例如:「沒有提供Web令牌,註冊認證」等等?任何幫助深表感謝。先謝謝你。
我現在有一個函數可以在服務頁面之前檢查令牌。它似乎現在工作。目前,我在postman中手動傳遞令牌作爲頭文件:x-access-token。如何在生成時捕獲令牌並自動讓客戶端在未來的請求中發送令牌?這是檢查令牌和受保護路由的函數。
太好了。我在等待任何答案的同時繼續工作,並完成了此步驟。我現在可以生成令牌並使用郵遞員傳遞給我創建的安全路線。它的工作原理非常完美,但我很努力地理解我將如何在客戶端保存令牌並在每個請求上傳遞該令牌。我仍然生成令牌,如上所述。我可以通過手動將它作爲x-access-token傳遞給我的頭部來驗證令牌,但我該如何自動執行此操作?
更新
這裏是檢查利用該功能的令牌和一個受保護的路由功能:
//路線 - 這裏定義路線
function getToken(req, res, next) {
var token = req.body.token || req.query.token || req.headers['x-access-token'];
// decode token
if (token) {
// verifies secret and checks exp
jwt.verify(token, config.secret, function(err, decoded) {
if (err) {
return res.json({ success: false, message: 'Failed to authenticate token.' });
} else {
// if everything is good, save to request for use in other routes
req.decoded = decoded;
console.log(decoded);
next();
}
});
} else {
// if there is no token
// return an error
return res.status(403).send({
success: false,
message: 'No token provided.'
});
}
}
router.get('/entries', getToken, entryController.get)
我發現這個問題save-token-in-local-storage-using-node解決了最後一塊難題。
太好了。我在等待任何答案的同時繼續工作,並完成了此步驟。我現在可以生成令牌並使用郵遞員傳遞給我創建的安全路線。它的工作原理非常完美,但我很努力地理解我將如何在客戶端保存令牌並在每個請求上傳遞該令牌。我仍然生成令牌,如上所述。我可以通過手動將它作爲x-access-token傳遞給我的頭部來驗證令牌,但我該如何自動執行此操作?檢查我的更新問題的代碼。 – n0rd
查看已更新的答案。 – Tolsee
太棒了。我想知道這是否是我應該做的。所以我需要將這個標記保存爲一個cookie,這應該不是我目前在我的令牌生成中使用的json響應。它是否正確? – n0rd