Browser detection versus feature detection

One of the more controversial chapters in my first book was the chapter on browser detection. I got flaming emails, blog comments, and reviews about the user-agent string detecting method, telling me that I was falsely promoting an outdated methodology for dealing with browser differences. Feature detection is the ideal, they all said, and that is the only thing you should be teaching. But alas, life is not so easy.

In an ideal world, feature detection would work perfectly. I’d just see if an element supported addEventListener before using it. No need for knowing what specific browser you’re using. For a decent amount of JavaScript code, this technique works perfectly. However, there are times when it is absolutely necessary to know the browser being used because of the biggest problem in the browser space today: incorrect implementations.

Using feature detection for a method or property is great when all browsers implement them the same way. However, there are cases when browsers implement them differently or implement only stubs. Take the min-height CSS property, which wasn’t supported in Internet Explorer prior to version 7.0. One would think that style.minHeight would be undefined, so using feature detection would be easy. However, version 6.0 reports this value as a string, and it can be set and read as if it’s actually implemented; the only problem, of course, is that it’s not. So in this case, feature detection doesn’t help the cause…you need to know that the browser is Internet Explorer version 6.0 and, in that case, style.minHeight doesn’t work.

This is just one example of feature detection falling on its face. Another was the getElementsByTagName("*") debacle. Internet Explorer prior to 6.0 supported getElementsByTagName(), but not when passing in an asterisk to get all elements. Yet another is the table-specific DOM methods that were implemented as stubs in Internet Explorer 5 for the Mac (they existed, they just didn’t do anything). Further, both Firefox and Opera implemented document.all so that web sites designed for Internet Explorer wouldn’t break; so much for that feature detection classic.

My point here is that user-agent string detection is still the most accurate way to determine what browser is being used, and this can, in some cases, be more valuable than using feature detection. Feature detection is a good practice and should always be used first, but if there are implementation differences that are bogging you down, don’t hesitate to look to the user-agent string for help in determining what to do.

Understanding JavaScript Promises E-book Cover

Demystify JavaScript promises with the e-book that explains not just concepts, but also real-world uses of promises.

Download the Free E-book!

The community edition of Understanding JavaScript Promises is a free download that arrives in minutes.