JWT with Bearer Token protect from CSRF and XSS whilst using AJAX - ajax

I have a webapp that has a javascript page that makes ajax calls up to the webservices. The authorization scheme used for the site is JWT with bearer tokens being used in the authorization header.
However, I now realize that I am vulnerable to XSS, because the token is being stored in a cookie, and the javascript needs access to this in order to set the bearer token in it's requests. Because of this, httponly is set to false, thus meaning my token can be stolen.
So, what I would like to know is whether there is a way to protect against both CSRF and XSS whilst using ajax requests and JWTs?

Related

stealing authentication cookie with fetch request contains credentials: include

Let's assume I implement my authentication by http-only & secure cookie. At first glance it should protect from stealing this cookie if an attacker got access to my site through javascript injection. It's true, he can't access my token through javascript, but on the other side he can use ajax request, fetch with credentials: include to his malicious site and get my token there. So do I have any way to prevent this type of vulnerability?

Spring Security - CSRF token on GET request

I configured CSRF protection in my Spring 5 (Boot 2) RESTful web service because I want to prevent CSRF attacks (I am using JWT cookie for authentication and authorization). On each request I am getting a new XSRF cookie. The value of that cookie I am sending back through the X-CSRF-TOKEN header.
I noticed that POST, PUT and DELETE methods require the value of this token (in the X-CSRF-TOKEN header) in order to work properly, but GET method works just fine without X-CSRF-TOKEN header.
Is this behavior intentional because GET method should not change state or I did something wrong?
CSRF token is intentionally excluded from GET to avoid token leakage to a 3rd party

How to do CSRF verification along with Bearer token in Laravel?

Pardon me If I am wrong.
I am going to build a system by using Angular and Laravel API and these are some things about what I am doing.
I am using Passport and I am successfully able to do authentication.
I also want to do a CSRF verification because still I don't know where to store the token. If I store on cookies its vulnerable for CSRF (Thats why need to do a CSRF). What if I store bearer token on local storage ? Should I need to do a CSRF verfify ?.
How can I do a CSRF verify along with bearer token? (using web middleware)

Are Anti-CSRF tokens stored on client-side, server-side, or both?

I'm creating a React Js website with a Node.js backend. I've been attempting to figure out a user authentication implementation to prevent CSRF attacks however I'm really confused about where to store Anti-CSRF tokens.
My thought process of a secure implementation is as follows...
User submits request to login with credentials.
Credentials are authenticated.
Server creates session.
Server creates JWT to use as Anti-CSRF token.
Server stores JWT (Anti-CSRF token) in session storage.
Server sends response to client.
Response has header to store session ID in HttpOnly cookie on client-side.
Response payload includes JWT (Anti-CSRF token).
Client receives response.
HttpOnly cookie holding session ID is stored on client-side.
Client stores JWT (Anti-CSRF token) in localStorage.
I figure when a user needs to request information, the client can send the JWT (Anti-CSRF token) via a header or payload, and the session ID will be sent automatically due to it being a cookie. Then, the server can check if the JWT (Anti-CSRF token) exists in the session storage.
I know that the JWT (Anti-CSRF token) will need to be refreshed at some point.
My confusion is due to storing the JWT (Anti-CSRF token) on the client side. I keep reading that it should only be stored on the server. But if it's only stored on the server it doesn't seem to be doing anything at all.
I thought of using both cookies and localStorage because it seems that if a request to the server needs both a HttpOnly cookie and something from localStorage to send back an "authorized" response, an attacker would need to both successfully ride a session and successfully implement an XSS attack to get the Anti-CSRF token.
I just started learning about CSRF and XSS recently so I could be completely wrong and there could be a huge flaw in my implementation that I'm missing. But my main question is... don't Anti-CSRF tokens need to be stored on the client AND the server?
They are also called "CSRF Tokens". When a client requests for a form (e.g. bank login page), server generates the tokens and passes them to client and when the client fills the form, client passes CSRF token along with the completed form. Server verifies the token value and if it matches, request is fulfilled. CSRF tokens are stored on server-side in synchronizer token pattern.

Httponly cookie as bearer token - Laravel Passport

I have began building an application using React JS and Laravel 5.5. I have installed the Laravel Passport and have successfully managed to log my user in and out in my React JS app - but I have been told to look into using httponly cookies for security purposes.
In my working code, I have simply stored the access token in localStorage and sent it to the api using Authorization': 'Bearer ' + token in the axios headers, and this works perfectly. However, when I set a cookie using httponly I can't fetch the value of it (which I assume is exactly the point!) - using react-cookie (from npm), if I log cookie.loadAll() to the console then the only cookie I see is a new XSRF-TOKEN cookie, but not the accessToken cookie I set. So how do I go about sending this token to the api?
Since you can't read the httpOnly cookie from JS, when getting a new token from the backend, the backend has to send the token in the response body.
Browser session cookie usage and bearer tokens are different strategies of authentication (cookie based and token based).
In my opinion they should not be mixed.
Lavavel passport supports authentication with bearer token or with cookie out of the box (see condition at TokenGuard user)
You have to use Passport::cookie for this.
In this case you will be able to set cookie and use HttpOnly flag with other attributes to secure them.
Httponly cookie as bearer token doesn't make much sense. Having cookies httponly helps to protect you and the user against XSS attack as their not readable by javascript. They can be used e.g. for storing session information and are sent when the user do e.g. a page reload.
Setting Authorization header to 'Bearer ' + token is correct way how to sent token to the api. Before using token on the api server you should always check if the token is still valid.

Resources