CSRF token not working in nodejs express

大城市里の小女人 提交于 2019-12-05 10:54:34

问题


I am developing a simple web app using nodejs, express and when i switched to session and csrf, my PUT, DELETE and POST Requests are failing. with error:

error: Forbidden at Object.exports.error (appFolder/node_modules/express/node_modules/connect/lib/utils.js:63:13) at createToken (appFolder/node_modules/express/node_modules/connect/lib/middleware/csrf.js:82:55)

I looked at this line, and found that it calls checkToken function which calls the defaultValue which finds the csrf token in the request like this:

function defaultValue(req) {
  return (req.body && req.body._csrf)
    || (req.query && req.query._csrf)
    || (req.headers['x-csrf-token'])
    || (req.headers['x-xsrf-token']);

}

This was giving null or undefined value, and my checkToken was failing.

My PUT requests are generated by backbone and i just send the model's data. so i started sending back the token in cookie. I set the token in cookie like:

app.use(express.cookieParser());
app.use(express.session({
    secret: '6767678376-3hudh-2u78di90-kjdu39i-jfujd'
}));
app.use(function(req,res,next) {
    console.log("Body "  + JSON.stringify(req.headers));
    return next();
});
app.use(express.csrf());


app.use(express.static(path.join(__dirname, 'public')));

app.use(function(req, res, next) {
    console.log(req.body);
    res.cookie('x-csrf-token', req.csrfToken());
    console.log('CSRF : ' + req.csrfToken());
    //res.session._csrf = req.csrfToken();
    return next();
});

and changed the defaultValue(req) to

function defaultValue(req) {
  var csrf_token = (req.body && req.body._csrf)
    || (req.query && req.query._csrf)
    || (req.headers['x-csrf-token'])
    || (req.headers['x-xsrf-token']);
  if(csrf_token)
    return csrf_token;

  // find in cookie.
  if(!req.headers['cookie'])
    return undefined;

  var csrfTokenInCookie = (req.headers['cookie'].split('x-csrf-token='));
  if(csrfTokenInCookie && (csrfTokenInCookie.length == 2)) {
    return csrfTokenInCookie[1];
  }
  var xsrfTokenInCookie = (req.headers['cookie'].split('x-xsrf-token='));
  if(xsrfTokenInCookie && (xsrfTokenInCookie.length == 2)) {
    return xsrfTokenInCookie[1];
  }
}

Now defaultValue is giving the csrftoken token rightly, but again checkToken is failing.

The file is here: csrf.js

What am i doing wrong ?

Or how can it not generate back the right-token ?


回答1:


Your issue is with Express not sending the CSRF token back in a header for POST/PUT/DELETE requests. Express's CSRF middleware is doing the correct thing in rejecting these requests when the header is missing.

Here's info on adding the header you need in Backbone: How to protect against CSRF when using Backbone.js to post data?




回答2:


your trying to validate the cookie and express session these will be different tokens so it will fail you would have to choose one either the cookie or token.

the author mentions it here https://github.com/expressjs/csurf/issues/52

personally i would recommend disabling cookies altogether and pass the token through the headers and form body -- this worked for me.



来源:https://stackoverflow.com/questions/21926062/csrf-token-not-working-in-nodejs-express

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!