From eb58768e32baf13b45d9649743d7ef45798ffb27 Mon Sep 17 00:00:00 2001 From: Friedel Ziegelmayer Date: Sat, 6 Apr 2013 21:55:55 +0200 Subject: [PATCH] feat(helper): Improve useragent detection. By using the module 3rd-Eden/useragent instead of a homegrown solution we are able to parse a much wider range of useragent strings. Fixes #373, #318. --- lib/helper.js | 33 +++------------------------------ package.json | 3 ++- test/unit/browser.spec.coffee | 8 +++++--- test/unit/helper.spec.coffee | 32 +++++++++++++++++++------------- 4 files changed, 29 insertions(+), 47 deletions(-) diff --git a/lib/helper.js b/lib/helper.js index 84c8d2239..707b3329b 100644 --- a/lib/helper.js +++ b/lib/helper.js @@ -1,39 +1,12 @@ var fs = require('fs'); var path = require('path'); var _ = require('lodash'); +var useragent = require('useragent'); -var OS = /(iPhone OS|Mac OS X|Windows|Linux)/; -var OS_MAP = { - 'iPhone OS': 'iOS', - 'Mac OS X': 'Mac' -}; - -var BROWSER = /(Chrome|Firefox|Opera|Safari|PhantomJS)\/([0-9]*\.[0-9]*)/; -var VERSION = /Version\/([0-9]*\.[0-9]*)/; -var MSIE = /MSIE ([0-9]*\.[0-9]*)/; - -// TODO(vojta): parse IE, Android, iPhone, etc... exports.browserFullNameToShort = function(fullName) { - var os = ''; - var osMatch = fullName.match(OS); - if (osMatch) { - os = osMatch[1]; - os = ' (' + (OS_MAP[os] || os) + ')'; - } - - var browserMatch = fullName.match(BROWSER); - if (browserMatch) { - var versionMatch = fullName.match(VERSION); - return browserMatch[1] + ' ' + (versionMatch && versionMatch[1] || browserMatch[2]) + os; - } - - var ieMatch = fullName.match(MSIE); - if (ieMatch) { - return 'IE ' + ieMatch[1] + os; - } - - return fullName; + var agent = useragent.parse(fullName); + return agent.toAgent() + ' (' + agent.os + ')'; }; diff --git a/package.json b/package.json index 18437e087..673dc7d7d 100644 --- a/package.json +++ b/package.json @@ -81,7 +81,8 @@ "lodash": "~1.1", "pause": "0.0.1", "mime": "~1.2", - "log4js": "~0.6.3" + "log4js": "~0.6.3", + "useragent": "~2.0.4" }, "peerDependencies": { "karma-jasmine": "*", diff --git a/test/unit/browser.spec.coffee b/test/unit/browser.spec.coffee index 33fbc698c..0da1d8f26 100644 --- a/test/unit/browser.spec.coffee +++ b/test/unit/browser.spec.coffee @@ -52,9 +52,11 @@ describe 'browser', -> describe 'onRegister', -> it 'should set fullName and name', -> - browser.onRegister name: 'Chrome/16.0 full name' - expect(browser.name).to.equal 'Chrome 16.0' - expect(browser.fullName).to.equal 'Chrome/16.0 full name' + fullName = 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_6_8) AppleWebKit/535.7 ' + + '(KHTML, like Gecko) Chrome/16.0.912.63 Safari/535.7' + browser.onRegister name: fullName + expect(browser.name).to.equal 'Chrome 16.0.912 (Mac OS X 10.6.8)' + expect(browser.fullName).to.equal fullName it 'should set launchId', -> diff --git a/test/unit/helper.spec.coffee b/test/unit/helper.spec.coffee index af5869d65..5fbc2d724 100644 --- a/test/unit/helper.spec.coffee +++ b/test/unit/helper.spec.coffee @@ -16,81 +16,87 @@ describe 'helper', -> it 'should parse iOS', -> expecting('Mozilla/5.0 (iPhone; CPU iPhone OS 6_0 like Mac OS X) AppleWebKit/536.26 ' + '(KHTML, like Gecko) Version/6.0 Mobile/10A403 Safari/8536.25'). - to.be.equal 'Safari 6.0 (iOS)' + to.be.equal 'Mobile Safari 6.0.0 (iOS 6.0)' it 'should parse Linux', -> expecting('Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.8.1.19) Gecko/20081216 ' + 'Ubuntu/8.04 (hardy) Firefox/2.0.0.19'). - to.be.equal 'Firefox 2.0 (Linux)' + to.be.equal 'Firefox 2.0.0 (Ubuntu 8.04)' it 'should degrade gracefully when OS not recognized', -> expecting('Mozilla/5.0 (X11; U; FreeBSD; i386; en-US; rv:1.7) Gecko/20081216 ' + 'Firefox/2.0.0.19'). - to.be.equal 'Firefox 2.0' + to.be.equal 'Firefox 2.0.0 (FreeBSD)' it 'should parse Chrome', -> expecting('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_6_8) AppleWebKit/535.7 ' + '(KHTML, like Gecko) Chrome/16.0.912.63 Safari/535.7'). - to.be.equal 'Chrome 16.0 (Mac)' + to.be.equal 'Chrome 16.0.912 (Mac OS X 10.6.8)' expecting('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_6_8) AppleWebKit/535.15 ' + '(KHTML, like Gecko) Chrome/18.0.985.0 Safari/535.15'). - to.be.equal 'Chrome 18.0 (Mac)' + to.be.equal 'Chrome 18.0.985 (Mac OS X 10.6.8)' it 'should parse Firefox', -> expecting('Mozilla/5.0 (Macintosh; Intel Mac OS X 10.6; rv:7.0.1) Gecko/20100101 ' + 'Firefox/7.0.1'). - to.be.equal 'Firefox 7.0 (Mac)' + to.be.equal 'Firefox 7.0.1 (Mac OS X 10.6)' it 'should parse Opera', -> expecting('Opera/9.80 (Macintosh; Intel Mac OS X 10.6.8; U; en) Presto/2.9.168 ' + 'Version/11.52'). - to.be.equal 'Opera 11.52 (Mac)' + to.be.equal 'Opera 11.52.0 (Mac OS X 10.6.8)' it 'should parse Safari', -> expecting('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_6_8) AppleWebKit/534.52.7 ' + '(KHTML, like Gecko) Version/5.1.2 Safari/534.52.7'). - to.be.equal 'Safari 5.1 (Mac)' + to.be.equal 'Safari 5.1.2 (Mac OS X 10.6.8)' it 'should parse IE7', -> expecting('Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.0; WOW64; SLCC1; ' + '.NET CLR 2.0.50727; .NET4.0C; .NET4.0E)'). - to.be.equal 'IE 7.0 (Windows)' + to.be.equal 'IE 7.0.0 (Windows Vista)' it 'should parse IE8', -> expecting('Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; ' + 'SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; .NET4.0C; ' + '.NET4.0E; InfoPath.3)"'). - to.be.equal 'IE 8.0 (Windows)' + to.be.equal 'IE 8.0.0 (Windows 7)' it 'should parse IE9', -> expecting('Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Win64; x64; Trident/5.0; ' + '.NET CLR 2.0.50727; SLCC2; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center ' + 'PC 6.0)'). - to.be.equal 'IE 9.0 (Windows)' + to.be.equal 'IE 9.0.0 (Windows 7)' it 'should parse IE10', -> expecting('Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0; ' + '.NET4.0E; .NET4.0C)'). - to.be.equal 'IE 10.0 (Windows)' + to.be.equal 'IE 10.0.0 (Windows 8)' it 'should parse PhantomJS', -> expecting('Mozilla/5.0 (Macintosh; Intel Mac OS X) AppleWebKit/534.34 (KHTML, like Gecko) ' + 'PhantomJS/1.6.0 Safari/534.34'). - to.be.equal 'PhantomJS 1.6 (Mac)' + to.be.equal 'PhantomJS 1.6.0 (Mac OS X)' + # Fix for #318 + it 'should parse old Android Browser', -> + expecting('Mozilla/5.0 (Linux; U; Android 4.2; en-us; sdk Build/JB_MR1) ' + + 'AppleWebKit/534.30 (KHTML, like Gecko) Version/4.0 Mobile Safari/534.30'). + to.be.equal 'Android 4.2.0 (Android 4.2)' + #============================================================================== # helper.isDefined() #==============================================================================