How to forcefully set IE's Compatibility Mode off from the server-side?

142,416

Solution 1

I found problems with the two common ways of doing this:

  1. Doing this with custom headers (<customHeaders>) in web.config allows different deployments of the same application to have this set differently. I see this as one more thing that can go wrong, so I think it's better if the application specifies this in code. Also, IIS6 doesn't support this.

  2. Including an HTML <meta> tag in a Web Forms Master Page or MVC Layout Page seems better than the above. However, if some pages don't inherit from these then the tag needs to be duplicated, so there's a potential maintainability and reliability problem.

  3. Network traffic could be reduced by only sending the X-UA-Compatible header to Internet Explorer clients.

Well-Structured Applications

If your application is structured in a way that causes all pages to ultimately inherit from a single root page, include the <meta> tag as shown in the other answers.

Legacy Applications

Otherwise, I think the best way to do this is to automatically add the HTTP header to all HTML responses. One way to do this is using an IHttpModule:

public class IeCompatibilityModeDisabler : IHttpModule
{
    public void Init(HttpApplication context)
    {
        context.PreSendRequestHeaders += (sender, e) => DisableCompatibilityModeIfApplicable();
    }

    private void DisableCompatibilityModeIfApplicable()
    {
        if (IsIe && IsPage)
            DisableCompatibilityMode();
    }

    private void DisableCompatibilityMode()
    {
        var response = Context.Response;
        response.AddHeader("X-UA-Compatible", "IE=edge");
    }

    private bool IsIe { get { return Context.Request.Browser.IsBrowser("IE"); } }

    private bool IsPage { get { return Context.Handler is Page; } }

    private HttpContext Context { get { return HttpContext.Current; } }

    public void Dispose() { }
}

IE=edge indicates that IE should use its latest rendering engine (rather than compatibility mode) to render the page.

It seems that HTTP modules are often registered in the web.config file, but this brings us back to the first problem. However, you can register them programmatically in Global.asax like this:

public class Global : HttpApplication
{
    private static IeCompatibilityModeDisabler module;

    void Application_Start(object sender, EventArgs e)
    {
        module = new IeCompatibilityModeDisabler();
    }

    public override void Init()
    {
        base.Init();
        module.Init(this);
    }
}

Note that it is important that the module is static and not instantiated in Init so that there is only one instance per application. Of course, in a real-world application an IoC container should probably be managing this.

Advantages

  • Overcomes the problems outlined at the start of this answer.

Disadvantages

  • Website admins don't have control over the header value. This could be a problem if a new version of Internet Explorer comes out and adversely affects the rendering of the website. However, this could be overcome by having the module read the header value from the application's configuration file instead of using a hard-coded value.
  • This may require modification to work with ASP.NET MVC.
  • This doesn't work for static HTML pages.
  • The PreSendRequestHeaders event in the above code doesn't seem to fire in IIS6. I haven't figured out how to resolve this bug yet.

Solution 2

Changing my header to the following solve the problem:

<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=Edge" />

Solution 3

Update: More useful information What does <meta http-equiv="X-UA-Compatible" content="IE=edge"> do?

Maybe this url can help you: Activating Browser Modes with Doctype

Edit: Today we were able to override the compatibility view with: <meta http-equiv="X-UA-Compatible" content="IE=EmulateIE8" />

Share:
142,416

Related videos on Youtube

JSancho
Author by

JSancho

Updated on September 18, 2020

Comments

  • JSancho
    JSancho over 3 years

    In a domain-controlled environment I'm finding that the compatibility mode is triggered on certain clients (winXP/Win7, IE8/IE9) even when we are providing a X-UA tags, a !DOCTYPE definition and "IE=Edge" response headers. These clients have the "display intranet sites in compatibility view" checkbox ticked. Which is precisely what I'm trying to override.

    The following is the documentation that I've used to try understand how IE decides to actually trigger the compatibility mode.

    http://msdn.microsoft.com/en-us/library/ff406036%28v=VS.85%29.aspx

    http://blogs.msdn.com/b/ie/archive/2009/02/16/just-the-facts-recap-of-compatibility-view.aspx

    Site owners are always in control of their content. Site owners can choose to use the X-UA-Compatible tag to be absolutely declarative about how they’d like their site to display and to map Standards mode pages to IE7 Standards. Use of the X-UA-Compatible tag overrides Compatibility View on the client.

    Google for "Defining Document Compatibility", sadly the SPAM engine doesn't let me post more than 2 urls.

    This is an ASP .NET web app and includes the following definitions on the master page:

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
    <head>
       <meta http-equiv="X-UA-Compatible" content="IE=Edge" />
    </head>
    

    and web.config

    <system.webServer>
      <httpProtocol>
        <customHeaders>
          <clear />
          <add name="X-UA-Compatible" value="IE=Edge" />
        </customHeaders>
      </httpProtocol>
    </system.webServer>
    

    I've used Fiddler to check that the header is indeed being injected correctly.

    My understanding is that with these settings I should be able override the "Display intranet sites in Compatibility View" browser setting. But depending on the client I've found that some of them will still trigger compatibility mode. It also seems to be down to the machine level rather a policy group setting, since I obtain different results even when I use with the same set of credentials on different clients.

    Disabling the Compatibility View Settings checkbox does the trick. But the actual purpose is to make sure that the app is rendered exactly the same way regardless of the client settings.

    Any thoughts and what I could be possibly missing? Is it possible at all to force IE to always render the pages without triggering Compat mode?

    thanks a million,

    Jaume

    PS: the site is currently in development and is of course not in Microsoft's compatibility list, but I've also checked just in case.

    Google for "Understanding the Compatibility View List", sadly the SPAM engine doesn't let me post more than 2 urls.

  • JSancho
    JSancho almost 13 years
    @Balanivash That was a really good read actually, thanks for the link. The article leads me to believe the "Compatibility Mode" is being enabled because the site is located within the intranet zone. However, this is not occurring consistently, for instance: - win7, IE8, on a client -> full standards mode - win7, IE8, on a different box with the same credentials -> compat mode To be on the safe-side I'm also starting new sessions of the browser and resetting the IE developer toolbar to default values on every test.
  • Andrew
    Andrew almost 13 years
    Maybe you can try this: <meta http-equiv="X-UA-Compatible" content="IE=8" />
  • Andrew
    Andrew almost 13 years
    Also: If you want your web application to tell IE8 to really trust you, you need to send X-UA-Compatible as an HTTP header from your web server instead of meta tag: social.msdn.microsoft.com/Forums/en-US/iewebdevelopment/thre‌​ad/…
  • JSancho
    JSancho almost 13 years
    The site uses css3 if the client is capable and the IE=Edge setting is working as far as switching to IE9 or IE8 standards depending on the client. It's the "compatibility mode" that it's bothering me. And the HTTP header is actually in. That's set with the web.config options above and Fiddler does pick it the header response.
  • Andrew
    Andrew almost 13 years
    Tried <add name="X-UA-Compatible" value="IE=8" /> yet?
  • Andrew
    Andrew over 12 years
    Actually today we were able to override the compatibility view with: <meta http-equiv="X-UA-Compatible" content="IE=EmulateIE8" />
  • Sam
    Sam almost 11 years
    Thanks for updating your answer. I think it would be better if your answer specified IE=Edge since the question is about disabling compatibility mode.
  • JSancho
    JSancho almost 11 years
    It might have taken more than a year for your answer to come around, and the actual app that I was working on is now deprecated. Nevertheless, this is definitely the most thorough and well-researched answer that I could have hoped for. Good things come to those who wait :) thanks Sam
  • BobRodes
    BobRodes over 9 years
    "This should ensure the page is rendered consistently with other browsers and in a standards-compliant manner." I'm sorry, but this has not been my experience in the least. Right now, I'm working with a SSRS report that renders all wrong in IE10, just fine in Chrome, and just about fine in IE10 compatibility mode.
  • Sam
    Sam over 9 years
    @BobRodes, I think I wrote that because later versions of IE are supposed to be more standards-compliant, but I wasn't really speaking from experience, so good point! I just updated the answer to remove that claim.
  • BobRodes
    BobRodes over 9 years
    Microsoft uses a concept of "embrace, expand, extinguish" in its relations with its competitors. First, embrace any sort of standard. Then, "improve" on the standard with proprietary features and functions. Then, quietly drop support for the standard in future versions. Fortunately, they are having trouble with that with IE. :)
  • user609926
    user609926 almost 8 years
    This worked for me and I'd tried several different solutions including the meta tag and attempting to use css hacks to account for the areas of the site that weren't rendering incorrectly in ie.
  • Catch22
    Catch22 over 7 years
    I also needed to add the customer header to the web.config file to get it to work on Windows 2008 server