Search code examples
httpcookiescross-domainsamesite

Configure a cookie to work with CORS, but only on subdomains


I'm trying to figure out a way to make cookie-based authentication work, when the frontend and the backend are two different subdomains, without exposing myself to the CSRF threat.

Currently, i'm resorting to setting the cookie attribute sameSite to "None". Problem is, that this totally exposes the site to CSRF attacks.

For example,this is my cookie with the sameSite set to "lax": cookieName=cookieValue; expires=Thu, 01 Jan 1970 00:00:00 GMT; Path=/; httponly; SameSite=Lax; Secure; Domain=some-sub-domain.localhost;

If my React app runs on locahost:3000, which is the same domain but different subdomain(and port..), this works only with sameSite=None. If sameSite is changed to "lax" or "strict", i get the following error, in the network tab, next to the set-cookie header:

This attempt to set a cookie via Set-Cookie header was blocked because it had the "SameSite=Lax" attribute but came from a cross-site response which was not the response to a top-level navigation.

I tried every possible configuration(including ".localhost"), and the only thing that seems to work is setting the SameSite to "None", but this would totally expose my site to CSRF attacks(assuming i do not incorporate some CSRF token, which is a different story).

My idea is to simply allow cookies to travel between subdomains, while blocking them on different domains. I mean, any subdomain would eventually be under my control.

Can it be done?


Solution

  • If anybody is interested, i found the "problem":

    It was "localhost". It's not a "normal" domain. It's not localhost.com, or localhost.net- it's just plain localhost.

    Therefore, setting up "subdomains" like frontend.localhost and backend.localhost doesn't work(unless you use sameSite=none), because those are actually totally different domains, not subdomains

    To overcome this issue locally, you should set up virtual hosts in your operating system's hosts file. Something like frontend.local.xyz and backend.local.xyz. "local.xyz" is the actual domain in this case, and the others are subdomains. This solves the "problem", and allows a "strict" cookie to travel between them.

    Note that this would still NOT work, if your domain is in this list: https://publicsuffix.org/list/public_suffix_list.dat