Where to store JWT in browser?
Skilled Software Developer with 3+ years of experience in the full SDLC creating dynamic web applications. Updates functionality based on customer requirements to ensure excellent user experience.
We need to store the JWT on the client computer. If we store it in a LocalStorage/SessionStorage then it can be easily grabbed by an XSS attack. If we store it in cookies then a hacker can use it (without reading it) in a CSRF attack and impersonate the user and contact our API and send requests to do actions or get information on behalf of a user. But there are several ways to secure the JWT in cookies to not to be stolen easily (but there are still some advanced techniques to steal them). But if you wanna rely on LocalStorage/SessionStorage, then it can be accessed by a simple XSS attack.
So to solve the CSRF problem, I use Double Submit Cookies in my application.
Double Submit Cookies Method
Store JWT in a HttpOnly cookie and used it in secure mode to transfer over HTTPS.
Most of CSRF attacks have a different origin or referrer header with your original host in their requests. So check if you have any of them in the header, are they coming from your domain or not! If not reject them. If both origin and referrer are not available in the request then no worries. You can rely on the result of X-XSRF-TOKEN header validation results which I explain in the next step.
While the browser will automatically supply your cookies for the domain of the request, there is one useful limitation: the JavaScript code that is running on a website cannot read the cookies of other websites. We can leverage this to create our CSRF solution. To prevent CSRF attacks, we must create an extra Javascript readable cookie which is called: XSRF-TOKEN. This cookie must be created when the user is logged in and should contain a random, un-guessable string. We also save this number in the JWT itself as a private claim. Every time the JavaScript application wants to make a request, it will need to read this token and send it along in a custom HTTP header. Because these operations (reading the cookie, setting the header) can only be done on the same domain of the JavaScript application, we can know that this is being done by a real user who is using our JavaScript application.
Look for a cookie named XSRF-TOKEN on the current domain. If that cookie is found, it reads the value and adds it to the request as the X-XSRF-TOKEN header. Thus the client-side implementation is handled for you, automatically! We just need to set a cookie named XSRF-TOKEN on the current domain in server side and when our API got any call from the client, it must check the X-XSRF-TOKEN header and compare it with the XSRF-TOKEN in the JWT. If they match, then the user is real. Otherwise, it's a forged request and you can ignore it. This method is inspired by the "Double Submit Cookie" method.




