user_agent_parser 1.0.0 → 2.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of user_agent_parser might be problematic. Click here for more details.

@@ -1,37 +1,47 @@
1
1
  module UserAgentParser
2
-
3
2
  class Version
4
3
 
5
- attr_accessor :version
4
+ # Private: Regex used to split version string into major, minor, patch,
5
+ # and patch_minor.
6
+ SEGMENTS_REGEX = /\d+\-\d+|\d+[a-zA-Z]+$|\d+|[A-Za-z][0-9A-Za-z-]*$/
7
+
8
+ attr_reader :version
6
9
  alias :to_s :version
7
10
 
8
11
  def initialize(version)
9
- self.version = version.to_s.strip
12
+ @version = version.to_s.strip
10
13
  end
11
14
 
12
- def segments
13
- version.scan(/\d+\-\d+|\d+[a-zA-Z]+$|\d+|[A-Za-z][0-9A-Za-z-]*$/).map do |s|
14
- /^\d+$/ =~ s ? s.to_i : s
15
- end
15
+ def major
16
+ segments[0]
17
+ end
18
+
19
+ def minor
20
+ segments[1]
21
+ end
22
+
23
+ def patch
24
+ segments[2]
16
25
  end
17
26
 
18
- def [](segment)
19
- segments[segment]
27
+ def patch_minor
28
+ segments[3]
20
29
  end
21
-
22
- def major; self[0] end
23
- def minor; self[1] end
24
- def patch; self[2] end
25
- def patch_minor; self[3] end
26
-
30
+
27
31
  def inspect
28
32
  "#<#{self.class} #{to_s}>"
29
33
  end
30
-
31
- def ==(other)
32
- version == other.version
34
+
35
+ def eql?(other)
36
+ self.class.eql?(other.class) &&
37
+ version == other.version
33
38
  end
34
39
 
35
- end
40
+ alias_method :==, :eql?
36
41
 
37
- end
42
+ # Private
43
+ def segments
44
+ @segments ||= version.scan(SEGMENTS_REGEX)
45
+ end
46
+ end
47
+ end
@@ -1,9 +1,10 @@
1
1
  user_agent_parsers:
2
2
  #### SPECIAL CASES TOP ####
3
3
 
4
- # must go before Opera
5
- - regex: '^(Opera)/(\d+)\.(\d+) \(Nintendo Wii'
6
- family_replacement: 'Wii'
4
+ # HbbTV standard defines what features the browser should understand.
5
+ # but it's like targeting "HTML5 browsers", effective browser support depends on the model
6
+ # See os_parsers if you want to target a specific TV
7
+ - regex: '(HbbTV)/(\d+)\.(\d+)\.(\d+) \('
7
8
 
8
9
  # must go before Firefox to catch SeaMonkey/Camino
9
10
  - regex: '(SeaMonkey|Camino)/(\d+)\.(\d+)\.?([ab]?\d+[a-z]*)'
@@ -14,7 +15,7 @@ user_agent_parsers:
14
15
  - regex: '(Fennec)/(\d+)\.(\d+)\.?([ab]?\d+[a-z]*)'
15
16
  family_replacement: 'Firefox Mobile'
16
17
  - regex: '(Fennec)/(\d+)\.(\d+)(pre)'
17
- family_replacment: 'Firefox Mobile'
18
+ family_replacement: 'Firefox Mobile'
18
19
  - regex: '(Fennec)/(\d+)\.(\d+)'
19
20
  family_replacement: 'Firefox Mobile'
20
21
  - regex: 'Mobile.*(Firefox)/(\d+)\.(\d+)'
@@ -65,17 +66,25 @@ user_agent_parsers:
65
66
  - regex: '(Opera Mini)/att/(\d+)\.(\d+)'
66
67
  - regex: '(Opera)/9.80.*Version/(\d+)\.(\d+)(?:\.(\d+))?'
67
68
 
69
+ # Opera 14 for Android uses a WebKit render engine.
70
+ - regex: '(?:Mobile Safari).*(OPR)/(\d+)\.(\d+)\.(\d+)'
71
+ family_replacement: 'Opera Mobile'
72
+
73
+ # Opera 15 for Desktop is similar to Chrome but includes an "OPR" Version string.
74
+ - regex: '(?:Chrome).*(OPR)/(\d+)\.(\d+)\.(\d+)'
75
+ family_replacement: 'Opera'
76
+
68
77
  # Palm WebOS looks a lot like Safari.
69
- - regex: '(webOSBrowser)/(\d+)\.(\d+)'
70
- - regex: '(webOS)/(\d+)\.(\d+)'
71
- family_replacement: 'webOSBrowser'
72
- - regex: '(wOSBrowser).+TouchPad/(\d+)\.(\d+)'
73
- family_replacement: 'webOS TouchPad'
78
+ - regex: '(hpw|web)OS/(\d+)\.(\d+)(?:\.(\d+))?'
79
+ family_replacement: 'webOS Browser'
74
80
 
75
81
  # LuaKit has no version info.
76
82
  # http://luakit.org/projects/luakit/
77
83
  - regex: '(luakit)'
78
84
  family_replacement: 'LuaKit'
85
+
86
+ # Snowshoe
87
+ - regex: '(Snowshoe)/(\d+)\.(\d+).(\d+)'
79
88
 
80
89
  # Lightning (for Thunderbird)
81
90
  # http://www.mozilla.org/projects/calendar/lightning/
@@ -88,6 +97,8 @@ user_agent_parsers:
88
97
  family_replacement: 'Swiftfox'
89
98
 
90
99
  # Rekonq
100
+ - regex: '(rekonq)/(\d+)\.(\d+)\.?(\d+)? Safari'
101
+ family_replacement: 'Rekonq'
91
102
  - regex: 'rekonq'
92
103
  family_replacement: 'Rekonq'
93
104
 
@@ -105,19 +116,18 @@ user_agent_parsers:
105
116
  - regex: '(Comodo_Dragon)/(\d+)\.(\d+)\.(\d+)'
106
117
  family_replacement: 'Comodo Dragon'
107
118
 
108
- # YottaaMonitor bot
109
- - regex: '(YottaaMonitor)'
110
-
111
- # must go before NetFront below
112
- - regex: '(Kindle)/(\d+)\.(\d+)'
119
+ # Bots
120
+ - regex: '(YottaaMonitor|BrowserMob|HttpMonitor|YandexBot|Slurp|BingPreview|PagePeeker|ThumbShotsBot|WebThumb|URL2PNG|ZooShot|GomezA|Catchpoint bot|Willow Internet Crawler|Google SketchUp|Read%20Later)'
113
121
 
114
122
  - regex: '(Symphony) (\d+).(\d+)'
115
123
 
116
- - regex: 'Minimo'
124
+ - regex: '(Minimo)'
117
125
 
118
126
  # Chrome Mobile
119
127
  - regex: '(CrMo)/(\d+)\.(\d+)\.(\d+)\.(\d+)'
120
128
  family_replacement: 'Chrome Mobile'
129
+ - regex: '(CriOS)/(\d+)\.(\d+)\.(\d+)\.(\d+)'
130
+ family_replacement: 'Chrome Mobile iOS'
121
131
  - regex: '(Chrome)/(\d+)\.(\d+)\.(\d+)\.(\d+) Mobile'
122
132
  family_replacement: 'Chrome Mobile'
123
133
 
@@ -126,34 +136,80 @@ user_agent_parsers:
126
136
  family_replacement: 'Chrome Frame'
127
137
 
128
138
  # UC Browser
129
- - regex: '(UC Browser)(\d+)\.(\d+)\.(\d+)'
139
+ - regex: '(UCBrowser)[ /](\d+)\.(\d+)\.(\d+)'
140
+ family_replacement: 'UC Browser'
141
+ - regex: '(UC Browser)[ /](\d+)\.(\d+)\.(\d+)'
142
+ - regex: '(UC Browser|UCBrowser|UCWEB)(\d+)\.(\d+)\.(\d+)'
143
+ family_replacement: 'UC Browser'
130
144
 
131
145
  # Tizen Browser (second case included in browser/major.minor regex)
132
146
  - regex: '(SLP Browser)/(\d+)\.(\d+)'
133
147
  family_replacement: 'Tizen Browser'
134
148
 
135
- # Epiphany browser (identifies as Chromium)
136
- - regex: '(Epiphany)/(\d+)\.(\d+).(\d+)'
137
-
138
149
  # Sogou Explorer 2.X
139
150
  - regex: '(SE 2\.X) MetaSr (\d+)\.(\d+)'
140
151
  family_replacement: 'Sogou Explorer'
141
152
 
153
+ # Baidu Browsers (desktop spoofs chrome & IE, explorer is mobile)
154
+ - regex: '(baidubrowser)[/\s](\d+)'
155
+ family_replacement: 'Baidu Browser'
156
+ - regex: '(FlyFlow)/(\d+)\.(\d+)'
157
+ family_replacement: 'Baidu Explorer'
158
+
159
+ # Pingdom
160
+ - regex: '(Pingdom.com_bot_version_)(\d+)\.(\d+)'
161
+ family_replacement: 'PingdomBot'
162
+
163
+ # Facebook
164
+ - regex: '(facebookexternalhit)/(\d+)\.(\d+)'
165
+ family_replacement: 'FacebookBot'
166
+
167
+ # Twitterbot
168
+ - regex: '(Twitterbot)/(\d+)\.(\d+)'
169
+ family_replacement: 'TwitterBot'
170
+
171
+ # Rackspace Monitoring
172
+ - regex: '(Rackspace Monitoring)/(\d+)\.(\d+)'
173
+ family_replacement: 'RackspaceBot'
174
+
175
+ # PyAMF
176
+ - regex: '(PyAMF)/(\d+)\.(\d+)\.(\d+)'
177
+
178
+ # Yandex Browser
179
+ - regex: '(YaBrowser)/(\d+)\.(\d+)\.(\d+)'
180
+ family_replacement: 'Yandex Browser'
181
+
182
+ # Mail.ru Amigo/Internet Browser (Chromium-based)
183
+ - regex: '(Chrome)/(\d+)\.(\d+)\.(\d+).* MRCHROME'
184
+ family_replacement: 'Mail.ru Chromium Browser'
185
+
186
+ # AOL Browser (IE-based)
187
+ - regex: '(AOL) (\d+)\.(\d+); AOLBuild (\d+)'
188
+
142
189
  #### END SPECIAL CASES TOP ####
143
190
 
144
191
  #### MAIN CASES - this catches > 50% of all browsers ####
145
192
 
146
193
  # Browser/major_version.minor_version.beta_version
147
- - regex: '(AdobeAIR|Chromium|FireWeb|Jasmine|ANTGalio|Midori|Fresco|Lobo|PaleMoon|Maxthon|Lynx|OmniWeb|Dillo|Camino|Demeter|Fluid|Fennec|Shiira|Sunrise|Chrome|Flock|Netscape|Lunascape|WebPilot|NetFront|Netfront|Konqueror|SeaMonkey|Kazehakase|Vienna|Iceape|Iceweasel|IceWeasel|Iron|K-Meleon|Sleipnir|Galeon|GranParadiso|Opera Mini|iCab|NetNewsWire|ThunderBrowse|Iron|Iris|UP\.Browser|Bunjaloo|Google Earth|Raven for Mac)/(\d+)\.(\d+)\.(\d+)'
194
+ - regex: '(AdobeAIR|FireWeb|Jasmine|ANTGalio|Midori|Fresco|Lobo|PaleMoon|Maxthon|Lynx|OmniWeb|Dillo|Camino|Demeter|Fluid|Fennec|Epiphany|Shiira|Sunrise|Flock|Netscape|Lunascape|WebPilot|Vodafone|NetFront|Netfront|Konqueror|SeaMonkey|Kazehakase|Vienna|Iceape|Iceweasel|IceWeasel|Iron|K-Meleon|Sleipnir|Galeon|GranParadiso|Opera Mini|iCab|NetNewsWire|ThunderBrowse|Iris|UP\.Browser|Bunjalloo|Google Earth|Raven for Mac|Openwave)/(\d+)\.(\d+)\.(\d+)'
195
+
196
+ # Chrome/Chromium/major_version.minor_version.beta_version
197
+ - regex: '(Chromium|Chrome)/(\d+)\.(\d+)\.(\d+)'
148
198
 
149
199
  # Browser/major_version.minor_version
150
- - regex: '(Bolt|Jasmine|IceCat|Skyfire|Midori|Maxthon|Lynx|Arora|IBrowse|Dillo|Camino|Shiira|Fennec|Phoenix|Chrome|Flock|Netscape|Lunascape|Epiphany|WebPilot|Opera Mini|Opera|NetFront|Netfront|Konqueror|Googlebot|SeaMonkey|Kazehakase|Vienna|Iceape|Iceweasel|IceWeasel|Iron|K-Meleon|Sleipnir|Galeon|GranParadiso|iCab|NetNewsWire|Iron|Space Bison|Stainless|Orca|Dolfin|BOLT|Minimo|Tizen Browser|Polaris)/(\d+)\.(\d+)'
200
+ - regex: '(Bolt|Jasmine|IceCat|Skyfire|Midori|Maxthon|Lynx|Arora|IBrowse|Dillo|Camino|Shiira|Fennec|Phoenix|Chrome|Flock|Netscape|Lunascape|Epiphany|WebPilot|Opera Mini|Opera|Vodafone|NetFront|Netfront|Konqueror|Googlebot|SeaMonkey|Kazehakase|Vienna|Iceape|Iceweasel|IceWeasel|Iron|K-Meleon|Sleipnir|Galeon|GranParadiso|iCab|NetNewsWire|Space Bison|Stainless|Orca|Dolfin|BOLT|Minimo|Tizen Browser|Polaris|Abrowser|Planetweb|ICE Browser)/(\d+)\.(\d+)'
201
+
202
+ # Chrome/Chromium/major_version.minor_version
203
+ - regex: '(Chromium|Chrome)/(\d+)\.(\d+)'
151
204
 
152
205
  # Browser major_version.minor_version.beta_version (space instead of slash)
153
206
  - regex: '(iRider|Crazy Browser|SkipStone|iCab|Lunascape|Sleipnir|Maemo Browser) (\d+)\.(\d+)\.(\d+)'
154
207
  # Browser major_version.minor_version (space instead of slash)
155
- - regex: '(iCab|Lunascape|Opera|Android|Jasmine|Polaris|BREW) (\d+)\.(\d+)\.?(\d+)?'
156
-
208
+ - regex: '(iCab|Lunascape|Opera|Android|Jasmine|Polaris) (\d+)\.(\d+)\.?(\d+)?'
209
+
210
+ # Kindle WebKit
211
+ - regex: '(Kindle)/(\d+)\.(\d+)'
212
+
157
213
  # weird android UAs
158
214
  - regex: '(Android) Donut'
159
215
  v1_replacement: '1'
@@ -192,18 +248,32 @@ user_agent_parsers:
192
248
  - regex: '(Obigo)InternetBrowser'
193
249
  - regex: '(Obigo)\-Browser'
194
250
  - regex: '(Obigo|OBIGO)[^\d]*(\d+)(?:.(\d+))?'
251
+ family_replacement: 'Obigo'
195
252
 
196
253
  - regex: '(MAXTHON|Maxthon) (\d+)\.(\d+)'
197
254
  family_replacement: 'Maxthon'
198
255
  - regex: '(Maxthon|MyIE2|Uzbl|Shiira)'
199
256
  v1_replacement: '0'
200
257
 
201
- - regex: '(PLAYSTATION) (\d+)'
202
- family_replacement: 'PlayStation'
203
- - regex: '(PlayStation Portable)[^\d]+(\d+).(\d+)'
258
+ - regex: 'PLAYSTATION 3.+WebKit'
259
+ family_replacement: 'NetFront NX'
260
+ - regex: 'PLAYSTATION 3'
261
+ family_replacement: 'NetFront'
262
+ - regex: '(PlayStation Portable)'
263
+ family_replacement: 'NetFront'
264
+ - regex: '(PlayStation Vita)'
265
+ family_replacement: 'NetFront NX'
266
+
267
+ - regex: 'AppleWebKit.+ (NX)/(\d+)\.(\d+)\.(\d+)'
268
+ family_replacement: 'NetFront NX'
269
+ - regex: '(Nintendo 3DS)'
270
+ family_replacement: 'NetFront NX'
204
271
 
205
272
  - regex: '(BrowseX) \((\d+)\.(\d+)\.(\d+)'
206
273
 
274
+ - regex: '(NCSA_Mosaic)/(\d+)\.(\d+)'
275
+ family_replacement: 'NCSA Mosaic'
276
+
207
277
  # Polaris/d.d is above
208
278
  - regex: '(POLARIS)/(\d+)\.(\d+)'
209
279
  family_replacement: 'Polaris'
@@ -213,56 +283,71 @@ user_agent_parsers:
213
283
  - regex: '(BonEcho)/(\d+)\.(\d+)\.(\d+)'
214
284
  family_replacement: 'Bon Echo'
215
285
 
286
+ - regex: 'M?QQBrowser'
287
+ family_replacement: 'QQ Browser'
288
+
216
289
  - regex: '(iPod).+Version/(\d+)\.(\d+)\.(\d+)'
217
290
  family_replacement: 'Mobile Safari'
218
291
  - regex: '(iPod).*Version/(\d+)\.(\d+)'
219
292
  family_replacement: 'Mobile Safari'
220
- - regex: '(iPod)'
221
- family_replacement: 'Mobile Safari'
222
293
  - regex: '(iPhone).*Version/(\d+)\.(\d+)\.(\d+)'
223
294
  family_replacement: 'Mobile Safari'
224
295
  - regex: '(iPhone).*Version/(\d+)\.(\d+)'
225
296
  family_replacement: 'Mobile Safari'
226
- - regex: '(iPhone)'
227
- family_replacement: 'Mobile Safari'
228
297
  - regex: '(iPad).*Version/(\d+)\.(\d+)\.(\d+)'
229
298
  family_replacement: 'Mobile Safari'
230
299
  - regex: '(iPad).*Version/(\d+)\.(\d+)'
231
300
  family_replacement: 'Mobile Safari'
232
- - regex: '(iPad)'
301
+ - regex: '(iPod|iPhone|iPad);.*CPU.*OS (\d+)(?:_\d+)?_(\d+).*Mobile'
302
+ family_replacement: 'Mobile Safari'
303
+ - regex: '(iPod|iPhone|iPad)'
233
304
  family_replacement: 'Mobile Safari'
234
305
 
235
306
  - regex: '(AvantGo) (\d+).(\d+)'
307
+
308
+ - regex: '(OneBrowser)/(\d+).(\d+)'
309
+ family_replacement: 'ONE Browser'
236
310
 
237
311
  - regex: '(Avant)'
238
312
  v1_replacement: '1'
239
313
 
314
+ # This is the Tesla Model S (see similar entry in device parsers)
315
+ - regex: '(QtCarBrowser)'
316
+ v1_replacement: '1'
317
+
318
+ - regex: '(iBrowser/Mini)(\d+).(\d+)'
319
+ family_replacement: 'iBrowser Mini'
240
320
  # nokia browsers
241
321
  # based on: http://www.developer.nokia.com/Community/Wiki/User-Agent_headers_for_Nokia_devices
242
322
  - regex: '^(Nokia)'
243
323
  family_replacement: 'Nokia Services (WAP) Browser'
244
324
  - regex: '(NokiaBrowser)/(\d+)\.(\d+).(\d+)\.(\d+)'
325
+ family_replacement: 'Nokia Browser'
245
326
  - regex: '(NokiaBrowser)/(\d+)\.(\d+).(\d+)'
327
+ family_replacement: 'Nokia Browser'
246
328
  - regex: '(NokiaBrowser)/(\d+)\.(\d+)'
329
+ family_replacement: 'Nokia Browser'
247
330
  - regex: '(BrowserNG)/(\d+)\.(\d+).(\d+)'
248
- family_replacement: 'NokiaBrowser'
331
+ family_replacement: 'Nokia Browser'
249
332
  - regex: '(Series60)/5\.0'
250
- family_replacement: 'NokiaBrowser'
333
+ family_replacement: 'Nokia Browser'
251
334
  v1_replacement: '7'
252
335
  v2_replacement: '0'
253
336
  - regex: '(Series60)/(\d+)\.(\d+)'
254
337
  family_replacement: 'Nokia OSS Browser'
255
338
  - regex: '(S40OviBrowser)/(\d+)\.(\d+)\.(\d+)\.(\d+)'
256
- family_replacement: 'Nokia Series 40 Ovi Browser'
339
+ family_replacement: 'Ovi Browser'
257
340
  - regex: '(Nokia)[EN]?(\d+)'
258
341
 
259
342
  # BlackBerry devices
343
+ - regex: '(BB10);'
344
+ family_replacement: 'BlackBerry WebKit'
260
345
  - regex: '(PlayBook).+RIM Tablet OS (\d+)\.(\d+)\.(\d+)'
261
- family_replacement: 'Blackberry WebKit'
346
+ family_replacement: 'BlackBerry WebKit'
262
347
  - regex: '(Black[bB]erry).+Version/(\d+)\.(\d+)\.(\d+)'
263
- family_replacement: 'Blackberry WebKit'
348
+ family_replacement: 'BlackBerry WebKit'
264
349
  - regex: '(Black[bB]erry)\s?(\d+)'
265
- family_replacement: 'Blackberry'
350
+ family_replacement: 'BlackBerry'
266
351
 
267
352
  - regex: '(OmniWeb)/v(\d+)\.(\d+)'
268
353
 
@@ -272,6 +357,9 @@ user_agent_parsers:
272
357
  - regex: '(Pre)/(\d+)\.(\d+)'
273
358
  family_replacement: 'Palm Pre'
274
359
 
360
+ # fork of Links
361
+ - regex: '(ELinks)/(\d+)\.(\d+)'
362
+ - regex: '(ELinks) \((\d+)\.(\d+)'
275
363
  - regex: '(Links) \((\d+)\.(\d+)'
276
364
 
277
365
  - regex: '(QtWeb) Internet Browser/(\d+)\.(\d+)'
@@ -281,9 +369,13 @@ user_agent_parsers:
281
369
 
282
370
  # Amazon Silk, should go before Safari
283
371
  - regex: '(Silk)/(\d+)\.(\d+)(?:\.([0-9\-]+))?'
372
+ family_replacement: 'Amazon Silk'
373
+
374
+ # Phantomjs, should go before Safari
375
+ - regex: '(PhantomJS)/(\d+)\.(\d+)\.(\d+)'
284
376
 
285
377
  # WebKit Nightly
286
- - regex: '(AppleWebKit)/(\d+)\.?(\d+)?\+ .* Version/\d+\.\d+.\d+ Safari/'
378
+ - regex: '(AppleWebKit)/(\d+)\.?(\d+)?\+ .* Safari'
287
379
  family_replacement: 'WebKit Nightly'
288
380
 
289
381
  # Safari
@@ -301,11 +393,77 @@ user_agent_parsers:
301
393
 
302
394
  - regex: '(Teleca)'
303
395
  family_replacement: 'Teleca Browser'
396
+
397
+ - regex: '(Phantom)/V(\d+)\.(\d+)'
398
+ family_replacement: 'Phantom Browser'
304
399
 
305
- - regex: '(MSIE) (\d+)\.(\d+)'
400
+ - regex: '([MS]?IE) (\d+)\.(\d+)'
306
401
  family_replacement: 'IE'
307
402
 
403
+ - regex: 'Trident(.*)rv.(\d+)\.(\d+)'
404
+ family_replacement: 'IE'
405
+
406
+ - regex: '(python-requests)/(\d+)\.(\d+)'
407
+ family_replacement: 'Python Requests'
408
+
308
409
  os_parsers:
410
+ ##########
411
+ # HbbTV vendors
412
+ ##########
413
+
414
+ # starts with the easy one : Panasonic seems consistent across years, hope it will continue
415
+ #HbbTV/1.1.1 (;Panasonic;VIERA 2011;f.532;0071-0802 2000-0000;)
416
+ #HbbTV/1.1.1 (;Panasonic;VIERA 2012;1.261;0071-3103 2000-0000;)
417
+ #HbbTV/1.2.1 (;Panasonic;VIERA 2013;3.672;4101-0003 0002-0000;)
418
+ #- regex: 'HbbTV/\d+\.\d+\.\d+ \(;(Panasonic);VIERA ([0-9]{4});'
419
+
420
+ # Sony is consistent too but do not place year like the other
421
+ # Opera/9.80 (Linux armv7l; HbbTV/1.1.1 (; Sony; KDL32W650A; PKG3.211EUA; 2013;); ) Presto/2.12.362 Version/12.11
422
+ # Opera/9.80 (Linux mips; U; HbbTV/1.1.1 (; Sony; KDL40HX751; PKG1.902EUA; 2012;);; en) Presto/2.10.250 Version/11.60
423
+ # Opera/9.80 (Linux mips; U; HbbTV/1.1.1 (; Sony; KDL22EX320; PKG4.017EUA; 2011;);; en) Presto/2.7.61 Version/11.00
424
+ #- regex: 'HbbTV/\d+\.\d+\.\d+ \(; (Sony);.*;.*; ([0-9]{4});\)'
425
+
426
+
427
+ # LG is consistent too, but we need to add manually the year model
428
+ #Mozilla/5.0 (Unknown; Linux armv7l) AppleWebKit/537.1+ (KHTML, like Gecko) Safari/537.1+ HbbTV/1.1.1 ( ;LGE ;NetCast 4.0 ;03.20.30 ;1.0M ;)
429
+ #Mozilla/5.0 (DirectFB; Linux armv7l) AppleWebKit/534.26+ (KHTML, like Gecko) Version/5.0 Safari/534.26+ HbbTV/1.1.1 ( ;LGE ;NetCast 3.0 ;1.0 ;1.0M ;)
430
+ - regex: 'HbbTV/\d+\.\d+\.\d+ \( ;(LG)E ;NetCast 4.0'
431
+ os_v1_replacement: '2013'
432
+ - regex: 'HbbTV/\d+\.\d+\.\d+ \( ;(LG)E ;NetCast 3.0'
433
+ os_v1_replacement: '2012'
434
+
435
+ # Samsung is on its way of normalizing their user-agent
436
+ # HbbTV/1.1.1 (;Samsung;SmartTV2013;T-FXPDEUC-1102.2;;) WebKit
437
+ # HbbTV/1.1.1 (;Samsung;SmartTV2013;T-MST12DEUC-1102.1;;) WebKit
438
+ # HbbTV/1.1.1 (;Samsung;SmartTV2012;;;) WebKit
439
+ # HbbTV/1.1.1 (;;;;;) Maple_2011
440
+ - regex: 'HbbTV/1.1.1 \(;;;;;\) Maple_2011'
441
+ os_replacement: 'Samsung'
442
+ os_v1_replacement: '2011'
443
+ # manage the two models of 2013
444
+ - regex: 'HbbTV/\d+\.\d+\.\d+ \(;(Samsung);SmartTV([0-9]{4});.*FXPDEUC'
445
+ os_v2_replacement: 'UE40F7000'
446
+ - regex: 'HbbTV/\d+\.\d+\.\d+ \(;(Samsung);SmartTV([0-9]{4});.*MST12DEUC'
447
+ os_v2_replacement: 'UE32F4500'
448
+ # generic Samsung (works starting in 2012)
449
+ #- regex: 'HbbTV/\d+\.\d+\.\d+ \(;(Samsung);SmartTV([0-9]{4});'
450
+
451
+ # Philips : not found any other way than a manual mapping
452
+ # Opera/9.80 (Linux mips; U; HbbTV/1.1.1 (; Philips; ; ; ; ) CE-HTML/1.0 NETTV/4.1.3 PHILIPSTV/1.1.1; en) Presto/2.10.250 Version/11.60
453
+ # Opera/9.80 (Linux mips ; U; HbbTV/1.1.1 (; Philips; ; ; ; ) CE-HTML/1.0 NETTV/3.2.1; en) Presto/2.6.33 Version/10.70
454
+ - regex: 'HbbTV/1.1.1 \(; (Philips);.*NETTV/4'
455
+ os_v1_replacement: '2013'
456
+ - regex: 'HbbTV/1.1.1 \(; (Philips);.*NETTV/3'
457
+ os_v1_replacement: '2012'
458
+ - regex: 'HbbTV/1.1.1 \(; (Philips);.*NETTV/2'
459
+ os_v1_replacement: '2011'
460
+
461
+ # the HbbTV emulator developers use HbbTV/1.1.1 (;;;;;) firetv-firefox-plugin 1.1.20
462
+ - regex: 'HbbTV/\d+\.\d+\.\d+.*(firetv)-firefox-plugin (\d+).(\d+).(\d+)'
463
+ os_replacement: 'FireHbbTV'
464
+
465
+ # generic HbbTV, hoping to catch manufacturer name (always after 2nd comma) and the first string that looks like a 2011-2019 year
466
+ - regex: 'HbbTV/\d+\.\d+\.\d+ \(.*; ?([a-zA-Z]+) ?;.*(201[1-9]).*\)'
309
467
 
310
468
  ##########
311
469
  # Android
@@ -333,6 +491,12 @@ os_parsers:
333
491
  - regex: '(Android) Honeycomb'
334
492
  os_v1_replacement: '3'
335
493
 
494
+ ##########
495
+ # Kindle Android
496
+ ##########
497
+ - regex: '(Silk-Accelerated=[a-z]{4,5})'
498
+ os_replacement: 'Android'
499
+
336
500
  ##########
337
501
  # Windows
338
502
  # http://en.wikipedia.org/wiki/Windows_NT#Releases
@@ -341,7 +505,6 @@ os_parsers:
341
505
  # lots of ua strings have Windows NT 4.1 !?!?!?!? !?!? !? !????!?! !!! ??? !?!?! ?
342
506
  # (very) roughly ordered in terms of frequency of occurence of regex (win xp currently most frequent, etc)
343
507
  ##########
344
- - regex: '(Windows Phone 6\.5)'
345
508
 
346
509
  - regex: '(Windows (?:NT 5\.2|NT 5\.1))'
347
510
  os_replacement: 'Windows XP'
@@ -349,7 +512,7 @@ os_parsers:
349
512
  # ie mobile des ktop mode
350
513
  # spoofs nt 6.1. must come before windows 7
351
514
  - regex: '(XBLWP7)'
352
- os_replacement: 'Windows Phone OS'
515
+ os_replacement: 'Windows Phone'
353
516
 
354
517
  - regex: '(Windows NT 6\.1)'
355
518
  os_replacement: 'Windows 7'
@@ -357,7 +520,13 @@ os_parsers:
357
520
  - regex: '(Windows NT 6\.0)'
358
521
  os_replacement: 'Windows Vista'
359
522
 
360
- - regex: '(Windows 98|Windows XP|Windows ME|Windows 95|Windows CE|Windows 7|Windows NT 4\.0|Windows Vista|Windows 2000)'
523
+ - regex: '(Win 9x 4\.90)'
524
+ os_replacement: 'Windows Me'
525
+
526
+ - regex: '(Windows 98|Windows XP|Windows ME|Windows 95|Windows CE|Windows 7|Windows NT 4\.0|Windows Vista|Windows 2000|Windows 3.1)'
527
+
528
+ - regex: '(Windows NT 6\.2; ARM;)'
529
+ os_replacement: 'Windows RT'
361
530
 
362
531
  # is this a spoof or is nt 6.2 out and about in some capacity?
363
532
  - regex: '(Windows NT 6\.2)'
@@ -366,8 +535,8 @@ os_parsers:
366
535
  - regex: '(Windows NT 5\.0)'
367
536
  os_replacement: 'Windows 2000'
368
537
 
369
- - regex: '(Windows Phone OS) (\d+)\.(\d+)'
370
-
538
+ - regex: '(Windows Phone) (\d+)\.(\d+)'
539
+ - regex: '(Windows Phone) OS (\d+)\.(\d+)'
371
540
  - regex: '(Windows ?Mobile)'
372
541
  os_replacement: 'Windows Mobile'
373
542
 
@@ -383,13 +552,15 @@ os_parsers:
383
552
  ##########
384
553
  - regex: '(Tizen)/(\d+)\.(\d+)'
385
554
 
386
-
387
-
388
555
  ##########
389
556
  # Mac OS
390
557
  # http://en.wikipedia.org/wiki/Mac_OS_X#Versions
391
558
  ##########
392
559
  - regex: '(Mac OS X) (\d+)[_.](\d+)(?:[_.](\d+))?'
560
+
561
+ # IE on Mac doesn't specify version number
562
+ - regex: 'Mac_PowerPC'
563
+ os_replacement: 'Mac OS'
393
564
 
394
565
  # builds before tiger don't seem to specify version?
395
566
 
@@ -411,6 +582,9 @@ os_parsers:
411
582
  - regex: '(iPhone|iPad|iPod).*Mac OS X.*Version/(\d+)\.(\d+)'
412
583
  os_replacement: 'iOS'
413
584
 
585
+ - regex: '(AppleTV)/(\d+)\.(\d+)'
586
+ os_replacement: 'ATV OS X'
587
+
414
588
  ##########
415
589
  # Chrome OS
416
590
  # if version 0.0.0, probably this stuff:
@@ -423,9 +597,10 @@ os_parsers:
423
597
  ##########
424
598
  # Linux distros
425
599
  ##########
426
- - regex: '(Debian)-(\d+)\.(\d+)\.(\d+)(?:\.(\d+))?'
600
+ - regex: '([Dd]ebian)'
601
+ os_replacement: 'Debian'
427
602
  - regex: '(Linux Mint)(?:/(\d+))?'
428
- - regex: '(Mandriva)(?: Linux)?/(\d+)\.(\d+)\.(\d+)(?:\.(\d+))?'
603
+ - regex: '(Mandriva)(?: Linux)?/(?:[\d.-]+m[a-z]{2}(\d+).(\d))?'
429
604
 
430
605
  ##########
431
606
  # Symbian + Symbian OS
@@ -444,10 +619,14 @@ os_parsers:
444
619
  - regex: '(MeeGo)'
445
620
  - regex: 'Symbian [Oo][Ss]'
446
621
  os_replacement: 'Symbian OS'
622
+ - regex: 'Series40;'
623
+ os_replacement: 'Nokia Series 40'
447
624
 
448
625
  ##########
449
626
  # BlackBerry devices
450
627
  ##########
628
+ - regex: '(BB10);.+Version/(\d+)\.(\d+)\.(\d+)'
629
+ os_replacement: 'BlackBerry OS'
451
630
  - regex: '(Black[Bb]erry)[0-9a-z]+/(\d+)\.(\d+)\.(\d+)(?:\.(\d+))?'
452
631
  os_replacement: 'BlackBerry OS'
453
632
  - regex: '(Black[Bb]erry).+Version/(\d+)\.(\d+)\.(\d+)(?:\.(\d+))?'
@@ -457,30 +636,61 @@ os_parsers:
457
636
  - regex: '(Play[Bb]ook)'
458
637
  os_replacement: 'BlackBerry Tablet OS'
459
638
  - regex: '(Black[Bb]erry)'
460
- os_replacement: 'Blackberry OS'
639
+ os_replacement: 'BlackBerry OS'
640
+
641
+ ##########
642
+ # Firefox OS
643
+ ##########
644
+ - regex: '\(Mobile;.+Firefox/\d+\.\d+'
645
+ os_replacement: 'Firefox OS'
646
+
647
+ ##########
648
+ # BREW
649
+ # yes, Brew is lower-cased for Brew MP
650
+ ##########
651
+ - regex: '(BREW)[ /](\d+)\.(\d+)\.(\d+)'
652
+ - regex: '(BREW);'
653
+ - regex: '(Brew MP|BMP)[ /](\d+)\.(\d+)\.(\d+)'
654
+ os_replacement: 'Brew MP'
655
+ - regex: 'BMP;'
656
+ os_replacement: 'Brew MP'
461
657
 
658
+ ##########
659
+ # Google TV
660
+ ##########
661
+ - regex: '(GoogleTV) (\d+)\.(\d+)\.(\d+)'
662
+ # Old style
663
+ - regex: '(GoogleTV)/[\da-z]+'
664
+
665
+ - regex: '(WebTV)/(\d+).(\d+)'
666
+
462
667
  ##########
463
668
  # Misc mobile
464
669
  ##########
465
- - regex: '(webOS|hpwOS)/(\d+)\.(\d+)(?:\.(\d+))?'
670
+ - regex: '(hpw|web)OS/(\d+)\.(\d+)(?:\.(\d+))?'
466
671
  os_replacement: 'webOS'
672
+ - regex: '(VRE);'
467
673
 
468
674
  ##########
469
675
  # Generic patterns
470
676
  # since the majority of os cases are very specific, these go last
471
677
  ##########
472
678
  # first.second.third.fourth bits
473
- - regex: '(SUSE|Fedora|Red Hat|PCLinuxOS)/(\d+)\.(\d+)\.(\d+)\.(\d+)'
679
+ - regex: '(Fedora|Red Hat|PCLinuxOS)/(\d+)\.(\d+)\.(\d+)\.(\d+)'
474
680
 
475
681
  # first.second.third bits
476
- - regex: '(SUSE|Fedora|Red Hat|Puppy|PCLinuxOS|CentOS)/(\d+)\.(\d+)\.(\d+)'
682
+ - regex: '(Red Hat|Puppy|PCLinuxOS)/(\d+)\.(\d+)\.(\d+)'
477
683
 
478
684
  # first.second bits
479
685
  - regex: '(Ubuntu|Kindle|Bada|Lubuntu|BackTrack|Red Hat|Slackware)/(\d+)\.(\d+)'
480
686
 
481
687
  # just os
482
- - regex: '(Windows|OpenBSD|FreeBSD|NetBSD|Ubuntu|Kubuntu|Android|Arch Linux|CentOS|WeTab|Slackware)'
688
+ - regex: '(Windows|OpenBSD|FreeBSD|NetBSD|Android|WeTab)'
689
+ - regex: '(Ubuntu|Kubuntu|Arch Linux|CentOS|Slackware|Gentoo|openSUSE|SUSE|Red Hat|Fedora|PCLinuxOS|Gentoo|Mageia)'
690
+ - regex: '(Linux)/(\d+)\.(\d+)'
483
691
  - regex: '(Linux|BSD)'
692
+ - regex: 'SunOS'
693
+ os_replacement: 'Solaris'
484
694
 
485
695
  device_parsers:
486
696
  ##########
@@ -510,31 +720,64 @@ device_parsers:
510
720
  - regex: 'Sprint APA(9292)'
511
721
  device_replacement: 'HTC $1 (Sprint)'
512
722
  - regex: 'HTC ([A-Za-z0-9]+ [A-Z])'
513
- device_replacement: HTC $1
514
- - regex: 'HTC-([A-Za-z0-9]+)'
515
- device_replacement: 'HTC $1'
516
- - regex: 'HTC_([A-Za-z0-9]+)'
517
723
  device_replacement: 'HTC $1'
518
- - regex: 'HTC ([A-Za-z0-9]+)'
724
+ - regex: 'HTC[-_/\s]([A-Za-z0-9]+)'
519
725
  device_replacement: 'HTC $1'
520
- - regex: '(ADR[A-z0-9]+)'
726
+ - regex: '(ADR[A-Za-z0-9]+)'
521
727
  device_replacement: 'HTC $1'
522
728
  - regex: '(HTC)'
523
729
 
730
+ # Tesla Model S
731
+ - regex: '(QtCarBrowser)'
732
+ device_replacement: 'Tesla Model S'
733
+
734
+ # Samsung
735
+ - regex: '(SamsungSGHi560)'
736
+ device_replacement: 'Samsung SGHi560'
737
+
524
738
  #########
525
739
  # Ericsson - must come before nokia since they also use symbian
526
740
  #########
527
- - regex: 'SonyEricsson([A-z0-9]+)/'
741
+ - regex: 'SonyEricsson([A-Za-z0-9]+)/'
528
742
  device_replacement: 'Ericsson $1'
529
743
 
744
+ ##########
745
+ # PlayStation
746
+ # The Vita spoofs the Kindle
747
+ ##########
748
+ - regex: 'PLAYSTATION 3'
749
+ device_replacement: 'PlayStation 3'
750
+ - regex: '(PlayStation Portable)'
751
+ - regex: '(PlayStation Vita)'
752
+
753
+ ##########
754
+ # incomplete!
755
+ # Kindle
756
+ # http://amazonsilk.wordpress.com/useful-bits/silk-user-agent/
757
+ ##########
758
+ - regex: '(KFOT Build)'
759
+ device_replacement: 'Kindle Fire'
760
+ - regex: '(KFTT Build)'
761
+ device_replacement: 'Kindle Fire HD'
762
+ - regex: '(KFJWI Build)'
763
+ device_replacement: 'Kindle Fire HD 8.9" WiFi'
764
+ - regex: '(KFJWA Build)'
765
+ device_replacement: 'Kindle Fire HD 8.9" 4G'
766
+ - regex: '(Kindle Fire)'
767
+ - regex: '(Kindle)'
768
+ - regex: '(Silk)/(\d+)\.(\d+)(?:\.([0-9\-]+))?'
769
+ device_replacement: 'Kindle Fire'
770
+
530
771
  #########
531
772
  # Android General Device Matching (far from perfect)
532
773
  #########
533
- - regex: 'Android[\- ][\d]+\.[\d]+\; [A-z]{2}\-[A-z]{2}\; WOWMobile (.+) Build'
534
- - regex: 'Android[\- ][\d]+\.[\d]+\.[\d]+; [A-z]{2}\-[A-z]{2}\; (.+) Build'
535
- - regex: 'Android[\- ][\d]+\.[\d]+\-update1\; [A-z]{2}\-[A-z]{2}\; (.+) Build'
536
- - regex: 'Android[\- ][\d]+\.[\d]+\; [A-z]{2}\-[A-z]{2}\; (.+) Build'
774
+ - regex: 'Android[\- ][\d]+\.[\d]+; [A-Za-z]{2}\-[A-Za-z]{0,2}; WOWMobile (.+) Build'
775
+ - regex: 'Android[\- ][\d]+\.[\d]+\-update1; [A-Za-z]{2}\-[A-Za-z]{0,2}; (.+) Build'
776
+ - regex: 'Android[\- ][\d]+\.[\d]+\.[\d]+; [A-Za-z]{2}\-[A-Za-z]{0,2}; (.+) Build'
777
+ - regex: 'Android[\- ][\d]+\.[\d]+\.[\d]+;[A-Za-z]{2}\-[A-Za-z]{0,2};(.+) Build'
778
+ - regex: 'Android[\- ][\d]+\.[\d]+; [A-Za-z]{2}\-[A-Za-z]{0,2}; (.+) Build'
537
779
  - regex: 'Android[\- ][\d]+\.[\d]+\.[\d]+; (.+) Build'
780
+ - regex: 'Android[\- ][\d]+\.[\d]+; (.+) Build'
538
781
 
539
782
  ##########
540
783
  # NOKIA
@@ -542,6 +785,8 @@ device_parsers:
542
785
  ##########
543
786
  - regex: 'NokiaN([0-9]+)'
544
787
  device_replacement: 'Nokia N$1'
788
+ - regex: 'NOKIA([A-Za-z0-9\v-]+)'
789
+ device_replacement: 'Nokia $1'
545
790
  - regex: 'Nokia([A-Za-z0-9\v-]+)'
546
791
  device_replacement: 'Nokia $1'
547
792
  - regex: 'NOKIA ([A-Za-z0-9\-]+)'
@@ -554,14 +799,19 @@ device_parsers:
554
799
  device_replacement: 'Nokia'
555
800
 
556
801
  ##########
557
- # Blackberry
802
+ # BlackBerry
558
803
  # http://www.useragentstring.com/pages/BlackBerry/
559
804
  ##########
805
+ - regex: 'BB10; ([A-Za-z0-9\- ]+)\)'
806
+ device_replacement: 'BlackBerry $1'
560
807
  - regex: '(PlayBook).+RIM Tablet OS'
561
- device_replacement: 'Blackberry Playbook'
562
- - regex: '(Black[Bb]erry [0-9]+);'
808
+ device_replacement: 'BlackBerry Playbook'
809
+ - regex: 'Black[Bb]erry ([0-9]+);'
810
+ device_replacement: 'BlackBerry $1'
563
811
  - regex: 'Black[Bb]erry([0-9]+)'
564
812
  device_replacement: 'BlackBerry $1'
813
+ - regex: 'Black[Bb]erry;'
814
+ device_replacement: 'BlackBerry'
565
815
 
566
816
  ##########
567
817
  # PALM / HP
@@ -571,26 +821,35 @@ device_parsers:
571
821
  device_replacement: 'Palm Pre'
572
822
  - regex: '(Pixi)/(\d+)\.(\d+)'
573
823
  device_replacement: 'Palm Pixi'
574
- - regex: '(Touchpad)/(\d+)\.(\d+)'
575
- device_replacement: 'HP Touchpad'
576
- - regex: 'HPiPAQ([A-z0-9]+)/(\d+).(\d+)'
824
+ - regex: '(Touch[Pp]ad)/(\d+)\.(\d+)'
825
+ device_replacement: 'HP TouchPad'
826
+ - regex: 'HPiPAQ([A-Za-z0-9]+)/(\d+).(\d+)'
577
827
  device_replacement: 'HP iPAQ $1'
578
- - regex: 'Palm([A-z0-9]+)'
828
+ - regex: 'Palm([A-Za-z0-9]+)'
579
829
  device_replacement: 'Palm $1'
580
- - regex: 'Treo([A-z0-9]+)'
830
+ - regex: 'Treo([A-Za-z0-9]+)'
581
831
  device_replacement: 'Palm Treo $1'
582
832
  - regex: 'webOS.*(P160UNA)/(\d+).(\d+)'
583
833
  device_replacement: 'HP Veer'
584
834
 
585
835
  ##########
586
- # incomplete!
587
- # Kindle
836
+ # AppleTV
837
+ # No built in browser that I can tell
838
+ # Stack Overflow indicated iTunes-AppleTV/4.1 as a known UA for app available and I'm seeing it in live traffic
839
+ ##########
840
+ - regex: '(AppleTV)'
841
+ device_replacement: 'AppleTV'
842
+
843
+ ##########
844
+ # Catch the google mobile crawler before checking for iPhones.
588
845
  ##########
589
- - regex: '(Kindle Fire)'
590
- - regex: '(Kindle)'
591
- - regex: '(Silk)/(\d+)\.(\d+)(?:\.([0-9\-]+))?'
592
- device_replacement: 'Kindle Fire'
593
846
 
847
+ - regex: 'AdsBot-Google-Mobile'
848
+ device_replacement: 'Spider'
849
+
850
+ - regex: 'Googlebot-Mobile/(\d+).(\d+)'
851
+ device_replacement: 'Spider'
852
+
594
853
  ##########
595
854
  # complete but probably catches spoofs
596
855
  # iSTUFF
@@ -599,6 +858,7 @@ device_parsers:
599
858
  # cannot determine specific device type from ua string. (3g, 3gs, 4, etc)
600
859
  - regex: '(iPad) Simulator;'
601
860
  - regex: '(iPad);'
861
+ - regex: '(iPod) touch;'
602
862
  - regex: '(iPod);'
603
863
  - regex: '(iPhone) Simulator;'
604
864
  - regex: '(iPhone);'
@@ -606,101 +866,119 @@ device_parsers:
606
866
  ##########
607
867
  # Acer
608
868
  ##########
609
- - regex: 'acer_([A-z0-9]+)_'
869
+ - regex: 'acer_([A-Za-z0-9]+)_'
610
870
  device_replacement: 'Acer $1'
611
- - regex: 'acer_([A-z0-9]+)_'
871
+ - regex: 'acer_([A-Za-z0-9]+)_'
612
872
  device_replacement: 'Acer $1'
613
873
 
874
+ ##########
875
+ # Alcatel
876
+ ##########
877
+ - regex: 'ALCATEL-([A-Za-z0-9]+)'
878
+ device_replacement: 'Alcatel $1'
879
+ - regex: 'Alcatel-([A-Za-z0-9]+)'
880
+ device_replacement: 'Alcatel $1'
881
+
614
882
  ##########
615
883
  # Amoi
616
884
  ##########
617
- - regex: 'Amoi\-([A-z0-9]+)'
885
+ - regex: 'Amoi\-([A-Za-z0-9]+)'
618
886
  device_replacement: 'Amoi $1'
619
- - regex: 'AMOI\-([A-z0-9]+)'
887
+ - regex: 'AMOI\-([A-Za-z0-9]+)'
620
888
  device_replacement: 'Amoi $1'
621
889
 
622
890
  ##########
623
891
  # Amoi
624
892
  ##########
625
- - regex: 'Asus\-([A-z0-9]+)'
893
+ - regex: 'Asus\-([A-Za-z0-9]+)'
626
894
  device_replacement: 'Asus $1'
627
- - regex: 'ASUS\-([A-z0-9]+)'
895
+ - regex: 'ASUS\-([A-Za-z0-9]+)'
628
896
  device_replacement: 'Asus $1'
629
897
 
630
898
  ##########
631
899
  # Bird
632
900
  ##########
633
- - regex: 'BIRD\-([A-z0-9]+)'
901
+ - regex: 'BIRD\-([A-Za-z0-9]+)'
634
902
  device_replacement: 'Bird $1'
635
- - regex: 'BIRD\.([A-z0-9]+)'
903
+ - regex: 'BIRD\.([A-Za-z0-9]+)'
636
904
  device_replacement: 'Bird $1'
637
- - regex: 'BIRD ([A-z0-9]+)'
905
+ - regex: 'BIRD ([A-Za-z0-9]+)'
638
906
  device_replacement: 'Bird $1'
639
907
 
640
908
  ##########
641
909
  # Dell
642
910
  ##########
643
- - regex: 'Dell ([A-z0-9]+)'
911
+ - regex: 'Dell ([A-Za-z0-9]+)'
644
912
  device_replacement: 'Dell $1'
645
913
 
646
914
  ##########
647
915
  # DoCoMo
648
916
  ##########
649
- - regex: 'DoCoMo/2\.0 ([A-z0-9]+)'
917
+ - regex: 'DoCoMo/2\.0 ([A-Za-z0-9]+)'
650
918
  device_replacement: 'DoCoMo $1'
651
- - regex: '([A-z0-9]+)\_W\;FOMA'
919
+ - regex: '([A-Za-z0-9]+)_W\;FOMA'
652
920
  device_replacement: 'DoCoMo $1'
653
- - regex: '([A-z0-9]+)\;FOMA'
921
+ - regex: '([A-Za-z0-9]+)\;FOMA'
654
922
  device_replacement: 'DoCoMo $1'
655
923
 
656
924
  ##########
657
- # Huawei Vodafone
925
+ # Huawei
658
926
  ##########
659
- - regex: 'vodafone([A-z0-9]+)'
927
+ - regex: 'Huawei([A-Za-z0-9]+)'
928
+ device_replacement: 'Huawei $1'
929
+ - regex: 'HUAWEI-([A-Za-z0-9]+)'
930
+ device_replacement: 'Huawei $1'
931
+ - regex: 'vodafone([A-Za-z0-9]+)'
660
932
  device_replacement: 'Huawei Vodafone $1'
661
933
 
662
934
  ##########
663
935
  # i-mate
664
936
  ##########
665
- - regex: 'i\-mate ([A-z0-9]+)'
937
+ - regex: 'i\-mate ([A-Za-z0-9]+)'
666
938
  device_replacement: 'i-mate $1'
667
939
 
668
940
  ##########
669
941
  # kyocera
670
942
  ##########
671
- - regex: 'Kyocera\-([A-z0-9]+)'
943
+ - regex: 'Kyocera\-([A-Za-z0-9]+)'
672
944
  device_replacement: 'Kyocera $1'
673
- - regex: 'KWC\-([A-z0-9]+)'
945
+ - regex: 'KWC\-([A-Za-z0-9]+)'
674
946
  device_replacement: 'Kyocera $1'
675
947
 
676
948
  ##########
677
949
  # lenovo
678
950
  ##########
679
- - regex: 'Lenovo\-([A-z0-9]+)'
951
+ - regex: 'Lenovo\-([A-Za-z0-9]+)'
680
952
  device_replacement: 'Lenovo $1'
681
- - regex: 'Lenovo\_([A-z0-9]+)'
953
+ - regex: 'Lenovo_([A-Za-z0-9]+)'
682
954
  device_replacement: 'Lenovo $1'
683
955
 
956
+ ##########
957
+ # HbbTV (European and Australian standard)
958
+ # written before the LG regexes, as LG is making HbbTV too
959
+ ##########
960
+ - regex: '(HbbTV)/[0-9]+\.[0-9]+\.[0-9]+'
961
+
684
962
  ##########
685
963
  # lg
686
964
  ##########
687
- - regex: 'LG/([A-z0-9]+)'
965
+ - regex: 'LG/([A-Za-z0-9]+)'
688
966
  device_replacement: 'LG $1'
689
- - regex: 'LG-LG([A-z0-9]+)'
967
+ - regex: 'LG-LG([A-Za-z0-9]+)'
690
968
  device_replacement: 'LG $1'
691
- - regex: 'LGE-LG([A-z0-9]+)'
969
+ - regex: 'LGE-LG([A-Za-z0-9]+)'
692
970
  device_replacement: 'LG $1'
693
- - regex: 'LGE VX([A-z0-9]+)'
971
+ - regex: 'LGE VX([A-Za-z0-9]+)'
694
972
  device_replacement: 'LG $1'
695
- - regex: 'LG ([A-z0-9]+)'
973
+ - regex: 'LG ([A-Za-z0-9]+)'
696
974
  device_replacement: 'LG $1'
697
- - regex: 'LGE LG\-AX([A-z0-9]+)'
975
+ - regex: 'LGE LG\-AX([A-Za-z0-9]+)'
698
976
  device_replacement: 'LG $1'
699
- - regex: 'LG\-([A-z0-9]+)'
977
+ - regex: 'LG\-([A-Za-z0-9]+)'
700
978
  device_replacement: 'LG $1'
701
- - regex: 'LGE\-([A-z0-9]+)'
979
+ - regex: 'LGE\-([A-Za-z0-9]+)'
702
980
  device_replacement: 'LG $1'
703
- - regex: 'LG([A-z0-9]+)'
981
+ - regex: 'LG([A-Za-z0-9]+)'
704
982
  device_replacement: 'LG $1'
705
983
 
706
984
  ##########
@@ -714,36 +992,61 @@ device_parsers:
714
992
  ##########
715
993
  # motorola
716
994
  ##########
717
- - regex: '(Motorola)\-([A-z0-9]+)'
718
- - regex: 'MOTO\-([A-z0-9]+)'
995
+ - regex: '(Motorola)\-([A-Za-z0-9]+)'
996
+ - regex: 'MOTO\-([A-Za-z0-9]+)'
719
997
  device_replacement: 'Motorola $1'
720
- - regex: 'MOT\-([A-z0-9]+)'
998
+ - regex: 'MOT\-([A-Za-z0-9]+)'
721
999
  device_replacement: 'Motorola $1'
1000
+
1001
+ ##########
1002
+ # nintendo
1003
+ ##########
1004
+ - regex: '(Nintendo WiiU)'
1005
+ device_replacement: 'Nintendo Wii U'
1006
+ - regex: 'Nintendo (DS|3DS|DSi|Wii);'
1007
+ device_replacement: 'Nintendo $1'
722
1008
 
1009
+ ##########
1010
+ # pantech
1011
+ ##########
1012
+ - regex: 'Pantech([A-Za-z0-9]+)'
1013
+ device_replacement: 'Pantech $1'
1014
+
723
1015
  ##########
724
1016
  # philips
725
1017
  ##########
726
- - regex: 'Philips([A-z0-9]+)'
1018
+ - regex: 'Philips([A-Za-z0-9]+)'
727
1019
  device_replacement: 'Philips $1'
728
- - regex: 'Philips ([A-z0-9]+)'
1020
+ - regex: 'Philips ([A-Za-z0-9]+)'
729
1021
  device_replacement: 'Philips $1'
730
1022
 
731
1023
  ##########
732
1024
  # Samsung
733
1025
  ##########
734
- - regex: 'SAMSUNG-([A-z0-9\-]+)'
1026
+ - regex: 'SAMSUNG-([A-Za-z0-9\-]+)'
735
1027
  device_replacement: 'Samsung $1'
736
- - regex: 'SAMSUNG\; ([A-z0-9\-]+)'
1028
+ - regex: 'SAMSUNG\; ([A-Za-z0-9\-]+)'
737
1029
  device_replacement: 'Samsung $1'
738
1030
 
1031
+ ##########
1032
+ # Sega
1033
+ ##########
1034
+ - regex: 'Dreamcast'
1035
+ device_replacement: 'Sega Dreamcast'
1036
+
739
1037
  ##########
740
1038
  # Softbank
741
1039
  ##########
742
- - regex: 'Softbank/1\.0/([A-z0-9]+)'
1040
+ - regex: 'Softbank/1\.0/([A-Za-z0-9]+)'
743
1041
  device_replacement: 'Softbank $1'
744
- - regex: 'Softbank/2\.0/([A-z0-9]+)'
1042
+ - regex: 'Softbank/2\.0/([A-Za-z0-9]+)'
745
1043
  device_replacement: 'Softbank $1'
746
1044
 
1045
+ ##########
1046
+ # WebTV
1047
+ ##########
1048
+ - regex: '(WebTV)/(\d+).(\d+)'
1049
+
747
1050
  ##########
748
1051
  # Generic Smart Phone
749
1052
  ##########
@@ -753,58 +1056,18 @@ device_parsers:
753
1056
  ##########
754
1057
  # Generic Feature Phone
755
1058
  ##########
756
- - regex: '^(1207|3gso|4thp|501i|502i|503i|504i|505i|506i|6310|6590|770s|802s|a wa|acer|acs\-|airn|alav|asus|attw|au\-m|aur |aus |abac|acoo|aiko|alco|alca|amoi|anex|anny|anyw|aptu|arch|argo|bell|bird|bw\-n|bw\-u|beck|benq|bilb|blac|c55/|cdm\-|chtm|capi|comp|cond|craw|dall|dbte|dc\-s|dica|ds\-d|ds12|dait|devi|dmob|doco|dopo|el49|erk0|esl8|ez40|ez60|ez70|ezos|ezze|elai|emul|eric|ezwa|fake|fly\-|fly\_|g\-mo|g1 u|g560|gf\-5|grun|gene|go.w|good|grad|hcit|hd\-m|hd\-p|hd\-t|hei\-|hp i|hpip|hs\-c|htc |htc\-|htca|htcg)'
1059
+ - regex: '^(1207|3gso|4thp|501i|502i|503i|504i|505i|506i|6310|6590|770s|802s|a wa|acer|acs\-|airn|alav|asus|attw|au\-m|aur |aus |abac|acoo|aiko|alco|alca|amoi|anex|anny|anyw|aptu|arch|argo|bell|bird|bw\-n|bw\-u|beck|benq|bilb|blac|c55/|cdm\-|chtm|capi|comp|cond|craw|dall|dbte|dc\-s|dica|ds\-d|ds12|dait|devi|dmob|doco|dopo|el49|erk0|esl8|ez40|ez60|ez70|ezos|ezze|elai|emul|eric|ezwa|fake|fly\-|fly_|g\-mo|g1 u|g560|gf\-5|grun|gene|go.w|good|grad|hcit|hd\-m|hd\-p|hd\-t|hei\-|hp i|hpip|hs\-c|htc |htc\-|htca|htcg)'
757
1060
  device_replacement: 'Generic Feature Phone'
758
- - regex: '^(htcp|htcs|htct|htc\_|haie|hita|huaw|hutc|i\-20|i\-go|i\-ma|i230|iac|iac\-|iac/|ig01|im1k|inno|iris|jata|java|kddi|kgt|kgt/|kpt |kwc\-|klon|lexi|lg g|lg\-a|lg\-b|lg\-c|lg\-d|lg\-f|lg\-g|lg\-k|lg\-l|lg\-m|lg\-o|lg\-p|lg\-s|lg\-t|lg\-u|lg\-w|lg/k|lg/l|lg/u|lg50|lg54|lge\-|lge/|lynx|leno|m1\-w|m3ga|m50/|maui|mc01|mc21|mcca|medi|meri|mio8|mioa|mo01|mo02|mode|modo|mot |mot\-|mt50|mtp1|mtv |mate|maxo|merc|mits|mobi|motv|mozz|n100|n101|n102|n202|n203|n300|n302|n500|n502|n505|n700|n701|n710|nec\-|nem\-|newg|neon)'
1061
+ - regex: '^(htcp|htcs|htct|htc_|haie|hita|huaw|hutc|i\-20|i\-go|i\-ma|i230|iac|iac\-|iac/|ig01|im1k|inno|iris|jata|java|kddi|kgt|kgt/|kpt |kwc\-|klon|lexi|lg g|lg\-a|lg\-b|lg\-c|lg\-d|lg\-f|lg\-g|lg\-k|lg\-l|lg\-m|lg\-o|lg\-p|lg\-s|lg\-t|lg\-u|lg\-w|lg/k|lg/l|lg/u|lg50|lg54|lge\-|lge/|lynx|leno|m1\-w|m3ga|m50/|maui|mc01|mc21|mcca|medi|meri|mio8|mioa|mo01|mo02|mode|modo|mot |mot\-|mt50|mtp1|mtv |mate|maxo|merc|mits|mobi|motv|mozz|n100|n101|n102|n202|n203|n300|n302|n500|n502|n505|n700|n701|n710|nec\-|nem\-|newg|neon)'
759
1062
  device_replacement: 'Generic Feature Phone'
760
1063
  - regex: '^(netf|noki|nzph|o2 x|o2\-x|opwv|owg1|opti|oran|ot\-s|p800|pand|pg\-1|pg\-2|pg\-3|pg\-6|pg\-8|pg\-c|pg13|phil|pn\-2|pt\-g|palm|pana|pire|pock|pose|psio|qa\-a|qc\-2|qc\-3|qc\-5|qc\-7|qc07|qc12|qc21|qc32|qc60|qci\-|qwap|qtek|r380|r600|raks|rim9|rove|s55/|sage|sams|sc01|sch\-|scp\-|sdk/|se47|sec\-|sec0|sec1|semc|sgh\-|shar|sie\-|sk\-0|sl45|slid|smb3|smt5|sp01|sph\-|spv |spv\-|sy01|samm|sany|sava|scoo|send|siem|smar|smit|soft|sony|t\-mo|t218|t250|t600|t610|t618|tcl\-|tdg\-|telm|tim\-|ts70|tsm\-|tsm3|tsm5|tx\-9|tagt)'
761
1064
  device_replacement: 'Generic Feature Phone'
762
- - regex: '^(talk|teli|topl|tosh|up.b|upg1|utst|v400|v750|veri|vk\-v|vk40|vk50|vk52|vk53|vm40|vx98|virg|vite|voda|vulc|w3c |w3c\-|wapj|wapp|wapu|wapm|wig |wapi|wapr|wapv|wapy|wapa|waps|wapt|winc|winw|wonu|x700|xda2|xdag|yas\-|your|zte\-|zeto|aste|audi|avan|blaz|brew|brvw|bumb|ccwa|cell|cldc|cmd\-|dang|eml2|fetc|hipt|http|ibro|idea|ikom|ipaq|jbro|jemu|jigs|keji|kyoc|kyok|libw|m\-cr|midp|mmef|moto|mwbp|mywa|newt|nok6|o2im|pant|pdxg|play|pluc|port|prox|rozo|sama|seri|smal|symb|treo|upsi|vx52|vx53|vx60|vx61|vx70|vx80|vx81|vx83|vx85|wap\-|webc|whit|wmlb|xda\-|xda\_)'
1065
+ - regex: '^(talk|teli|topl|tosh|up.b|upg1|utst|v400|v750|veri|vk\-v|vk40|vk50|vk52|vk53|vm40|vx98|virg|vite|voda|vulc|w3c |w3c\-|wapj|wapp|wapu|wapm|wig |wapi|wapr|wapv|wapy|wapa|waps|wapt|winc|winw|wonu|x700|xda2|xdag|yas\-|your|zte\-|zeto|aste|audi|avan|blaz|brew|brvw|bumb|ccwa|cell|cldc|cmd\-|dang|eml2|fetc|hipt|http|ibro|idea|ikom|ipaq|jbro|jemu|jigs|keji|kyoc|kyok|libw|m\-cr|midp|mmef|moto|mwbp|mywa|newt|nok6|o2im|pant|pdxg|play|pluc|port|prox|rozo|sama|seri|smal|symb|treo|upsi|vx52|vx53|vx60|vx61|vx70|vx80|vx81|vx83|vx85|wap\-|webc|whit|wmlb|xda\-|xda_)'
763
1066
  device_replacement: 'Generic Feature Phone'
764
1067
 
765
1068
  ##########
766
1069
  # Spiders (this is hack...)
767
1070
  ##########
768
- - regex: '(bot|borg|google(^tv)|yahoo|slurp|msnbot|msrbot|openbot|archiver|netresearch|lycos|scooter|altavista|teoma|gigabot|baiduspider|blitzbot|oegp|charlotte|furlbot|http%20client|polybot|htdig|ichiro|mogimogi|larbin|pompos|scrubby|searchsight|seekbot|semanticdiscovery|silk|snappy|speedy|spider|voila|vortex|voyager|zao|zeal|fast\-webcrawler|converacrawler|dataparksearch|findlinks)'
1071
+ - regex: '(bot|borg|google(^tv)|yahoo|slurp|msnbot|msrbot|openbot|archiver|netresearch|lycos|scooter|altavista|teoma|gigabot|baiduspider|blitzbot|oegp|charlotte|furlbot|http%20client|polybot|htdig|ichiro|mogimogi|larbin|pompos|scrubby|searchsight|seekbot|semanticdiscovery|silk|snappy|speedy|spider|voila|vortex|voyager|zao|zeal|fast\-webcrawler|converacrawler|dataparksearch|findlinks|crawler)'
769
1072
  device_replacement: 'Spider'
770
1073
 
771
-
772
- mobile_user_agent_families:
773
- - 'Firefox Mobile'
774
- - 'Opera Mobile'
775
- - 'Opera Mini'
776
- - 'Mobile Safari'
777
- - 'webOS'
778
- - 'IE Mobile'
779
- - 'Playstation Portable'
780
- - 'Nokia'
781
- - 'Blackberry'
782
- - 'Palm'
783
- - 'Silk'
784
- - 'Android'
785
- - 'Maemo'
786
- - 'Obigo'
787
- - 'Netfront'
788
- - 'AvantGo'
789
- - 'Teleca'
790
- - 'SEMC-Browser'
791
- - 'Bolt'
792
- - 'Iris'
793
- - 'UP.Browser'
794
- - 'Symphony'
795
- - 'Minimo'
796
- - 'Bunjaloo'
797
- - 'Jasmine'
798
- - 'Dolfin'
799
- - 'Polaris'
800
- - 'BREW'
801
- - 'Chrome Mobile'
802
- - 'UC Browser'
803
- - 'Tizen Browser'
804
-
805
- # Some select mobile OSs report a desktop browser.
806
- # make sure we note they're mobile
807
- mobile_os_families:
808
- - 'Windows Phone 6.5'
809
- - 'Windows CE'
810
- - 'Symbian OS'