Cross-site request forgery, also known as one-click
attack or session riding and abbreviated as CSRF (sometimes
pronounced sea-surf) or XSRF, is a type of malicious exploit of a website where
unauthorized commands are transmitted from a user that
the web application trusts. There are many ways in which a malicious website
can transmit such commands; specially-crafted image tags, hidden forms, and
JavaScript XMLHttpRequests, for example, can all work without the user's interaction
or even knowledge. Unlike cross-site scripting (XSS),
which exploits the trust a user has for a particular site, CSRF exploits the
trust that a site has in a user's browser.
To prevent this we are using Synchronizer token pattern (STP) which is a
technique where a token, secret and unique value for each request, is embedded
by the web application in all HTML forms and verified on the server side. The
token may be generated by any method that ensures unpredictability and
uniqueness (e.g. using a hash chain of
random seed). The attacker is thus unable to place a correct token in their
requests to authenticate them.
Another technique used to prevent is Double Submit Cookie. If storing the CSRF token in
session is problematic, an alternative defense is use of a double submit
cookie. A double submit cookie is defined as sending a random value in both a
cookie and as a request parameter, with the server verifying if the cookie
value and request value match.
When a user authenticates to a site, the site should
generate a (cryptographically strong) pseudorandom value and set it as a cookie
on the user's machine separate from the session id. The site does not have to
save this value in any way, thus avoiding server side state. The site then
requires that every transaction request include this random value as a hidden
form value (or other request parameter). A cross origin attacker cannot read
any data sent from the server or modify cookie values, per the same-origin
policy. This means that while an attacker can force a victim to send any value
he wants with a malicious CSRF request, the attacker will be unable to modify
or read the value stored in the cookie. Since the cookie value and the request
parameter or form value must be the same, the attacker will be unable to
successfully force the submission of a request with the random CSRF value.
Synchronizer Token Pattern
In the upcoming steps we will learn how to implement Synchronizer
Token Pattern for a web application using simple steps.
1. User Login Page – Values prefilled to testing
purposes.
2. Generate
session identifier and set it as a cookie.
Uses express-session middleware
and UUID library for
defining session id.
Generated a session identifier and session
cookie in chrome.
3. Generate
the CSRF token and store in the server side.
The CSRF token is stored in memory and mapped
to the session identifier
4. The endpoint receives the session cookie and based on
the session identifier return the CSRF token value.
5. Implement a html page with a form and its method
should be POST and action should be another URL ( '/login' ). When page loads
run a script to obtain the CSRF token created for the session.
Once the page is loaded successfully, update form’s
document object model and add a new hidden field that has the value of the
received CSRF token (_csrf).
Once the csrf token returned from '/middleware' endpoint,
we get the form id and assign it to a variable called 'form' and then, create a
input type element and assign it to a variable called 'input'.
Then set input type, name and value as hidden, '_csrf'
and the csrf token value obtained from the ajax call when the page loads and
then we append the updated input element as one of the child elements to the
html form element.
6. Once the HTML form is submitted to the action, in the
server side, extract the received CSRF token value and check if it is the
correct token issued for the relevant session.
If the session csrf token and the csrf token passed from
the hidden input field or body is the same show a success message if not same
show an error message.
Successful login screenshot.
Double Submit Cookies Pattern
In the upcoming steps we will learn how to implement Double
Submit Cookies Pattern for a web application using simple steps.
1. User Login Page – Values prefilled to testing
purposes.
2. Generate
session identifier and set it as a cookie.
Uses express-session middleware
and UUID library for
defining session id.
3. Generate the CSRF token for the session and set a csrf
cookie in the web browser.
httpOnly flag is set to false is
to allow JavaScript to access the csrf cookie.
4. Implement a html page with a form and
its method should be POST and action should be another URL ( '/login' ).
5. Once html form is loaded, run a JavaScript which reads
the csrf token cookie value in the browser and add a hidden field to the html
form modifying the DOM.
Obtain all the cookies using ‘document.cookie’ and split
the key value pairs using ' ; '. After splitting, pass the key value pairs to an
array. Using ‘for loop’, identify the csrf cookie by using the csrf cookie name
set in the server side. Then extract the csrf token value and create a input
element and append the input element to the html form element with the csrf
token.
6. Obtain the CSRF token received in the cookie and also in
the message body and compare them.
req.cookies._csrf is the csrf cookie with the csrf token value which was send
to the server side after submitting the form. req.body._csrf contains the csrf token value in the hidden field input.
If they match display a success message. If not show error
message.
GitHub Repo link for complete code: