在 Express.js 中使用会话

Posted

技术标签:

【中文标题】在 Express.js 中使用会话【英文标题】:Working with Sessions in Express.js 【发布时间】:2012-12-22 12:38:25 【问题描述】:

我需要帮助来理解 Web 应用程序的会话概念。我正在使用 Express 3.0 运行 Node.js 服务器。

我的目标是:

为每个登录的用户创建一个会话

存储此会话并将其用于验证用户是否已登录(防止两台设备同时使用同一用户)并限制对某些页面的访问(通过将会话 ID 与其他一些数据匹配)

我将使用 MemoryStore 来保存会话(似乎最简单)。如果上述目标有意义,您能否详细说明如何实现这些目标?

【问题讨论】:

你应该看看Passport 我已经尝试过使用护照,但无法正常工作,我认为在 express 中使用默认会话会更容易。 您可能想阅读以下内容:***.com/questions/11187342/… Session 只不过是 db/memory 中具有唯一 ID 的条目。 这里非常详细地描述了会话如何在 express 中工作。 ***.com/a/11585839/74291 【参考方案1】:

Express 在 github 存储库中有很好的 examples。其中之一处理authentication,并展示了如何将用户附加到req.session 对象。这是在app.post('/login') 路由内完成的。

要限制对某些页面的访问,请向这些路由添加一个简单的中间件

function restrict(req, res, next) 
  if (req.session.user) 
    next();
   else 
    req.session.error = 'Access denied!';
    res.redirect('/login');
  


app.get('/restricted', restrict, function(req, res)
  res.send('Wahoo! restricted area, click to <a href="/logout">logout</a>');
);

正如Brandon 已经提到的,您不应该在生产中使用 MemoryStore。 Redis 是一个不错的选择。使用connect-redis 访问数据库。示例配置如下所示

var RedisStore = require('connect-redis')(express);

// add this to your app.configure
app.use(express.session(
  secret: "kqsdjfmlksdhfhzirzeoibrzecrbzuzefcuercazeafxzeokwdfzeijfxcerig",
  store: new RedisStore( host: 'localhost', port: 3000, client: redis )
));

【讨论】:

你在哪里比较两个 session_id 和 cookie id ?? 你能告诉我使用redis我必须自己生成唯一令牌还是redis提供这个功能??【参考方案2】:

仅当您不创建多个实例(例如使用集群模块)时,才在 express 中使用 MemoryStore。如果您要跨机器进行负载平衡,您的负载平衡器将需要使用粘性/持久会话。

如果您满足这些要求,那么您只需在登录时,验证凭据后,设置会话变量以指示已登录,例如:

req.session.loggedIn = true;

如果您想检查用户是否已登录,只需检查该变量即可。

if (req.session.loggedIn) 
    // user is logged in.

else 
    // user is not logged in.

您提到防止单个用户一次进行多个会话。为了实现这一点,您可能需要在数据库中存储一些指示用户已登录的内容。我警告您,由于会话过时,这可能很危险。例如,如果用户登录但从未注销怎么办?如果他们关闭浏览器窗口,会话就永远消失了怎么办?

Express 没有空闲会话到期的概念。我通过将所有会话与上次访问的时间戳一起存储在数据库中来实现这样的事情,然后根据时间定期清理会话数据。但是,您还需要更新您的登录列表。

【讨论】:

他可以覆盖上一个会话,以这种方式禁用旧会话并防止“陈旧会话”成为问题? 不知道为什么他需要使用粘性端口而不是循环?使用带有 connect_redis 的循环将允许会话在网站的任何实例上工作。加上作者声称它是insanely fast,但是你可能会在性能上失去什么,你会在容错中获得。 @Neikos :我不需要完全实现该机制,但很难绕过它。你有什么建议吗?请在这里回答:***.com/questions/29144827/…

以上是关于在 Express.js 中使用会话的主要内容,如果未能解决你的问题,请参考以下文章

使用 Express.js v4 和 Socket.io v1 的会话

React 前端 + Express.js 会话

会话如何在 Express.js 和 Node.js 中工作?

Node.js/Express.js 会话管理 cookie 为会话 cookie

从 Jade 模板访问 Express.js 请求或会话

Express.js/Passport 应用程序为每个请求创建新会话,尽管请求标头中有会话 ID