How can I redirect after OAUTH2 with SameSite=Strict and still get my cookies? How can I redirect after OAUTH2 with SameSite=Strict and still get my cookies? google-chrome google-chrome

How can I redirect after OAUTH2 with SameSite=Strict and still get my cookies?


I don't think that this can be done for security reasons. SameSite=Strict means that if user has been redirected or just clicked on link to your site (from other host), cookie shouldn't be send. And redirecting is like 'chaining' requests. So if your server redirects to another and this server redirects back immediately with 3xx code, cookie will be sent, because your server is 'on top' of this chain.

However if you redirect to oauth provider and user has to allow there you to access his account it means that this 'chain' is broken, and cookie will no longer be sent even if your site sets it (it is set however not sent). Your redirect is just 'extension' of clicked 'allow' link.

If you want to prevent others from click-jacking your site, just use nonce in link if you think, that you have to prevent that kind of behavior, and it can be dangerous if you don't. But consider that most providers are checking for you if redirect url was previously defined and allowed by your app.

Here are other solutions (use only if you know what you're doing and can get on yourself 100% responsibility).

  • Prepare site with 'Continue to site' link (cookie of course will be send after hitting link)
  • Reload window with JavaScript
  • Prepare site with JavaScript which will redirect user
  • Combine first and third method to have cleaner solution, and working without JavaScript support in browser.

I have used second while developing, now I am using same site lax (this was default in Hapi up to maybe 15 ver, so it isn't so bad).


HTTP OK with HTML redirect ensures the redirected request actually sends the SameSite=Strict cookie.

Solution is simple. Instead of a 302, send a 200 with the following body:

<html><head><meta http-equiv="refresh" content="0;URL='https://example.com/destination'"/></head><body><p>Moved to <a href="https://example.com/destination">https://example.com/destination</a>.</p></body></html>

Using meta refresh to create an instant client-side redirect

My OIDC scenario involved:

  • GET 302 https://strict redirect to different domain
  • GET 302 https://oidc redirect
  • GET 200 https://oidc/2 ok
  • POST 302 http://strict
  • GET 200 https://strict/redirect?returnUrl=target (new HTML redirect)
  • GET 200 https://strict/target

Normally we would 302 redirect to the target on the OIDC POST, but, this doesn't work with SameSite=Strict. The browser refuses to send the cookie, even though it stored it. If you close the browser and re-open, it will send the cookie. By adding an additional HTML redirect, the browser sends the cookie when it requests the final URL.

In .NET Core, I was able to use SameSite=Strict cookies by replacing the Response.Redirect with the HTML redirect solution:

public sealed class OpenIdConnectHtmlRedirectHandler : OpenIdConnectHandler{    public OpenIdConnectHtmlRedirectHandler(IOptionsMonitor<OpenIdConnectOptions> options,                                            ILoggerFactory logger,                                            HtmlEncoder htmlEncoder,                                            UrlEncoder encoder,                                            ISystemClock clock) : base(options, logger, htmlEncoder, encoder, clock) { }    public override async Task<bool> HandleRequestAsync()    {        if (!await base.HandleRequestAsync())            return false;        var headers = Response.GetTypedHeaders();        if (null == headers.Location)            return true;        Response.ContentType = "text/html";        Response.StatusCode = 200;        headers.Location = null;        await Response.WriteAsync($"<html><head><meta http-equiv=\"refresh\" content=\"0; URL='{location}'\"/></head></html>",                                  Encoding.UTF8, Context.RequestAborted);        return true;    }}