ua-parser-js 2.0.0-alpha.2 → 2.0.0-beta.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.
@@ -1,27 +1,28 @@
1
- // Generated ESM version of UAParser.js
1
+ // Generated ESM version of ua-parser-js
2
2
  // DO NOT EDIT THIS FILE!
3
- // Source: /src/ua-parser.js
4
-
5
- const window = undefined;
3
+ // Source: /src/main/ua-parser.js
6
4
 
7
5
  /////////////////////////////////////////////////////////////////////////////////
8
- /* UAParser.js v2.0.0-alpha.2
6
+ /* UAParser.js v2.0.0-beta.1
9
7
  Copyright © 2012-2023 Faisal Salman <f@faisalman.com>
10
- MIT License *//*
8
+ AGPLv3 License *//*
11
9
  Detect Browser, Engine, OS, CPU, and Device type/model from User-Agent data.
12
10
  Supports browser & node.js environment.
13
11
  Demo : https://faisalman.github.io/ua-parser-js
14
12
  Source : https://github.com/faisalman/ua-parser-js */
15
13
  /////////////////////////////////////////////////////////////////////////////////
16
14
 
15
+ /* jshint esversion: 6 */
16
+ /* globals window */
17
17
 
18
18
 
19
+
19
20
  //////////////
20
21
  // Constants
21
22
  /////////////
22
23
 
23
24
 
24
- var LIBVERSION = '2.0.0-alpha.2',
25
+ var LIBVERSION = '2.0.0-beta.1',
25
26
  EMPTY = '',
26
27
  UNKNOWN = '?',
27
28
  FUNC_TYPE = 'function',
@@ -44,6 +45,7 @@ const window = undefined;
44
45
  USER_AGENT = 'user-agent',
45
46
  UA_MAX_LENGTH = 350,
46
47
  BRANDS = 'brands',
48
+ FORMFACTOR = 'formFactor',
47
49
  FULLVERLIST = 'fullVersionList',
48
50
  PLATFORM = 'platform',
49
51
  PLATFORMVER = 'platformVersion',
@@ -51,12 +53,13 @@ const window = undefined;
51
53
  CH_HEADER = 'sec-ch-ua',
52
54
  CH_HEADER_FULL_VER_LIST = CH_HEADER + '-full-version-list',
53
55
  CH_HEADER_ARCH = CH_HEADER + '-arch',
54
- CH_HEADER_BITNESS = CH_HEADER + '-bitness',
55
- CH_HEADER_MOBILE = CH_HEADER + '-mobile',
56
- CH_HEADER_MODEL = CH_HEADER + '-model',
57
- CH_HEADER_PLATFORM = CH_HEADER + '-platform',
56
+ CH_HEADER_BITNESS = CH_HEADER + '-' + BITNESS,
57
+ CH_HEADER_FORM_FACTOR = CH_HEADER + '-form-factor',
58
+ CH_HEADER_MOBILE = CH_HEADER + '-' + MOBILE,
59
+ CH_HEADER_MODEL = CH_HEADER + '-' + MODEL,
60
+ CH_HEADER_PLATFORM = CH_HEADER + '-' + PLATFORM,
58
61
  CH_HEADER_PLATFORM_VER = CH_HEADER_PLATFORM + '-version',
59
- CH_ALL_VALUES = ['brands', 'fullVersionList', MOBILE, MODEL, 'platform', 'platformVersion', ARCHITECTURE, 'bitness'],
62
+ CH_ALL_VALUES = [BRANDS, FULLVERLIST, MOBILE, MODEL, PLATFORM, PLATFORMVER, ARCHITECTURE, FORMFACTOR, BITNESS],
60
63
  UA_BROWSER = 'browser',
61
64
  UA_CPU = 'cpu',
62
65
  UA_DEVICE = 'device',
@@ -97,18 +100,7 @@ const window = undefined;
97
100
  // Helper
98
101
  //////////
99
102
 
100
- var assignFromEntries = function (arr) {
101
- for (var i in arr) {
102
- var propName = arr[i];
103
- if (typeof propName == OBJ_TYPE && propName.length == 2) {
104
- this[propName[0]] = propName[1];
105
- } else {
106
- this[propName] = undefined;
107
- }
108
- }
109
- return this;
110
- },
111
- extend = function (regexes, extensions) {
103
+ var extend = function (regexes, extensions) {
112
104
  var mergedRegexes = {};
113
105
  for (var i in regexes) {
114
106
  mergedRegexes[i] = extensions[i] && extensions[i].length % 2 === 0 ? extensions[i].concat(regexes[i]) : regexes[i];
@@ -139,10 +131,14 @@ const window = undefined;
139
131
  itemListToArray = function (header) {
140
132
  if (!header) return undefined;
141
133
  var arr = [];
142
- var tokens = strip(/\\?\"/g, header).split(', ');
134
+ var tokens = strip(/\\?\"/g, header).split(',');
143
135
  for (var i = 0; i < tokens.length; i++) {
144
- var token = tokens[i].split(';v=');
145
- arr[i] = { brand : token[0], version : token[1] };
136
+ if (tokens[i].indexOf(';') > -1) {
137
+ var token = trim(tokens[i]).split(';v=');
138
+ arr[i] = { brand : token[0], version : token[1] };
139
+ } else {
140
+ arr[i] = tokens[i];
141
+ }
146
142
  }
147
143
  return arr;
148
144
  },
@@ -152,11 +148,22 @@ const window = undefined;
152
148
  majorize = function (version) {
153
149
  return typeof(version) === STR_TYPE ? strip(/[^\d\.]/g, version).split('.')[0] : undefined;
154
150
  },
151
+ setProps = function (arr) {
152
+ for (var i in arr) {
153
+ var propName = arr[i];
154
+ if (typeof propName == OBJ_TYPE && propName.length == 2) {
155
+ this[propName[0]] = propName[1];
156
+ } else {
157
+ this[propName] = undefined;
158
+ }
159
+ }
160
+ return this;
161
+ },
155
162
  strip = function (pattern, str) {
156
163
  return str.replace(pattern, EMPTY);
157
164
  },
158
165
  stripQuotes = function (val) {
159
- return typeof val === STR_TYPE ? strip(/\"/g, val) : val;
166
+ return typeof val === STR_TYPE ? strip(/\\?\"/g, val) : val;
160
167
  },
161
168
  trim = function (str, len) {
162
169
  if (typeof(str) === STR_TYPE) {
@@ -238,25 +245,14 @@ const window = undefined;
238
245
  return (i === UNKNOWN) ? undefined : i;
239
246
  }
240
247
  }
241
- return str;
248
+ return map.hasOwnProperty('*') ? map['*'] : str;
242
249
  };
243
250
 
244
251
  ///////////////
245
252
  // String map
246
253
  //////////////
247
254
 
248
- // Safari < 3.0
249
- var oldSafariMap = {
250
- '1.0' : '/8',
251
- '1.2' : '/1',
252
- '1.3' : '/3',
253
- '2.0' : '/412',
254
- '2.0.2' : '/416',
255
- '2.0.3' : '/417',
256
- '2.0.4' : '/419',
257
- '?' : '/'
258
- },
259
- windowsVersionMap = {
255
+ var windowsVersionMap = {
260
256
  'ME' : '4.90',
261
257
  'NT 3.11' : 'NT3.51',
262
258
  'NT 4.0' : 'NT4.0',
@@ -268,6 +264,16 @@ const window = undefined;
268
264
  '8.1' : 'NT 6.3',
269
265
  '10' : ['NT 6.4', 'NT 10.0'],
270
266
  'RT' : 'ARM'
267
+ },
268
+
269
+ formFactorMap = {
270
+ 'embedded' : 'Automotive',
271
+ 'mobile' : 'Mobile',
272
+ 'tablet' : ['Tablet', 'EInk'],
273
+ 'smarttv' : 'TV',
274
+ 'wearable' : ['VR', 'XR', 'Watch'],
275
+ '?' : ['Desktop', 'Unknown'],
276
+ '*' : undefined
271
277
  };
272
278
 
273
279
  //////////////
@@ -359,7 +365,7 @@ const window = undefined;
359
365
  /(naver)\(.*?(\d+\.[\w\.]+).*\)/i, // Naver InApp
360
366
  /safari (line)\/([\w\.]+)/i, // Line App for iOS
361
367
  /\b(line)\/([\w\.]+)\/iab/i, // Line App for Android
362
- /(chromium|instagram)[\/ ]([-\w\.]+)/i // Chromium/Instagram
368
+ /(chromium|instagram|snapchat)[\/ ]([-\w\.]+)/i // Chromium/Instagram/Snapchat
363
369
  ], [NAME, VERSION], [
364
370
  /\bgsa\/([\w\.]+) .*safari\//i // Google Search Appliance on iOS
365
371
  ], [VERSION, [NAME, 'GSA']], [
@@ -388,7 +394,7 @@ const window = undefined;
388
394
  /version\/([\w\.\,]+) .*(safari)/i // Safari
389
395
  ], [VERSION, NAME], [
390
396
  /webkit.+?(mobile ?safari|safari)(\/[\w\.]+)/i // Safari < 3.0
391
- ], [NAME, [VERSION, strMapper, oldSafariMap]], [
397
+ ], [NAME, [VERSION, '1']], [
392
398
 
393
399
  /(webkit|khtml)\/([\w\.]+)/i
394
400
  ], [NAME, VERSION], [
@@ -429,7 +435,7 @@ const window = undefined;
429
435
  /((?:i[346]|x)86)[;\)]/i // IA32 (x86)
430
436
  ], [[ARCHITECTURE, 'ia32']], [
431
437
 
432
- /\b(aarch64|arm(v?8e?l?|_?64))\b/i // ARM64
438
+ /\b(aarch64|arm(v?8e?l?|_?64))\b/i // ARM64
433
439
  ], [[ARCHITECTURE, 'arm64']], [
434
440
 
435
441
  /\b(arm(?:v[67])?ht?n?[fl]p?)\b/i // ARMHF
@@ -486,12 +492,14 @@ const window = undefined;
486
492
  ], [MODEL, [VENDOR, HUAWEI], [TYPE, MOBILE]], [
487
493
 
488
494
  // Xiaomi
489
- /\b(poco[\w ]+)(?: bui|\))/i, // Xiaomi POCO
495
+ /\b(poco[\w ]+|m2\d{3}j\d\d[a-z]{2})(?: bui|\))/i, // Xiaomi POCO
490
496
  /\b; (\w+) build\/hm\1/i, // Xiaomi Hongmi 'numeric' models
491
497
  /\b(hm[-_ ]?note?[_ ]?(?:\d\w)?) bui/i, // Xiaomi Hongmi
492
498
  /\b(redmi[\-_ ]?(?:note|k)?[\w_ ]+)(?: bui|\))/i, // Xiaomi Redmi
499
+ /oid[^\)]+; (m?[12][0-389][01]\w{3,6}[c-y])( bui|\))/i, // Xiaomi Redmi 'numeric' models
493
500
  /\b(mi[-_ ]?(?:a\d|one|one[_ ]plus|note lte|max|cc)?[_ ]?(?:\d?\w?)[_ ]?(?:plus|se|lite)?)(?: bui|\))/i // Xiaomi Mi
494
501
  ], [[MODEL, /_/g, ' '], [VENDOR, XIAOMI], [TYPE, MOBILE]], [
502
+ /oid[^\)]+; (2\d{4}(283|rpbf)[cgl])( bui|\))/i, // Redmi Pad
495
503
  /\b(mi[-_ ]?(?:pad)(?:[\w_ ]+))(?: bui|\))/i // Mi Pad tablets
496
504
  ],[[MODEL, /_/g, ' '], [VENDOR, XIAOMI], [TYPE, TABLET]], [
497
505
 
@@ -506,7 +514,7 @@ const window = undefined;
506
514
  ], [MODEL, [VENDOR, 'Vivo'], [TYPE, MOBILE]], [
507
515
 
508
516
  // Realme
509
- /\b(rmx[12]\d{3})(?: bui|;|\))/i
517
+ /\b(rmx[1-3]\d{3})(?: bui|;|\))/i
510
518
  ], [MODEL, [VENDOR, 'Realme'], [TYPE, MOBILE]], [
511
519
 
512
520
  // Motorola
@@ -592,9 +600,13 @@ const window = undefined;
592
600
  /droid.+; (m[1-5] note) bui/i,
593
601
  /\bmz-([-\w]{2,})/i
594
602
  ], [MODEL, [VENDOR, 'Meizu'], [TYPE, MOBILE]], [
603
+
604
+ // Ulefone
605
+ /; ((?:power )?armor(?:[\w ]{0,8}))(?: bui|\))/i
606
+ ], [MODEL, [VENDOR, 'Ulefone'], [TYPE, MOBILE]], [
595
607
 
596
608
  // MIXED
597
- /(blackberry|benq|palm(?=\-)|sonyericsson|acer|asus|dell|meizu|motorola|polytron)[-_ ]?([-\w]*)/i,
609
+ /(blackberry|benq|palm(?=\-)|sonyericsson|acer|asus|dell|meizu|motorola|polytron|infinix|tecno)[-_ ]?([-\w]*)/i,
598
610
  // BlackBerry/BenQ/Palm/Sony-Ericsson/Acer/Asus/Dell/Meizu/Motorola/Polytron
599
611
  /(hp) ([\w ]+\w)/i, // HP iPAQ
600
612
  /(asus)-?(\w+)/i, // Asus
@@ -639,7 +651,7 @@ const window = undefined;
639
651
  ], [VENDOR, [MODEL, APPLE+' TV'], [TYPE, SMARTTV]], [
640
652
  /crkey/i // Google Chromecast
641
653
  ], [[MODEL, CHROME+'cast'], [VENDOR, GOOGLE], [TYPE, SMARTTV]], [
642
- /droid.+aft(\w)( bui|\))/i // Fire TV
654
+ /droid.+aft(\w+)( bui|\))/i // Fire TV
643
655
  ], [MODEL, [VENDOR, AMAZON], [TYPE, SMARTTV]], [
644
656
  /\(dtv[\);].+(aquos)/i,
645
657
  /(aquos-tv[\w ]+)\)/i // Sharp
@@ -744,7 +756,7 @@ const window = undefined;
744
756
 
745
757
  // iOS/macOS
746
758
  /ip[honead]{2,4}\b(?:.*os ([\w]+) like mac|; opera)/i, // iOS
747
- /ios;fbsv\/([\d\.]+)/i,
759
+ /(?:ios;fbsv\/|iphone.+ios[\/ ])([\d\.]+)/i,
748
760
  /cfnetwork\/.+darwin/i
749
761
  ], [[VERSION, /_/g, '.'], [NAME, 'iOS']], [
750
762
  /(mac os x) ?([\w\. ]*)/i,
@@ -813,23 +825,23 @@ const window = undefined;
813
825
 
814
826
  var defaultProps = (function () {
815
827
  var props = { init : {}, isIgnore : {}, isIgnoreRgx : {}, toString : {}};
816
- assignFromEntries.call(props.init, [
828
+ setProps.call(props.init, [
817
829
  [UA_BROWSER, [NAME, VERSION, MAJOR]],
818
830
  [UA_CPU, [ARCHITECTURE]],
819
831
  [UA_DEVICE, [TYPE, MODEL, VENDOR]],
820
832
  [UA_ENGINE, [NAME, VERSION]],
821
833
  [UA_OS, [NAME, VERSION]]
822
834
  ]);
823
- assignFromEntries.call(props.isIgnore, [
835
+ setProps.call(props.isIgnore, [
824
836
  [UA_BROWSER, [VERSION, MAJOR]],
825
837
  [UA_ENGINE, [VERSION]],
826
838
  [UA_OS, [VERSION]]
827
839
  ]);
828
- assignFromEntries.call(props.isIgnoreRgx, [
840
+ setProps.call(props.isIgnoreRgx, [
829
841
  [UA_BROWSER, / ?browser$/i],
830
842
  [UA_OS, / ?os$/i]
831
843
  ]);
832
- assignFromEntries.call(props.toString, [
844
+ setProps.call(props.toString, [
833
845
  [UA_BROWSER, [NAME, VERSION]],
834
846
  [UA_CPU, [ARCHITECTURE]],
835
847
  [UA_DEVICE, [VENDOR, MODEL]],
@@ -839,34 +851,47 @@ const window = undefined;
839
851
  return props;
840
852
  })();
841
853
 
842
- var createUAParserData = function (itemType, ua, rgxMap, uaCH) {
854
+ var createIData = function (item, itemType) {
843
855
 
844
856
  var init_props = defaultProps.init[itemType],
845
857
  is_ignoreProps = defaultProps.isIgnore[itemType] || 0,
846
858
  is_ignoreRgx = defaultProps.isIgnoreRgx[itemType] || 0,
847
859
  toString_props = defaultProps.toString[itemType] || 0;
848
860
 
849
- function UAParserData () {
850
- assignFromEntries.call(this, init_props);
861
+ function IData () {
862
+ setProps.call(this, init_props);
851
863
  }
852
- UAParserData.prototype.withClientHints = function () {
853
-
864
+
865
+ IData.prototype.getItem = function () {
866
+ return item;
867
+ };
868
+
869
+ IData.prototype.withClientHints = function () {
870
+
854
871
  // nodejs / non-client-hints browsers
855
872
  if (!NAVIGATOR_UADATA) {
856
- return new UAParserItem(itemType, ua, rgxMap, uaCH).parseCH().get();
873
+ return item
874
+ .parseCH()
875
+ .get();
857
876
  }
858
877
 
859
878
  // browsers based on chromium 85+
860
879
  return NAVIGATOR_UADATA
861
880
  .getHighEntropyValues(CH_ALL_VALUES)
862
881
  .then(function (res) {
863
- var JS_UACH = new UAParserDataCH(res, false);
864
- return new UAParserItem(itemType, ua, rgxMap, JS_UACH).parseCH().get();
882
+ return item
883
+ .setCH(new UACHData(res, false))
884
+ .parseCH()
885
+ .get();
865
886
  });
866
887
  };
867
888
 
889
+ IData.prototype.withFeatureCheck = function () {
890
+ return item.detectFeature().get();
891
+ };
892
+
868
893
  if (itemType != UA_RESULT) {
869
- UAParserData.prototype.is = function (strToCheck) {
894
+ IData.prototype.is = function (strToCheck) {
870
895
  var is = false;
871
896
  for (var i in this) {
872
897
  if (this.hasOwnProperty(i) && !has(is_ignoreProps, i) && lowerize(is_ignoreRgx ? strip(is_ignoreRgx, this[i]) : this[i]) == lowerize(is_ignoreRgx ? strip(is_ignoreRgx, strToCheck) : strToCheck)) {
@@ -879,7 +904,7 @@ const window = undefined;
879
904
  }
880
905
  return is;
881
906
  };
882
- UAParserData.prototype.toString = function () {
907
+ IData.prototype.toString = function () {
883
908
  var str = EMPTY;
884
909
  for (var i in toString_props) {
885
910
  if (typeof(this[toString_props[i]]) !== UNDEF_TYPE) {
@@ -891,45 +916,45 @@ const window = undefined;
891
916
  }
892
917
 
893
918
  if (!NAVIGATOR_UADATA) {
894
- UAParserData.prototype.then = function (cb) {
919
+ IData.prototype.then = function (cb) {
895
920
  var that = this;
896
- var UAParserDataResolve = function () {
921
+ var IDataResolve = function () {
897
922
  for (var prop in that) {
898
923
  if (that.hasOwnProperty(prop)) {
899
924
  this[prop] = that[prop];
900
925
  }
901
926
  }
902
927
  };
903
- UAParserDataResolve.prototype = {
904
- is : UAParserData.prototype.is,
905
- toString : UAParserData.prototype.toString
928
+ IDataResolve.prototype = {
929
+ is : IData.prototype.is,
930
+ toString : IData.prototype.toString
906
931
  };
907
- var resolveData = new UAParserDataResolve();
932
+ var resolveData = new IDataResolve();
908
933
  cb(resolveData);
909
934
  return resolveData;
910
935
  };
911
936
  }
912
937
 
913
- return new UAParserData();
938
+ return new IData();
914
939
  };
915
940
 
916
941
  /////////////////
917
942
  // Constructor
918
943
  ////////////////
919
944
 
920
- function UAParserDataCH (uach, isHTTP_UACH) {
945
+ function UACHData (uach, isHttpUACH) {
921
946
  uach = uach || {};
922
- assignFromEntries.call(this, CH_ALL_VALUES);
923
- if (isHTTP_UACH) {
924
- assignFromEntries.call(this, [
947
+ setProps.call(this, CH_ALL_VALUES);
948
+ if (isHttpUACH) {
949
+ setProps.call(this, [
925
950
  [BRANDS, itemListToArray(uach[CH_HEADER])],
926
951
  [FULLVERLIST, itemListToArray(uach[CH_HEADER_FULL_VER_LIST])],
927
- [BRANDS, itemListToArray(uach[CH_HEADER])],
928
952
  [MOBILE, /\?1/.test(uach[CH_HEADER_MOBILE])],
929
953
  [MODEL, stripQuotes(uach[CH_HEADER_MODEL])],
930
954
  [PLATFORM, stripQuotes(uach[CH_HEADER_PLATFORM])],
931
955
  [PLATFORMVER, stripQuotes(uach[CH_HEADER_PLATFORM_VER])],
932
956
  [ARCHITECTURE, stripQuotes(uach[CH_HEADER_ARCH])],
957
+ [FORMFACTOR, itemListToArray(uach[CH_HEADER_FORM_FACTOR])],
933
958
  [BITNESS, stripQuotes(uach[CH_HEADER_BITNESS])]
934
959
  ]);
935
960
  } else {
@@ -937,127 +962,162 @@ const window = undefined;
937
962
  if(this.hasOwnProperty(prop) && typeof uach[prop] !== UNDEF_TYPE) this[prop] = uach[prop];
938
963
  }
939
964
  }
940
- return this;
941
965
  }
942
966
 
943
- function UAParserItem (itemType, ua, rgxMap, uaCH) {
944
- assignFromEntries.call(this, [
967
+ function UAItem (itemType, ua, rgxMap, uaCH) {
968
+
969
+ this.get = function (prop) {
970
+ if (!prop) return this.data;
971
+ return this.data.hasOwnProperty(prop) ? this.data[prop] : undefined;
972
+ };
973
+
974
+ this.set = function (prop, val) {
975
+ this.data[prop] = val;
976
+ return this;
977
+ };
978
+
979
+ this.setCH = function (ch) {
980
+ this.uaCH = ch;
981
+ return this;
982
+ };
983
+
984
+ this.detectFeature = function () {
985
+ if (NAVIGATOR && NAVIGATOR.userAgent == this.ua) {
986
+ switch (this.itemType) {
987
+ case UA_BROWSER:
988
+ // Brave-specific detection
989
+ if (NAVIGATOR.brave && typeof NAVIGATOR.brave.isBrave == FUNC_TYPE) {
990
+ this.set(NAME, 'Brave');
991
+ }
992
+ break;
993
+ case UA_DEVICE:
994
+ // Chrome-specific detection: check for 'mobile' value of navigator.userAgentData
995
+ if (!this.get(TYPE) && NAVIGATOR_UADATA && NAVIGATOR_UADATA[MOBILE]) {
996
+ this.set(TYPE, MOBILE);
997
+ }
998
+ // iPadOS-specific detection: identified as Mac, but has some iOS-only properties
999
+ if (this.get(MODEL) == 'Macintosh' && NAVIGATOR && typeof NAVIGATOR.standalone !== UNDEF_TYPE && NAVIGATOR.maxTouchPoints && NAVIGATOR.maxTouchPoints > 2) {
1000
+ this.set(MODEL, 'iPad')
1001
+ .set(TYPE, TABLET);
1002
+ }
1003
+ break;
1004
+ case UA_OS:
1005
+ // Chrome-specific detection: check for 'platform' value of navigator.userAgentData
1006
+ if (!this.get(NAME) && NAVIGATOR_UADATA && NAVIGATOR_UADATA[PLATFORM]) {
1007
+ this.set(NAME, NAVIGATOR_UADATA[PLATFORM]);
1008
+ }
1009
+ break;
1010
+ case UA_RESULT:
1011
+ var data = this.data;
1012
+ var detect = function (itemType) {
1013
+ return data[itemType]
1014
+ .getItem()
1015
+ .detectFeature()
1016
+ .get();
1017
+ };
1018
+ this.set(UA_BROWSER, detect(UA_BROWSER))
1019
+ .set(UA_CPU, detect(UA_CPU))
1020
+ .set(UA_DEVICE, detect(UA_DEVICE))
1021
+ .set(UA_ENGINE, detect(UA_ENGINE))
1022
+ .set(UA_OS, detect(UA_OS));
1023
+ }
1024
+ }
1025
+ return this;
1026
+ };
1027
+
1028
+ this.parseUA = function () {
1029
+ if (this.itemType != UA_RESULT) {
1030
+ rgxMapper.call(this.data, this.ua, this.rgxMap);
1031
+ }
1032
+ if (this.itemType == UA_BROWSER) {
1033
+ this.set(MAJOR, majorize(this.get(VERSION)));
1034
+ }
1035
+ return this;
1036
+ };
1037
+
1038
+ this.parseCH = function () {
1039
+ var uaCH = this.uaCH,
1040
+ rgxMap = this.rgxMap;
1041
+
1042
+ switch (this.itemType) {
1043
+ case UA_BROWSER:
1044
+ var brands = uaCH[FULLVERLIST] || uaCH[BRANDS];
1045
+ if (brands) {
1046
+ for (var i in brands) {
1047
+ var brandName = brands[i].brand,
1048
+ brandVersion = brands[i].version;
1049
+ if (!/not.a.brand/i.test(brandName) && (i < 1 || /chromi/i.test(this.get(NAME)))) {
1050
+ this.set(NAME, strip(GOOGLE+' ', brandName))
1051
+ .set(VERSION, brandVersion)
1052
+ .set(MAJOR, majorize(brandVersion));
1053
+ }
1054
+ }
1055
+ }
1056
+ break;
1057
+ case UA_CPU:
1058
+ var archName = uaCH[ARCHITECTURE];
1059
+ if (archName) {
1060
+ if (archName && uaCH[BITNESS] == '64') archName += '64';
1061
+ rgxMapper.call(this.data, archName + ';', rgxMap);
1062
+ }
1063
+ break;
1064
+ case UA_DEVICE:
1065
+ if (uaCH[MOBILE]) {
1066
+ this.set(TYPE, MOBILE);
1067
+ }
1068
+ if (uaCH[MODEL]) {
1069
+ this.set(MODEL, uaCH[MODEL]);
1070
+ }
1071
+ if (uaCH[FORMFACTOR]) {
1072
+ var ff;
1073
+ if (typeof uaCH[FORMFACTOR] !== 'string') {
1074
+ var idx = 0;
1075
+ while (!ff && idx < uaCH[FORMFACTOR].length) {
1076
+ ff = strMapper(uaCH[FORMFACTOR][idx++], formFactorMap);
1077
+ }
1078
+ } else {
1079
+ ff = strMapper(uaCH[FORMFACTOR], formFactorMap);
1080
+ }
1081
+ this.set(TYPE, ff);
1082
+ }
1083
+ break;
1084
+ case UA_OS:
1085
+ var osName = uaCH[PLATFORM];
1086
+ if(osName) {
1087
+ var osVersion = uaCH[PLATFORMVER];
1088
+ if (osName == WINDOWS) osVersion = (parseInt(majorize(osVersion), 10) >= 13 ? '11' : '10');
1089
+ this.set(NAME, osName)
1090
+ .set(VERSION, osVersion);
1091
+ }
1092
+ break;
1093
+ case UA_RESULT:
1094
+ var data = this.data;
1095
+ var parse = function (itemType) {
1096
+ return data[itemType]
1097
+ .getItem()
1098
+ .setCH(uaCH)
1099
+ .parseCH()
1100
+ .get();
1101
+ };
1102
+ this.set(UA_BROWSER, parse(UA_BROWSER))
1103
+ .set(UA_CPU, parse(UA_CPU))
1104
+ .set(UA_DEVICE, parse(UA_DEVICE))
1105
+ .set(UA_ENGINE, parse(UA_ENGINE))
1106
+ .set(UA_OS, parse(UA_OS));
1107
+ }
1108
+ return this;
1109
+ };
1110
+
1111
+ setProps.call(this, [
945
1112
  ['itemType', itemType],
946
1113
  ['ua', ua],
947
1114
  ['uaCH', uaCH],
948
1115
  ['rgxMap', rgxMap],
949
- ['data', createUAParserData(itemType, ua, rgxMap, uaCH)]
1116
+ ['data', createIData(this, itemType)]
950
1117
  ]);
951
- this.parse();
952
- var isSelfNav = NAVIGATOR && NAVIGATOR.userAgent == ua;
953
- switch(this.itemType) {
954
- case UA_BROWSER:
955
- // Brave-specific detection
956
- if (isSelfNav && NAVIGATOR.brave && typeof NAVIGATOR.brave.isBrave == FUNC_TYPE) {
957
- this.set(NAME, 'Brave');
958
- }
959
- this.set(MAJOR, majorize(this.get(VERSION)));
960
- break;
961
- case UA_DEVICE:
962
- if (isSelfNav && !this.get(TYPE) && NAVIGATOR_UADATA && NAVIGATOR_UADATA[MOBILE]) {
963
- this.set(TYPE, MOBILE);
964
- }
965
- // iPadOS-specific detection: identified as Mac, but has some iOS-only properties
966
- if (isSelfNav && this.get(MODEL) == 'Macintosh' && NAVIGATOR && typeof NAVIGATOR.standalone !== UNDEF_TYPE && NAVIGATOR.maxTouchPoints && NAVIGATOR.maxTouchPoints > 2) {
967
- this.set(MODEL, 'iPad')
968
- .set(TYPE, TABLET);
969
- }
970
- break;
971
- case UA_OS:
972
- if (isSelfNav && !this.get(NAME) && NAVIGATOR_UADATA && NAVIGATOR_UADATA[PLATFORM]) {
973
- this.set(NAME, NAVIGATOR_UADATA[PLATFORM]);
974
- }
975
- break;
976
- case UA_RESULT:
977
- var createUAParserItem = function (itemType) {
978
- return new UAParserItem(itemType, ua, rgxMap[itemType], uaCH).get();
979
- };
980
- this.set('ua', ua)
981
- .set(UA_BROWSER, createUAParserItem(UA_BROWSER))
982
- .set(UA_CPU, createUAParserItem(UA_CPU))
983
- .set(UA_DEVICE, createUAParserItem(UA_DEVICE))
984
- .set(UA_ENGINE, createUAParserItem(UA_ENGINE))
985
- .set(UA_OS, createUAParserItem(UA_OS))
986
- .get();
987
- }
1118
+
988
1119
  return this;
989
1120
  }
990
- UAParserItem.prototype.get = function (prop) {
991
- if (!prop) return this.data;
992
- return this.data.hasOwnProperty(prop) ? this.data[prop] : undefined;
993
- };
994
- UAParserItem.prototype.parse = function () {
995
- if (this.itemType != UA_RESULT) {
996
- rgxMapper.call(this.data, this.ua, this.rgxMap);
997
- }
998
- return this;
999
- };
1000
- UAParserItem.prototype.parseCH = function () {
1001
- var ua = this.ua,
1002
- uaCH = this.uaCH,
1003
- rgxMap = this.rgxMap;
1004
-
1005
- switch (this.itemType) {
1006
- case UA_BROWSER:
1007
- var brands = uaCH[FULLVERLIST] || uaCH[BRANDS];
1008
- if (brands) {
1009
- for (var i in brands) {
1010
- var brandName = brands[i].brand,
1011
- brandVersion = brands[i].version;
1012
- if (!/not.a.brand/i.test(brandName) && (i < 1 || /chromi/i.test(this.get(NAME)))) {
1013
- this.set(NAME, strip(GOOGLE+' ', brandName))
1014
- .set(VERSION, brandVersion)
1015
- .set(MAJOR, majorize(brandVersion));
1016
- }
1017
- }
1018
- }
1019
- break;
1020
- case UA_CPU:
1021
- var archName = uaCH[ARCHITECTURE];
1022
- if (archName) {
1023
- if (archName && uaCH[BITNESS] == '64') archName += '64';
1024
- rgxMapper.call(this.data, archName + ';', rgxMap);
1025
- }
1026
- break;
1027
- case UA_DEVICE:
1028
- if (uaCH[MOBILE]) {
1029
- this.set(TYPE, MOBILE);
1030
- }
1031
- if (uaCH[MODEL]) {
1032
- this.set(MODEL, uaCH[MODEL]);
1033
- }
1034
- break;
1035
- case UA_OS:
1036
- var osName = uaCH[PLATFORM];
1037
- if(osName) {
1038
- var osVersion = uaCH[PLATFORMVER];
1039
- if (osName == WINDOWS) osVersion = (parseInt(majorize(osVersion), 10) >= 13 ? '11' : '10');
1040
- this.set(NAME, osName)
1041
- .set(VERSION, osVersion);
1042
- }
1043
- break;
1044
- case UA_RESULT:
1045
- var createUAParserItemWithCH = function (itemType) {
1046
- return new UAParserItem(itemType, ua, rgxMap[itemType], uaCH).parseCH().get();
1047
- };
1048
- this.set('ua', ua)
1049
- .set(UA_BROWSER, createUAParserItemWithCH(UA_BROWSER))
1050
- .set(UA_CPU, createUAParserItemWithCH(UA_CPU))
1051
- .set(UA_DEVICE, createUAParserItemWithCH(UA_DEVICE))
1052
- .set(UA_ENGINE, createUAParserItemWithCH(UA_ENGINE))
1053
- .set(UA_OS, createUAParserItemWithCH(UA_OS));
1054
- }
1055
- return this;
1056
- };
1057
- UAParserItem.prototype.set = function (prop, val) {
1058
- this.data[prop] = val;
1059
- return this;
1060
- };
1061
1121
 
1062
1122
  function UAParser (ua, extensions, headers) {
1063
1123
 
@@ -1081,39 +1141,54 @@ const window = undefined;
1081
1141
  return new UAParser(ua, extensions, headers).getResult();
1082
1142
  }
1083
1143
 
1084
- var userAgent = ua ||
1085
- ((NAVIGATOR && NAVIGATOR.userAgent) ?
1086
- NAVIGATOR.userAgent :
1087
- (headers && headers[USER_AGENT] ?
1088
- headers[USER_AGENT] :
1089
- EMPTY)),
1090
-
1091
- HTTP_UACH = new UAParserDataCH(headers, true),
1144
+ var userAgent = typeof ua === STR_TYPE ? ua : // Passed user-agent string
1145
+ ((NAVIGATOR && NAVIGATOR.userAgent) ? NAVIGATOR.userAgent : // navigator.userAgent
1146
+ (headers && headers[USER_AGENT] ? headers[USER_AGENT] : // User-Agent from passed headers
1147
+ EMPTY)), // empty string
1092
1148
 
1149
+ httpUACH = new UACHData(headers, true),
1093
1150
  regexMap = extensions ?
1094
1151
  extend(defaultRegexes, extensions) :
1095
1152
  defaultRegexes,
1096
1153
 
1097
- createUAParserItemFunc = function (itemType) {
1098
- return function () {
1099
- return new UAParserItem(itemType, userAgent, itemType == UA_RESULT ? regexMap : regexMap[itemType], HTTP_UACH).get();
1100
- };
1154
+ createItemFunc = function (itemType) {
1155
+ if (itemType == UA_RESULT) {
1156
+ return function () {
1157
+ return new UAItem(itemType, userAgent, regexMap, httpUACH)
1158
+ .set('ua', userAgent)
1159
+ .set(UA_BROWSER, this.getBrowser())
1160
+ .set(UA_CPU, this.getCPU())
1161
+ .set(UA_DEVICE, this.getDevice())
1162
+ .set(UA_ENGINE, this.getEngine())
1163
+ .set(UA_OS, this.getOS())
1164
+ .get();
1165
+ };
1166
+ } else {
1167
+ return function () {
1168
+ return new UAItem(itemType, userAgent, regexMap[itemType], httpUACH)
1169
+ .parseUA()
1170
+ .get();
1171
+ };
1172
+ }
1101
1173
  };
1102
-
1174
+
1103
1175
  // public methods
1104
- assignFromEntries.call(this, [
1105
- ['getBrowser', createUAParserItemFunc(UA_BROWSER)],
1106
- ['getCPU', createUAParserItemFunc(UA_CPU)],
1107
- ['getDevice', createUAParserItemFunc(UA_DEVICE)],
1108
- ['getEngine', createUAParserItemFunc(UA_ENGINE)],
1109
- ['getOS', createUAParserItemFunc(UA_OS)],
1110
- ['getResult', createUAParserItemFunc(UA_RESULT)],
1176
+ setProps.call(this, [
1177
+ ['getBrowser', createItemFunc(UA_BROWSER)],
1178
+ ['getCPU', createItemFunc(UA_CPU)],
1179
+ ['getDevice', createItemFunc(UA_DEVICE)],
1180
+ ['getEngine', createItemFunc(UA_ENGINE)],
1181
+ ['getOS', createItemFunc(UA_OS)],
1182
+ ['getResult', createItemFunc(UA_RESULT)],
1111
1183
  ['getUA', function () { return userAgent; }],
1112
1184
  ['setUA', function (ua) {
1113
- userAgent = (typeof ua === STR_TYPE && ua.length > UA_MAX_LENGTH) ? trim(ua, UA_MAX_LENGTH) : ua;
1185
+ if (typeof ua === STR_TYPE)
1186
+ userAgent = ua.length > UA_MAX_LENGTH ? trim(ua, UA_MAX_LENGTH) : ua;
1114
1187
  return this;
1115
1188
  }]
1116
- ]).setUA(userAgent);
1189
+ ])
1190
+ .setUA(userAgent);
1191
+
1117
1192
  return this;
1118
1193
  }
1119
1194