谁来简单的介绍一下Nodejs下登录验证和权限的标准做法?
谁来简单的介绍一下Nodejs下登录验证和权限的标准做法?
我是一只小小小菜鸟,对于nodejs中的session和登录以及权限有不理解的地方,目前我登录这边是这么做的: 1.请求登录,验证用户名密码,通过后记录req的sessionid和用户名,权限,存成名值对放在全局变量中 2.在cookie中记录用户名,以后每次请求都判断sessionid和用户名、权限是否和存储的一致 3.30分钟内无操作删除req的sessionid和用户名、权限的名值对
我想问问,大家是怎么利用session、cookie、nodejs做登录和权限验证的? 求各位介绍一下自己的基本流程,说说大意即可
当然可以。下面我会介绍一个基于 Node.js 的典型登录验证和权限管理的标准做法,并提供一些示例代码。
基本概念
- Session:用于在服务器端存储用户会话信息。
- Cookie:客户端存储会话标识符(如 session ID),以便后续请求能够关联到同一个会话。
- 中间件:用于处理请求和响应的函数,可以在请求到达路由之前或之后执行特定的操作。
使用 Express 和 express-session
中间件
首先,你需要安装 express
和 express-session
:
npm install express express-session
示例代码
1. 设置 Session
const express = require('express');
const session = require('express-session');
const app = express();
app.use(session({
secret: 'your_secret_key', // 用于加密 session id 的密钥
resave: false,
saveUninitialized: true,
cookie: { maxAge: 30 * 60 * 1000 } // 30分钟
}));
app.get('/login', (req, res) => {
// 假设用户名和密码正确
req.session.user = {
username: 'testUser',
role: 'admin'
};
res.send('Login successful!');
});
app.get('/profile', (req, res) => {
if (req.session.user) {
res.send(`Welcome ${req.session.user.username}! Your role is ${req.session.user.role}.`);
} else {
res.redirect('/login');
}
});
app.listen(3000, () => console.log('Server running on port 3000'));
解释
-
设置 Session:使用
express-session
中间件来管理 session。secret
是用来加密 session ID 的密钥,确保安全性。maxAge
指定 session 的有效期。 -
登录逻辑:当用户访问
/login
路由时,我们假设用户名和密码是正确的,并将用户信息存储在req.session.user
中。然后重定向到其他页面。 -
权限检查:在需要权限检查的路由(如
/profile
)中,检查req.session.user
是否存在。如果存在,则显示用户信息;否则,重定向到登录页面。
总结
这种做法通过 express-session
来管理 session,利用 cookie 存储 session ID,并通过中间件在每个请求中自动加载 session 数据。这种方式比直接在全局变量中存储数据更安全和高效。
请参考 nodeclub 源码
谢谢,我看懂了
我没有看明白,请问有没有像J2EE 那样的过滤器或者Struts2那样的拦截器之类的东西来判断用户登录状态?
我跟你想的一样,就自己写了个,可以试试npm install rainbow
,仓库地址:https://github.com/mytharcher/rainbow
在Node.js中处理登录验证和权限管理时,通常使用中间件(如express-session
)来管理会话,并使用JWT(JSON Web Tokens)或基于Cookie的机制来处理用户身份验证和权限。下面是基于这些常用技术的一个简单标准做法。
基本流程
- 登录请求:客户端发送包含用户名和密码的登录请求。
- 验证用户:服务器端验证用户名和密码的有效性。
- 生成Token或设置Session:验证成功后,生成JWT Token或设置
express-session
,并将相关信息(如用户ID、角色等)存储在Token或Session中。 - 返回Token或Session ID:将Token或Session ID返回给客户端。
- 后续请求认证:客户端在后续请求中附带Token或Session ID,服务器验证Token或检查Session以确认用户身份。
- 权限控制:根据用户的角色或权限级别进行资源访问控制。
示例代码
假设我们使用express
, express-session
和bcrypt
库来处理密码哈希,以及jsonwebtoken
来生成JWT Token。
const express = require('express');
const session = require('express-session');
const bcrypt = require('bcrypt');
const jwt = require('jsonwebtoken');
const app = express();
app.use(express.json());
app.use(session({
secret: 'your_secret_key',
resave: false,
saveUninitialized: true,
}));
// 用户数据库模拟
const users = [
{ id: 1, username: 'admin', password: '$2b$10$QnDyRJGZPzF8mHk7KqUvN.gi7wTjGzXtEzVgOz9Xf1C' }, // 密码为'password'
];
app.post('/login', async (req, res) => {
const { username, password } = req.body;
const user = users.find(u => u.username === username);
if (!user || !(await bcrypt.compare(password, user.password))) {
return res.status(401).send('Unauthorized');
}
// 生成JWT Token
const token = jwt.sign({ userId: user.id, role: 'admin' }, 'your_jwt_secret', { expiresIn: '1h' });
// 或者设置Session
// req.session.user = { userId: user.id, role: 'admin' };
res.json({ token });
});
app.get('/protected', verifyToken, (req, res) => {
res.send('You have access to this protected route.');
});
function verifyToken(req, res, next) {
const token = req.headers['authorization'];
if (!token) return res.status(403).send('A token is required for authentication');
try {
const decoded = jwt.verify(token, 'your_jwt_secret');
req.user = decoded;
} catch (err) {
return res.status(401).send('Invalid Token');
}
return next();
}
app.listen(3000, () => console.log('Server running on port 3000'));
在这个例子中,我们首先验证了用户名和密码,然后生成了一个JWT Token。客户端在后续请求中携带该Token,服务器使用verifyToken
中间件来解码并验证Token,从而决定是否允许访问受保护的路由。
这种方法相比直接操作全局变量更安全,也更容易扩展。