客户端和node端在环境变量中声明一个秘钥:SECRET=xxxx,注意这个是保密的;
客户端发起请求时,将当前时间戳(timestamp)和
SECRET 通过某种算法,生成一个
signature ,请求时带上
timestamp 和
signature ;node接收到请求,获得
timestamp 和
signature ,将
timestamp 和秘钥用同样的算法再生成一次签名
_signature对比客户端请求的
signature 和node用同样的算法生成的
_signature ,如果一致就表示通过,否则鉴权失败。具体的步骤:
客户端对axios进行一层封装:
import axios from 'axios'
import sha256 from 'crypto-js/sha256'
import Base64 from 'crypto-js/enc-base64'
// 加密算法,需安装crypto-js
function crypto (str) {
const _sign = sha256(str)
return encodeURIComponent(Base64.stringify(_sign))
}const SECRET = process.env.SECRET
const options = {
headers: { 'X-Requested-With': 'XMLHttpRequest' },
timeout: 30000,
baseURL: '/api'
}
// The server-side needs a full url to works
if (process.server) {
options.baseURL = `http://${process.env.HOST || 'localhost'}:${process.env.PORT || 3000}/api`
options.withCredentials = true
}
const instance = axios.create(options)
// 对axios的每一个请求都做一个处理,携带上签名和timestamp
instance.interceptors.request.use(
config => {
const timestamp = new Date().getTime()
const param = `timestamp=${timestamp}&secret=${SECRET}`
const sign = crypto(param)
config.params = Object.assign({}, config.params, { timestamp, sign })
return config
}
)
export default instance
接着,在server端写一个鉴权的中间件,
/server/middleware/verify.js :
const sha256 = require('crypto-js/sha256')
const Base64 = require('crypto-js/enc-base64')function crypto (str) {
const _sign = sha256(str)
return encodeURIComponent(Base64.stringify(_sign))
}
// 使用和客户端相同的一个秘钥
const SECRET = process.env.SECRET
function verifyMiddleware (req, res, next) {
const { sign, timestamp } = req.query
// 加密算法与请求时的一致
const _sign = crypto(`timestamp=${timestamp}&secret=${SECRET}`)
if (_sign === sign) {
next()
} else {
res.status(401).send({










