Closed Yu-Jack closed 3 years ago
Thank you for this, but the issue is that users are 100% allowed to call this module twice, and this will break that. Here is a quick scenario that will break with this change: you want csurf on two parts of your application but not the entire application. You just app.use('/admin', csurf())
and then app.use('/forum', csurf())
for example.
Okay, thank you!
@dougwilson
What if I return secret from "set-cookie" response headers when bag[key]
is null, is it okay?
This is my modified code, then the test case is all passed.
And it will let the above case passed.
function getSecret (req, res, sessionKey, cookie) {
// get the bag & key
var bag = getSecretBag(req, sessionKey, cookie)
var key = cookie ? cookie.key : 'csrfSecret'
if (!bag) {
throw new Error('misconfigured csrf')
}
if (!bag[key]) {
let setCookieHeaders = res.getHeader("set-cookie")
if (setCookieHeaders) {
for (const header of setCookieHeaders) {
let cookie = Cookie.parse(header)
if (cookie[key]) {
// return secert from sent response headers
return cookie[key]
}
}
}
}
// return secret from bag
return bag[key]
}
Hi @Yu-Jack that may work, but there are a few issues with your code there:
cookie.parse
cannot parse a set-cookie
syntax; you need to use an appropriate parser for that header.set-cookie
header, you need to also check that it will come back to the relevant path and domain, as the cookie name is not unique enough to know that would be the cookie the browser would send back to you
Introduction
Recently, I answered a question in the stackoverflow. The user repeatedly call
csurf
then put it into express middleware. It result in a error message "invalid csrf token" when user make form post at first time.Reason
This is a sample code make this happen.
Reproduced Way:
localhost:8080
)http://localhost:8080/settings
We could there are two line called
csurf()
and put it into middleware of express in mark1 and mark2. In mark1, csurf will generate asecret1
andtoken1
to give ejs template. But, in mark2, csurf is re-initialized, secret and token1 is changed. That means csurf will validate next request with newsecret2
andtoken2
.But, it only happen at the first time validation. Subsequently, the request will be validated correctly.
Solution
I think I could add a flag to decide the csurf is initialized or not.
It's default is false, it will be changed to true when user call
csurf()
. Then It will throw error when initialized is already true.I'm not sure is it a good idea to prevent user from using
csurf()
Please let me know, is there any problem will make a new problem? Thanks!