IE9 is the first version of Internet Explorer to natively support XHTML. For those not familiar, XHTML is the XML serialization of HTML. Among other benefits, XHTML can help maintain cleaner markup due to its fail-fast nature in the face of parsing errors. You can see IE9 running XHTML for yourself by visiting examples on the Internet Explorer Test Drive site like SVG Helicopter, IE Beatz, and SVG-oids. In this post I’ll share a few details about XHTML and IE9's support for it.

What version of XHTML does IE9 support?

The short answer is XHTML5 (defined by the HTML5 specification). This means that new HTML5 elements such as <canvas>, <audio>, and <video> are all supported by XHTML in IE9. In fact, all of the same HTML (and SVG) elements and attributes that can be used in HTML in IE9 can also be used in XHTML in IE9. Moreover IE9 continues to follow "Same Markup" principles with XHTML just like with other parts of the platform, meaning most of the same XHTML markup should "just work" in the same way across IE9, Firefox, Chrome, etc.

How do I use XHTML in IE9?

Adding a <!DOCTYPE> pointing to an XHTML DTD does NOT influence whether a page is treated as HTML or XHTML. XHTML support for files on the web can only be triggered by the MIME type of the response from the web server. This is true both in IE9 and other browsers. This MIME type should be "application/xhtml+xml" (though you can technically use any supported XML mime type). Local files with ".xht" or ".xhtml" extensions will also be opened as XHTML.

You can verify the correct MIME type was sent to the browser using the "Network" tab in IE9's developer tools. Press F12 to open the tools, click "Start Capturing", and then refresh the page. The MIME type will be listed in the "Type" column for each file received from the server:

IE9 Dev tools, Network tab.

How does versioning impact XHTML?

IE9 will always run documents received with the "application/xhtml+xml" MIME type in IE9 Standards Mode. Not even the developer toolbar can override this behavior. The reason legacy document modes are not supported is because XHTML is new to IE9. Note that this means XHTML documents cannot be loaded into frames unless the parent page is also running in IE9 Standards Mode. These versioning rules also apply to SVG documents received as "image/svg+xml".

How does XHTML differ from HTML?

One of the most notable differences between XHTML and HTML is how parsing errors are handled. Any parsing error in an XHTML document will cause parsing to stop; no fix-up rules are applied. IE9 displays content parsed up until the point at which the error occurred. This is useful during development to catch errors quickly. You can find parsing error details in the "Console" tab of the developer toolbar (note you'll need to refresh the page to see the error if you opened the developer toolbar after the page loaded).

Another important difference is that XHTML is case-sensitive. For XHTML, this generally means that element and attribute names should be lowercased, both in markup and when referenced from script or CSS. Other languages embedded in XHTML may have elements and attributes with mixed case. Such elements and attributes must be written exactly as documented in the appropriate language specification. The "textPath" element from SVG is an example of this.

Yet another difference between HTML and XHTML is that XHTML supports namespaces in markup. This allows integration of XML languages beyond those explicitly defined in HTML5. Note that XHTML requires explicit namespace declarations for each language in use. This means that the root <html> element of an XHTML document must have the XHTML namespace declared in order to be interpreted properly:

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

Any embedded languages require their own namespace declarations as well. This is most easily done by placing the declaration on the start of the embedded sub-tree:

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
		<svg xmlns="http://www.w3.org/2000/svg" width="100" height="100">
			<circle fill="green" cx="50" cy="50" r="50"/>

Note that namespaces can also be associated with elements in other ways, though the approach outlined above generally results in markup that is more portable between HTML and XHTML. For a more in-depth explanation about authoring pages that validate in both HTML and XHTML, see the latest draft of the W3C's Polyglot Markup: HTML-Compatible XHTML Documents.

Next Steps

XHTML can be used today. Just be sure to apply feature detection when using XHTML while still supporting older browsers. Use server-side code to look at HTTP Accept header of incoming requests for the presence of "application/xhtml+xml" to determine if XHTML is supported by the requesting browser. If not, have your server fall back to returning polyglot markup as HTML (or some other reasonable alternative).

// Pseudo-code for server-side XHTML detection
// Pivots between sending polyglot markup as XHTML or HTML
IF request.headers["Accept"] CONTAINS "application/xhtml+xml"
	// XHTML is supported; use it
	response.headers["Content-Type"] = "application/xhtml+xml"
	// XHTML is not supported; fall back to HTML
	response.headers["Content-Type"] = "text/html"

Tony Ross

Program Manager

Comments (34)

  1. Alexandre says:

    Are there any advantages in IE9 of using XHTML over HTML, in addition the fact that XHTML is more extensible and cleaner?

    I am thinking of e.g. speed and features only available in XHTML mode.




  2. Steve says:

    Will IE9 support XML rendering like the IE6-8 did? The Beta currently does not.

  3. Randall says:

    Will/does IE9 not advertise support for application/xhtml+xml when a page load is triggered by an iframe in a document that isn't loaded in IE9 Standards mode?  Seems important for preserving backwards compatibility with sites that iframe arbitrary other sites that might be in XHTML.  If the framed site can't tell whether the browser will be able to handle an XHTML response (can't tell if it's being iframed by a non-Standards mode document or not), sometimes it'll serve an XHTML MIME type and won't be able to be displayed.

  4. Rob says:

    Wow. IE supports 13 year old technology that everyone else supported 13 years ago. Wow.

  5. J. King says:

    Rob, XHTML only became a recommendation ten years and nine months ago.  Even if we take the first working draft as the metric for age, it's still less than twelve years old.  I'm not sure when the first browser implementation came about (I don't care enough to check), but they're certainly younger than the first draft, I'd imagine.  You might want to get your facts straight before you go raking mud.  Just a thought.

  6. Sven says:

    Does IE9 behave correctly if you serve an XHTML1.1 page as application/xhtml+xml. What about the differences in the object model, CSS rule interpretation (particularly regarding the HTML element itself), and inline CSS and script parsing rules? Does IE9 behave the same as other browsers for those?

  7. Morton says:

    Hahaha……yeah ROB.  10 year-old technology is MUCH better than 13 year-old technology.

  8. gawicks says:

    Just got new that IE9 PP6 is top in the Official HTML5 Test Suite Conformance Results



  9. Michael A. Puls II says:

    "Local files with ".xht" or ".xhtml" extensions will also be opened as XHTML."

    You forgot the .xhtm extension. It should be supported as it's more common than .xht.

    Will document.body be available in xhtml documents?

    What about the  xml-stylehseet PI in xhtml documents? Will IE9 load stylesheets specified there?

    Also, what if you have a plain XML file with a script element somewhere in the middle with xmlns="http://www.w3.org/1999.xhtml&quot; on it? Will it execute JS in it like other browsers do?

    (I'd check myself, but I have WinXP)

  10. Andrey says:

    Developers IE9 work in Redmond?

  11. klkl says:

    Your detection code isn't standards-compliant. It will send XHTML to browsers that explicitly refuse it:

    Accept: text/html, application/xhtml+xml;q=0

  12. Lol says:

    And which browsers would those be, klkl?

  13. Patrick Garies says:

    @Michael A. Puls II:

    1. *.xhtml is not an official extension. See RFC3236. You can configure your server to support that if you want, of course, but I don't see any good reason to encourage the proliferation of unofficial extensions when official ones already exist.

    2. |document.body| returns |null| in IE9PP6. However, |document.getElementsByTagName("body").length| returns |0| while |document.getElementsByTagName("head").length| returns |1| in an ordinary XHTML document, so clearly there are bugs. (Per DOM3 Core, both should return |0| and, per Web DOM Core, both should return |1|.)

    3. IE9PP6 seems to support CSS via |xml-stylesheet| PIs. It doesn't not seem to support XSLT via such PIs though despite trying two file extensions (*.xsl and *.xslt) and three MIME types (text/xsl, application/xml, and application/xslt+xml) in the |href| pseudo-attribute.

    4. IE9PP6 seems to load scripts called from an XHTML |script| element placed in a generic XML document based on a simple |window.alert| test.

  14. Patrick Garies says:

    Sorry, "*.xhtml is not…" should be "*.xhtm is not…"

  15. piotr says:

    Hm, what is a purpose of sending XHTML as text/html? Isn't better just to use HTML 4.x or 5?

  16. the_dees says:


    No browser implements XHTML 1.1 because it was incompatible to XHTML 1.0 for most of its life span. Today it is almost the same as XHTML 1.0 Strict, except that you can't use the lang attribute.

    XHTML 1.1 is a dead end. The succesor of XHTML 1.0 is XHTML5.


    Code that looks like XHTML but uses text/html is simple HTML, nothing else. In former times, that meant sending invalid HTML (as <br/> is actually <br>>), but these issues are fixed in most browsers (and standarized in the HTML5 parser, which Gecko and WebKit will implement in their upcoming releases).

    I personally don't see any advantage in XHTML compared to HTML at least on the client side.

  17. Michael A. Puls II says:

    Thanks Patrick!

  18. Michael A. Puls II says:


    Yes, RFC3236 doesn't list .xhtm. But, .xhtm is to .xhtml like .htm is to .html. It's an intuitive thing. (Opera supports .xht, .xhtm and .xhtml for local file association and for triggering xhtml mode for local files. I've used both .xhtm and .xhtml, but never .xht)

  19. Bertil Wennergren says:


    "No browser implements XHTML 1.1"

    So how come my pages, served as XHTML 1.1 to browsers that claim support for XTHML in the accept, header, do work perfectly well in Firefox? Have I missed something? To me it does seem like Firefox supports XHTML 1.1. Actually I believe that Safari, Chrome and Opera do too.

    Test here: "http://bertilow.com&quot;.   If you use Firefox or some other modern browser, you'll get XHTML 1.1.

    So what about MSIE 9? Will XHTML 1.0 and XHTML 1.1 – served as "application/xhtml+xml" – work or not?

    "XHTML 1.1 is a dead end."

    That is most probably true.

  20. Former IE loyalist says:

    Dear IE team, I am having extreme heartburn using the IE9 beta due to a lack of the green progress bar and how it used to say "Done" when loading a page. The spinning Aero cursor doesn't cut it.

  21. Stifu says:

    @Michael A. Puls II:

    ".htm" was made up to fit the extension into 3 letters, so ".xhtm" doesn't make much sense as it becomes 4 letters. 2 different extensions for one file type already adds enough confusion as is, no need to add a 3rd one. What if Super XHTML comes up, should 4 different extensions be supported?

  22. raw says:

    The iframe element should follow the css border:none and overflow:hidden to hide the border and scrollbar.

    frameborder and scrolling are no longer allowed in the HTML 5 spec.

  23. mmm says:

    Where can i find IE9 roadmap? Will be more public betas ?

  24. yellowstone says:

    .wdp File and .jxr File…. !!!SUPPORT(.wdp, .hdp, jxr etc    Support…)

    I'm can not Speak English ^^;;

    Thank you

  25. Mario says:


    I downloaded The Newest platform preview and I saw that the buttons on sites like the tweet button on twitter is not round it should be round but it is a square on ie please fix this!

  26. Green bars says:

    Hello, you should  Make it so that the status bar a.k.a the loading bar that tells you when a webpage is done loading still there but you just see it if you hover the mouse over the area where it is. but just make it do this when a webpage is loading 😛

  27. the_dees says:

    @Bertil Wennergren

    "So how come my pages, served as XHTML 1.1 to browsers that claim support for XTHML in the accept, header, do work perfectly well in Firefox? Have I missed something? To me it does seem like Firefox supports XHTML 1.1. Actually I believe that Safari, Chrome and Opera do too."

    Long story.

    As you say, a browser can state it accepts the application/xhtml+xml media type. Note that there is no version indicator.

    It's probably important to note that todays XHTML 1.1 is almost the same as XHTML 1.0, however that was a long fight.

    When XHTML 1.1 came out (became a REC) it contained several contradictions to XHTML 1.0 (no lang attribute allowed, no text/html allowed, a bug in the handling of client side image maps, different CSS handling).

    That wouldn't have been a problem, but unfortunately the W3C decided that XHTML 1.1 "lives" in the same namespace as XHTML 1.0 does. So if a browser receives a document labled application/xhtml+xml and namespace http://www.w3.org/1999/xhtml/ it can not decide what version of the language the document is written in.

    To solve this problem on the browser side there are three solutions: a) Implement doctype switching in XML, b) do not implement XHTML 1.1 or c) do not implement XHTML 1.0 anymore.

    For a while, browsers tried a) which led to several bug reports and critic on the bad influence on the XML ecosystem.

    It's not like browser vendors didn't want to implement XHTML 1.1 – they even tried for years to fix the issues in XHTML 1.1, but their tries were in vain.

    Then, the WHATWG and HTML5 appeared. HTML5 defines its vocabulary to be backwards compatible to HTML 4.01 and XHTML 1.0, so in the end, browser vendors decided to not implement XHTML 1.1 because a XHTML 1.0 is a perfectly fine subset of XHTML5.

    Most XHTML 1.1 issues are resolved as of today, the only real issue in my opinion is that it still doesn't allow the lang attribute.

    You probaly got it by now, your XHTML 1.1 code simply works because the browser can't tell it's XHTML 1.1 – and even if it could, you probably wouldn't notice a difference anymore.

    However, keeping in mind that HTML5 introduced the widely used ruby elements for HTML and XHTML, there is no real advantage in using XHTML 1.1 anymore.

    So in short, XHTML (without version number) sill simply work in IE9 and all other browsers.

  28. IronTed says:

    Your support of HTML5 is a bunch of BS!  You only selectively support some elements of Canvas in order to protect Silverlight.   I don't see any need for IE in my enterprise.  Because I have Firefox, Chrome, Opera and Safari.

  29. Bertil Wennergren says:


    "Most XHTML 1.1 issues are resolved as of today, the only real issue in my opinion is that it still doesn't allow the lang attribute."

    I use "xml:lang" as the XHTML 1.1 rules say I should. It seems to work, at least in Firefox. What actual breakage or problems do you see happening? I see none.

  30. jabcreations says:

    Firefox's RSS feed reader doesn't update regularly for MSDN for some reason…hm…

    Well I applaud finally supporting XHTML as application/xhtml+xml however instead of rendering up to an error it would make more sense to not display the page and display an error message instead like Gecko and Presto do. Presto handles it best by allowing the user to render the page as text/html. This has a VERY large bearing on why I test with Gecko first and Presto secondly. WebKit doesn't break the page and I think KHTML doesn't either so I test with WebKit third and up to this point with IE last. Since IE9 isn't available on XP I will continue to test with it last because it's the least convenient requiring tons of RAM for virtualization.

    Handling the mime with PHP…



    if (isset($_SERVER['HTTP_ACCEPT']))


    $mime_ua = stristr($_SERVER['HTTP_ACCEPT'],'application/xhtml+xml');

    if ($mime_ua) {$mime = 'application/xhtml+xml';}

    else {$mime = 'text/html';}


    else {$mime = 'text/html';}

    header('content-type: '.$header->mime.'; charset=utf-8');

    echo '<?xml version="1.0" encoding="UTF-8"?>'."n";


    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/…/xhtml11.dtd"&gt;


    It should be noted that AJAX content loaded via importNode (innerHTML should NOT be used EVER) should be served as text/xml.

    I like the idea of NOT implementing quirks mode for XHTML, that's a good move.

    But limiting IE9 to Vista/7 is NOT a smart move. Want us to "upgrade"? Tell the Windows team to stop removing all the ACTUALLY useful things and shortcuts from Windows. Heck there isn't even an "Explore" option in the context menu on the My Documents or My Computer icon in 7 and I couldn't effectively move the ENTIRE My Documents folder to the D: for a client last week as IE was still saved files to the C:. This isn't guess work or trying to figure out how to one-up Apple, it's listening to users who actually use their machines for production and as power users. Oh and fix IE9's totally borked GUI, less isn't more, it's less. Having you guys actually listen to CRITICAL input besides standards compliance is like trying to tell Linux fan boys to just make the start key with with their version of the start menu. End users and ESPECIALLY people like myself who do production are having to put up with worse and worse software GUI while hardware is getting more and more awesome.

  31. Patrick Garies says:

    @the_dees: XHTML 1.1 supports complex ruby markup whereas HTML5 does not. That, rather than |lang| attribute differences, is probably the most major difference between XHTML 1.1 and HTML5. That problem is more with Ruby Annotations and CSS3 Ruby specs being too vague and poorly thought through than with XHTML 1.1 though, so we may yet see more complete de facto XHTML 1.1 support in the future when those specs have been scrapped or rewritten.

    There was another difference: modularity (hence the spec title: "Module-based XHTML"). But, given that implementors apparently don't plan to ever support validation against DTDs, that feature is optional per XML, and people can write their own XML schema, that feature has been pretty much invisible and will probably remain that way.

  32. the_dees says:

    @Bertil Wennergren:

    There is no problem with xml:lang (nowadays). But the xml:lang attribute has had the problem of being unrecognized by browsers or assistive technology. It's not a problem anymore.

    However, note that in XHTML 1.0 you can use the lang attribute to define the language of an element, and in XHTML 1.1 you can not. Thus both are incompatible. A browser that implemented XHTML 1.1 wouldn't be allowed to look for lang attributes in XHTML documents. It would've to be treated like any other attribute xyz.

    It works in modern browsers (and even older ones) because XHTML 1.1 documents are simply treated like XHTML 1.0 documents.

    @Patrick Garies:

    Let's assue a browser implemented XHTML 1.1 completly (including CSS Ruby and the Ruby Annotations Spec). In this scenario, HTML5 would automatically have Ruby support as well. That is not a thing of specifications but of implementations. And that is the crux of the matter. Something implemented in abrowser will work in any document. But if that meant either one document mode or another (which do not really exist) had a bug, a spec is not implementable.

    Module-based XHTML sounds nice in theory but it is just a nice concept that wasn't ever needed. Technology evolved way too fast to make this concept needed. You see HTML parsers in mobile browsers. Something no one thought would be possible.

Skip to main content