CSRF Protection Episode 1. Synchronizer Token Pattern

Munsif Musthafa
4 min readOct 7, 2018

--

In my previous blog post, I had discussed about Cross-site Request Forgery, how it happens. I had mentioned about a couple of preventative measures that web application developers could follow to provide a safe and better experience to their users.

Introduction

The basic flow of events in a normal “secure” client-server request-response would go as follows. Client types in his/her credentials and clicks Sign In, which sends a POST request to the server. The server would check if the username and password matches with what’s there in its storage. If the user is a match, server would generate a session cookie, store it against the username and send it back in the response header as set-cookie=abc123. The client browser would then store this session cookie in the cookie storage and send it along any subsequent requests made to the server. The issue with this is any malicious party could trick the authenticated user externally to send in a request on behalf of the attacker unbeknownst to the user. In this post, we shall take a look at the Synchronizer Token Pattern and a quick example application which implements this pattern.

Flow of Events of Synchronizer Token Pattern

Flow of Events of Synchronizer Token Pattern

Flow of events

The difference here is that alongside generating and sending a session cookie, the server would also generate a token and store it against the sessionId for the user. Then the web page with the state changing operation, would make an AJAX call internally to the token end-point of the server to retrieve the token from the server. The JavaScript that runs on the page would then extract the token from the response and embed it into a hidden field inside the form. When the user clicks on the button to submit the page, the request that goes would contain the session cookie in the header, and the token as a field in the body. The server can now verify and validate the request and make sure no forging has been done.

Why is this secure?

Of course still a malicious entity could do some social engineering and manipulate the the user into clicking or executing a state-changing operation from the client browser unbeknownst to the user. The attacker could easily forge a similar form with all hidden fields and execute the url from the user’s browser… and that server’s relevant session cookie would be sent along the request too. But the request would fail on the server side. The reason is that the the token embedding cannot be carried out by the attacker because cross-domain AJAX calls are blocked by default.

Example Implementation

This sample application is implemented using Spring Boot.

Login page
Homepage with the state changing operation

Below is the login page, which uses Thymeleaf for as the templating engine.

login.html

The login action submits the credentials to the server. I don’t want to go deep on how Thymeleaf handles the data binding (it’s a topic for another time).

Next up we shall take a look at the Main Controller which for simplicity’s sake would handle our Login post request and the subsequent state changing post request to add a blog post.

MainController.java

Next up we’ll look at the Service class which processes the requests, i.e. validate user, validate session, validate token and so on.

AuthenticationService.java

Next up is the redirected add blog/home page, which contains the state-changing POST operation (create) and the associated JavaScript which sends a GET request to the token end-point and embeds the token into a hidden field in the form body.

home.html
main.js

Once the user submits the form, it gets sent to the post end-point and in the request body is the form fields which contains the hidden field witht the token value. How the “synchronizer” validation is done in the server is also available in the gist above “MainController.java”. Upon receiving the request the server will validate the token from the body.

The full implementation of this pattern can be found in this GitHub link.

In the next blog, we shall look at how the Double Submit Cookie pattern works and its implications.

If you enjoyed this article, please hold down the clap button below 👏 to help others find it.

--

--