将路由拆分为不同的文件/模块时获取"ForbiddenError: invalid csrf token"



我在express项目中使用csurf。我有3个文件:

  • app.js-主要入口点
  • 路由/index.js-索引路由
  • routes/users.js-用户路由

当使用express应用程序生成器时,它是标准样板。

我在index.js:中有一条路线

router.get('/', csrfProtection, function(req, res, next) {
res.render('index', {
csrfToken: req.csrfToken()
});
});

此路由的页面包含一个具有csrf令牌的隐藏字段的表单:

input(name='_csrf', type='hidden', value='#{csrfToken}')

一切都很好,我可以在源代码中看到csrf令牌。

提交表单时,在routes/users.js:中处理购买路线

router.post('/login', csrfProtection, function(req, resp) {
if(!validator.isAlphanumeric(req.username))
console.log('Not alphanumeric');
...
});

问题似乎与两个文件都必须创建csrfcsrfToken的新实例有关。在两个路由文件的开头,我需要它们,如下所示:

var csrf = require('csurf');
var csrfProtection = csrf({ cookie: true });

如果我将登录路由放入routes/index.js中,它可以正常工作,这让我认为这两个实例可能都使用了不同的csrf令牌。

有什么想法吗?

是的,我相信它使用了不同的CSRF令牌。我在子模块中定义了一个init函数,然后将CSRF令牌传递到其中,从而解决了这个问题。这样,CSRF令牌只创建一次。我认为在app.js中创建CSRF令牌可能是最好的,然后您可以将其传递到各个子模块中。

例如:

在users.js:中

function init(router, csrfProtection) {
router.post('/login', csrfProtection, function(req, resp) {
if(!validator.isAlphanumeric(req.username))
console.log('Not alphanumeric');
...
});
}
module.exports.init = init;

在app.js:中

...initialize router and CSRF protection...
var users = require('./users.js');
users.init(router, csrfProtection);

最新更新