the open web, web development, and more

Friday, October 17, 2008

Why Lenient Browsers are Evil

Evil might be a strong word, but it accurately conveys my frustration with web browsers and how their overly forgiving parsing rules can lead to a lot of wasted time.

The particular browser leniency I am talking about is the auto-insertion of the <tbody> element into an HTML table. Given that I try to use semantic markup whenever possible, I rarely use tables and therefore my knowledge of table markup goes back to pre-web 2.0 to when every part of a page resided in a table cell. At that time, table markup typically looked like:


<table cellspacing="0" cellpadding="0" border="0">
<tr>
<td>Foo</td>
<td>Bar</td>
</tr>
</table>

Yes, this is really simple and in reality would contain a table within table within table and nasty shims, but I think you get the point. However, what isn't apparent from this markup (and you are excused from forgetting) is that this is an invalid table because of the missing <tbody> tags around the table row. Instead of breaking the page though, the browser will just auto-insert the missing tags into its internal version of the page (a.k.a the DOM).

This doesn't seem all that evil yet and really just makes writing the HTML easier. However, fast forward this browser trait to the world of Ajax and manipulating the DOM and it becomes rather annoying. For example, take the same table and add some ids:

<table cellspacing="0" cellpadding="0" border="0" id="parent">
<tr id="child">
<td>Foo</td>
<td>Bar</td>
</tr>
</table>

Then run some simple JavaScript to delete the table row:

var parent = document.getElementById("parent");
var child = document.getElementById("child");
parent.removeChild(child);

And boom! This doesn't work because the child element is not a child of the <table> element, but of the magically inserted <tbody> element. The DOM would actually look like this:

<table cellspacing="0" cellpadding="0" border="0" id="parent">
<tbody>
<tr id="child">
<td>Foo</td>
<td>Bar</td>
</tr>
</tbody>
</table>

The terrible thing is you would not know this unless you used a tool like Firebug to inspect the DOM and see that the browser inserted the <tbody> tag to "help" you.

No comments:

Post a Comment