I enjoyed my last experiment to create tiny browser detection hacks, so I thought I’d try and do some more in other browsers. I’ve found these while testing Hackvertor and writing the inspection functions. The rules are simple if you want to post your own:-
1. The variable assignment must be the abbreviation of the browser. E.g. FF, IE, Op, Saf, Chr.
2. The detection shouldn’t be able to be overwritten. E.g. IE=!!top.execScript is incorrect because a web site can redefine execScript as a variable or function.
3. Small and as fast as possible please.
To start off, this one was found by DoctorDan from the slackers forums:-
//Firefox detector 2/3 by DoctorDan
FF=/a/[-1]=='a'
//Firefox 3 by me:-
FF3=(function x(){})[-5]=='x'
//Firefox 2 by me:-
FF2=(function x(){})[-6]=='x'
//IE detector I posted previously
IE='\v'=='v'
//Safari detector by me
Saf=/a/.__proto__=='//'
//Chrome by me
Chr=/source/.test((/a/.toString+''))
//Opera by me
Op=/^function \(/.test([].sort)
//IE6 detector using conditionals
try {IE6=@cc_on @_jscript_version <= 5.7&&@_jscript_build<10000} catch(e){IE6=false;}
As I come across more developing Hackvertor I shall post them here. Please post your own or verify any of the ones posted.
Update…
One line to rule them all:-
B=(function x(){})[-5]=='x'?'FF3':(function x(){})[-6]=='x'?'FF2':/a/[-1]=='a'?'FF':'\v'=='v'?'IE':/a/.__proto__=='//'?'Saf':/s/.test(/a/.toString)?'Chr':/^function \(/.test([].sort)?'Op':'Unknown'
Comments 34
Nice!
Posted 29 Jan 2009 at 10:01 am ¶That is pretty epic I wont lie. *Blogs this*
Posted 29 Jan 2009 at 11:26 am ¶I can make it smaller if you’re not interested in which version of FF:-
B=/a/[-1]==’a'?’FF’:'\v’==’v'?’IE’:/a/.__proto__==’//’?'Saf’:/s/.test(/a/.toString)?’Chr’:'Op’
//94!
Posted 29 Jan 2009 at 11:52 am ¶This is pretty insane, man!
I sure do hope it gets implemented in jQuery’s and the other libraries’ cores…
Posted 29 Jan 2009 at 2:07 pm ¶It gives ‘Op’ in FF3.1 beta2.
Posted 29 Jan 2009 at 2:36 pm ¶@Sam
I’ve updated the one rule, please try again. If you can please run this hackvertor code to see what results in FF3.1 beta :-
http://www.businessinfo.co.uk/labs/hackvertor/hackvertor.php?input=Ly9DbGljayAiaW5zcGVjdCBvdXRwdXQiCmFsZXJ0
Posted 29 Jan 2009 at 2:47 pm ¶Another little change would be a CSS-Selector in 252 Bytes:
document.getElementsByTagName(’html’)[0].className+=’ ‘+(function x(){})[-5]==’x'?’FF3′:(function x(){})[-6]==’x'?’FF2′:/a/[-1]==’a'?’FF’:'\v’==’v'?’IE’:/a/.__proto__==’//’?'Saf’:/s/.test(/a/.toString)?’Chr’:/^function \(/.test([].sort)?’Op’:'Unknown’
You can use:
.IE .example { color: red; }
.FF2 . example { color: lime; }
etc…
(classNames are case sensitive!)
Have fun
Posted 30 Jan 2009 at 9:08 am ¶One obvious point is that browser detection is something that should be avoided wherever possible - feature detection should be used instead otherwise your website won’t work on the next browser released…
Posted 30 Jan 2009 at 10:03 am ¶Opera test doesn’t quite satisfy your rules, as it can be easily overwritten:
Array.prototype.sort.toString = function(){ return ‘function (){}’ }
/^function \(/.test([].sort); // true
Posted 31 Jan 2009 at 3:31 am ¶Safari check can be fooled in the very same way, of course:
RegExp.prototype.toString = function(){ return ‘//’ };
Posted 31 Jan 2009 at 3:35 am ¶/a/.__proto__==’//’; // true
These are most excellent. I just used a few in a bookmarklet for adding new css rules to the page
The safari test only catches safari proper and not the webkit-also Chrome… Do you have a clever solution to catch both? (I recognize they’re different js engines, but come on.. you’re clever.
Posted 04 Feb 2009 at 6:45 pm ¶@Paul
I’ve not got Chrome handy at the moment because I’m on a different computer. However this should work:-
WebKit=typeof document.body.style.WebkitAppearance==’string’;
This can be overwritten though so technically it breaks the rules but it might be good enough for what you want.
Posted 04 Feb 2009 at 10:33 pm ¶Just to confirm it does work in Chrome and Safari
Posted 05 Feb 2009 at 2:06 pm ¶Gareth, you are a machine. Well done.
Posted 06 Feb 2009 at 6:35 pm ¶Nice stuff!
Posted 16 Mar 2009 at 1:06 pm ¶The Opera test does not work in 9.2x
Posted 08 Apr 2009 at 10:53 pm ¶IE=@cc_on true ? true : @false;
Internet Explorer supports <a href=”http://msdn.microsoft.com/en-us/library/ahx1z4fs(VS.80).aspx”>conditional compilation</a> which can be used to accurately detect its version:
IE8=@cc_on @_jscript_version == 5.8 ? true : @false
IE7=@cc_on @_jscript_version == 5.7 ? true : @false
IE6=@cc_on @_jscript_version == 5.6 ? true : @false
IE55=@cc_on @_jscript_version == 5.5 ? true : @false
Posted 24 Apr 2009 at 8:51 pm ¶My asterisks and slashes have vanished.
There should be a block comment opened right before each @cc_on, and closed after the final @.
Posted 24 Apr 2009 at 8:53 pm ¶@Gyrobo
Sorry about that I remove comments from Wordpress to avoid SQL injection attacks.
Conditional comments work well but not when the code is compressed
Posted 25 Apr 2009 at 6:44 am ¶Quite a great effect.
Posted 25 Apr 2009 at 1:12 pm ¶Thanks for sharing.
Well then, I guess I learned something about both compression and SQL injection. Yay!
Posted 28 Apr 2009 at 12:37 pm ¶Хорошая статья, больше бы таких!
Posted 25 Jun 2009 at 12:38 pm ¶А подробнее можно?
Posted 31 Jul 2009 at 11:17 am ¶Да, больше невозможно. Попробуйте JavaScript обнаружения CSS свойства как МОЗ или MS-т.д.
Posted 31 Jul 2009 at 11:51 am ¶hello,
great stuff! it seems that the one line detector is just returning ‘FF’ for firefox 3.5.1 mac+win. Any chance of a fix?
best,
Posted 04 Aug 2009 at 4:33 pm ¶-D
@d
This should detect FF3.5 and above:-
FF3=(/a/[-1]&&Object.getPrototypeOf)?true:false
Posted 04 Aug 2009 at 5:01 pm ¶Just wanted to share two hacks I’m currently using (in LABjs) for detecting Firefox(Gecko) and for detecting Opera:
is_opera = window.opera && Object.toString.call(window.opera) == “[object Opera]”
is_gecko = (function(o) { o[o] = o+”"; return o[o] != o+”"; })(new String(”__count__”))
Posted 01 Dec 2009 at 3:47 pm ¶@gareth:
Posted 01 Dec 2009 at 7:22 pm ¶thanks brother!
The IE check can be shortened to:
Posted 17 Dec 2009 at 12:14 pm ¶@Mathias
Yeah someone already pointed that out:-
http://sla.ckers.org/forum/read.php?2,15812,26331,page=13#msg-26331
Posted 17 Dec 2009 at 12:28 pm ¶I didn’t know that. thank you
Posted 18 Dec 2009 at 1:32 pm ¶When I run the one-liner in Mac Google Chrome, I get “Unknown”.
Any chance someone could update the one-liner to work with Mac Google Chrome?
Posted 23 Dec 2009 at 1:36 am ¶/a/[-1]==’a’ isn’t work on firefox3.6
Posted 09 Feb 2010 at 2:10 pm ¶@superhei
Yep Mozilla decided this was a security issue when I reported it so these techniques can no longer be expected to work in later versions of Firefox
Posted 09 Feb 2010 at 2:13 pm ¶Post a Comment