SSL Termination and Secure Cookies/requireSSL with ASP.NET Forms Authentication

If you’re running a HTTPS-only web application, then you probably have requireSSL set to true in your web.config like so:

<httpCookies requireSSL="true" httpOnlyCookies="true"

With requireSSL set, any cookies ASP.NET sends with the HTTP response – in particular, the forms authentication cookies – will have the “secure” flag set. This ensures that they will only be sent to your website when being accessed over HTTPS.

What happens if you put your web application behind a load balancer with SSL termination? In this case, ASP.NET will see the request coming in as non-HTTPS (Request.IsSecureConnection always returns false) and refuse to set your cookies:

“The application is configured to issue secure cookies. These cookies require the browser to issue the request over SSL (https protocol). However, the current request is not over SSL.”

Fortunately, we have a few tricks up our sleeve:

  1. If the HTTPS server variable is set to ‘on’, ASP.NET will think we are over HTTPS
  2. The HTTP_X_FORWARDED_PROTO header will contain the original protocol running at the load balancer (so we can check that the end connection is in fact HTTPS)

With this knowledge, and the rewrite module available in IIS 7 upwards, we can set up the following:

    <rewrite>
        <rules>
            <rule name="HTTPS_AlwaysOn" patternSyntax="Wildcard">
                <match url="*" />
                <serverVariables>
                    <set name="HTTPS" value="on" />
                </serverVariables>
                <action type="None" />
                <conditions>
                    <add input="{HTTP_X_FORWARDED_PROTO}" pattern="https" />
                </conditions>
            </rule>
        </rules>
    </rewrite>

You’ll also need to add HTTPS to the list of allowedServerVariables in the applicationHost.config (or through the URL Rewrite config)

        <rewrite>
            <allowedServerVariables>
                <add name="HTTPS" />
            </allowedServerVariables>
        </rewrite>

With thanks to Levi Broderick on the ASP.NET team who sent me in the right direction to this solution!

6 thoughts on “SSL Termination and Secure Cookies/requireSSL with ASP.NET Forms Authentication”

  1. Repost, since my code didn’t come through

    I’m wondering if some recent patch by Microsoft hasn’t disabled the setting of the HTTPS server variable because I can’t get it to work no matter what I do. My rule has no conditions and I my custom server variable is set as would be expected, but the HTTPS server variable doesn’t seem to be writable using the rewrite module.

    I have a rule setup in my sites web.config …

    and in applicationHost.config I have two server level variables allowed…

  2. Question: Due to the fact that the developers are able to run the site on their local boxes without a load balancer, is there a way to get this going without enforcing SSL? I know it’s kinda silly, but I’d rather be able to have one config for all as opposed to having to add extra config values as part of the deploy process. Prod will or course stay https only.

    Right now when we attempt to use the site over http, it seems that it goes into an infinite redirect loop.

    -Alex

  3. On IIS 10 :
    The server variable “HTTPS” is not allowed to be set. Add the server variable name to the allowed server variable list.
    To add:
    1. In IIS Manager select your site
    2. Select ‘URL Rewrite’
    3. Select ‘View Server Variables’
    4. Select ‘Add’ and enter ‘HTTPS’.

    1. Never mind, it did work with MVC 4 Forms Authentication! Thanks for posting… you saved the day for me!

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.