Browser Sniffing for Windows XP Media Center Edition in ASP.NET 2.0

Since last week I am involved in a project to develop an ASP.NET 2.0 website that should work in Windows XP Media Center Edition 2005.

We want to detect if the web site is running on a PC that has Windows XP Media Center Edition 2005 installed. ASP.NET has built-in browser sniffing capabilities, but ASP.NET 2.0 does not ship with detection for Media Center Edition. Fortunately, adding this is quite easy.

ASP.NET 2.0 has a hierarchical model for matching the User-Agent HTTP header sent by the browser. In 2.0 the browser sniffing configuration is no longer a humongous section in the machine.config file. It consists of several .browser files in the folder: %WINDIR%Microsoft.NETFrameworkv2.0.50727CONFIGBrowsers. It is possible to add extra “sniffers” as .browser files in the App_Browsers folder of your web application. This a part of the ie.browser file:

<browsers>

    <browser id="IE" parentID="Mozilla">

        <identification>

            <userAgent match="^Mozilla[^(]*([C|c]ompatible;s*MSIE (?'version'(?'major'd+)(?'minor'.d+)(?'letters'w*))(?'extra'[^)]*)" />

            <userAgent nonMatch="Opera|Go.Web|Windows CE|EudoraWeb" />

        </identification>

        <capture>

        </capture>

        <capabilities>

            <capability name="browser"              value="IE" />

            <capability name="extra"                value="${extra}" />

            <capability name="letters"              value="${letters}" />

            <capability name="majorversion"         value="${major}" />

            <capability name="minorversion"         value="${minor}" />

            <capability name="version"              value="${version}" />

(…)

        </capabilities>

    </browser>

    <browser id="IE5to9" parentID="IE">

        <identification>

            <capability name="majorversion" match="^[5-9]" />

        </identification>

(…)

    </browser>

    <browser id="IE6to9" parentID="IE5to9">

        <identification>

            <capability name="majorversion" match="[6-9]" />

        </identification>

(…)

    </browser>

As you can see IE “derives” from Mozilla, IE5to9 extends IE and IE6to9 extends IE5to9.

ASP.NET 2.0 makes this information available through the HttpBrowserCapabilities class. An instance of this class is exposed through HttpContext.Current.Request.Browser.

The browser used by the Media Center Shell is Internet Explorer 6.0. MCE comes with some extra ActiveX controls and extra client-side scripting capabilities through the window.external.MediaCenter object. When IE 6.0 is running as stand-alone browser on a Media Center PC it has access to the ActiveX controls, but not to the window.external.MediaCenter object. Fortunately, the user agent string has the information that indicates in which mode IE6.0 is running. The user agent strings of the various Media Center Editions can be found in this MSDN article.

As the core capabilities are the same as those of IE 6.0 I extended the IE6to9 browser. I added a WindowsMediaCenter.browser file to the App_Browsers folder of my web application with the following content:

<browsers>

      <browser id="IE6to9onMCE" parentID="IE6to9">

            <identification>

                  <capability name="extra" match="Media Center PC" />

            </identification>

            <capture>

                  <capability name="extra" match="Media Center PC (?'version'(?'major'd+)(?'minor'.d+))" />

            </capture>

            <capabilities>

                  <capability name="windowsMediaCenterExtensions" value="true" />

                  <capability name="mceVersion" value="${version}" />

                  <capability name="mceMajorVersion" value="${major}" />

                  <capability name="mceMinorVersion" value="${minor}" />

            </capabilities>

      </browser>

      <browser id="IE6to9onMCEinShell" parentID="IE6to9onMCE">

            <identification>

                  <capability name="extra" match="MediaCenter" />

            </identification>

            <capture>

                  <capability name="extra" match="MediaCenter (?'version'(d+.d+.d+.d+))" />

            </capture>

            <capabilities>

                  <capability name="runningInMceShell" value="true" />

                  <capability name="mceShellVersion" value="${version}" />

            </capabilities>

      </browser>

</browsers>

For more information about the .browser file format see MSDN.

I used the following Default.aspx page to test the browser sniffing:

<%@ Page Language="C#" AutoEventWireup="false" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<script runat="server">

    protected override void OnPreRender(EventArgs e)

    {

        base.OnPreRender(e);

        Response.Cache.SetCacheability(HttpCacheability.NoCache);

        string[] browsers = (string[])Request.Browser.Browsers.ToArray(typeof(string));

        BrowserInfo.Text = "<b>Browser ID</b>: " + Request.Browser.Id

            + " - <b>Version</b>: " + Request.Browser.Version

            + " - <b>Hierarchy</b>: " + String.Join(" | ", browsers)

            + " - <b>MCE enabled</b>: " + Request.Browser["windowsMediaCenterExtensions"]

            + " - <b>In MCE shell</b>: " + Request.Browser["runningInMceShell"];

    }

</script>

<html xmlns="http://www.w3.org/1999/xhtml">

<head>

    <title>Browser sniffing</title>

    <script type="text/javascript">

function IsMCEEnabled()

{

    return true;

}

    </script>

</head>

<body>

    <h1>

        Browser Sniffing Info</h1>

    <div>

        <asp:Label ID="BrowserInfo" runat="server"></asp:Label>

    </div>

</body>

</html>

When this page is requested in Mozilla Firefox 1.0.7 the result is:

Browser ID: mozillafirefox - Version: 1.0.7 - Hierarchy: default | mozilla | gecko | mozillarv | mozillafirefox - MCE enabled: - In MCE shell:

When this page is requested in the Media Center Shell on PC with XP Media Center Edition 2005 that has Update Rollup 2 installed the result is:

Browser ID: ie6to9onmceinshell - Version: 6.0 - Hierarchy: default | mozilla | ie | ie5to9 | ie6to9 | ie6to9onmce | ie6to9onmceinshell - MCE enabled: true - In MCE shell: true

Unfortunately I ran into some problems when trying to give the capabilities windowsMediaCenterExtensions and runningInMceShell the default value false by adding this to WindowsMediaCenter.browser:

      <browser refID="Default">

            <capabilities>

                  <capability name="windowsMediaCenterExtensions" value="false" />

                  <capability name="runningInMceShell" value="false" />

            </capabilities>

      </browser>

When I added this (at the top of the file), the values were false for all browsers even when overridden. This seems to be a bug in ASP.NET 2.0 to me.  Another strange thing I encountered was that there seems to be some inappropriate caching going on. When a MCE PC is the first to request the page after an application restart, an ordinary IE 6.0 browser on another PC who comes after the MCE PC is identified as IE6to9onMCEinShell. When the ordinary IE 6.0 is the first browser to request the page, it is the other way around. The MCE PC that comes second is falsely identified as IE6to9. Mozilla Firefox is always identified as mozillafirefox no matter if it comes first or second.

Leave a Reply

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