ua-browser 0.1.8 → 1.0.0

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.
package/dist/index.mjs ADDED
@@ -0,0 +1,486 @@
1
+ // package.json
2
+ var package_default = {
3
+ version: "1.0.0"};
4
+
5
+ // src/constants/browsers.ts
6
+ var BROWSER_DEFS = [
7
+ // ── Generic / low-priority base browsers ──────────────────────────────────
8
+ { name: "Safari", priority: 10, detect: /Safari/, versionPattern: /Version\/([\d.]+)/ },
9
+ { name: "Chrome", priority: 20, detect: /(Chrome|CriOS)/, versionPattern: [/Chrome\/([\d.]+)/, /CriOS\/([\d.]+)/] },
10
+ { name: "IE", priority: 30, detect: /(MSIE|Trident)/, versionPattern: [/MSIE ([\d.]+)/, /rv:([\d.]+)/] },
11
+ { name: "Edge", priority: 40, detect: /(Edge|Edg\/|EdgA|EdgiOS)/, versionPattern: [/Edge\/([\d.]+)/, /Edg\/([\d.]+)/, /EdgA\/([\d.]+)/, /EdgiOS\/([\d.]+)/] },
12
+ { name: "Firefox", priority: 50, detect: /(Firefox|FxiOS)/, versionPattern: [/Firefox\/([\d.]+)/, /FxiOS\/([\d.]+)/] },
13
+ { name: "Firefox Focus", priority: 55, detect: /Focus/, versionPattern: /Focus\/([\d.]+)/ },
14
+ { name: "Chromium", priority: 60, detect: /Chromium/, versionPattern: /Chromium\/([\d.]+)/ },
15
+ { name: "Opera", priority: 70, detect: /(Opera|OPR|OPT)/, versionPattern: [/Opera\/([\d.]+)/, /OPR\/([\d.]+)/, /OPT\/([\d.]+)/] },
16
+ { name: "Vivaldi", priority: 80, detect: /Vivaldi/, versionPattern: /Vivaldi\/([\d.]+)/ },
17
+ { name: "Yandex", priority: 90, detect: /YaBrowser/, versionPattern: /YaBrowser\/([\d.]+)/ },
18
+ { name: "Arora", priority: 100, detect: /Arora/, versionPattern: /Arora\/([\d.]+)/ },
19
+ { name: "Lunascape", priority: 110, detect: /Lunascape/, versionPattern: /Lunascape[\s]([\d.]+)/ },
20
+ { name: "QupZilla", priority: 120, detect: /QupZilla/, versionPattern: /QupZilla[\s]([\d.]+)/ },
21
+ { name: "Coc Coc", priority: 130, detect: /coc_coc_browser/, versionPattern: /coc_coc_browser\/([\d.]+)/ },
22
+ { name: "Kindle", priority: 140, detect: /(Kindle|Silk\/)/, versionPattern: /Version\/([\d.]+)/ },
23
+ { name: "Iceweasel", priority: 150, detect: /Iceweasel/, versionPattern: /Iceweasel\/([\d.]+)/ },
24
+ { name: "Konqueror", priority: 160, detect: /Konqueror/, versionPattern: /Konqueror\/([\d.]+)/ },
25
+ { name: "Iceape", priority: 170, detect: /Iceape/, versionPattern: /Iceape\/([\d.]+)/ },
26
+ { name: "SeaMonkey", priority: 180, detect: /SeaMonkey/, versionPattern: /SeaMonkey\/([\d.]+)/ },
27
+ { name: "Epiphany", priority: 190, detect: /Epiphany/, versionPattern: /Epiphany\/([\d.]+)/ },
28
+ { name: "Maxthon", priority: 200, detect: /Maxthon/, versionPattern: /Maxthon\/([\d.]+)/ },
29
+ // ── Chinese / Asian browsers — higher priority than generic Chrome ─────────
30
+ { name: "360", priority: 300, detect: /(QihooBrowser|QHBrowser)/, versionPattern: /QihooBrowser\/([\d.]+)/ },
31
+ {
32
+ name: "360SE",
33
+ priority: 310,
34
+ detect: /360SE/,
35
+ versionPattern: null,
36
+ chromeLookup: {
37
+ "108": "14.0",
38
+ "86": "13.0",
39
+ "78": "12.0",
40
+ "69": "11.0",
41
+ "63": "10.0",
42
+ "55": "9.1",
43
+ "45": "8.1",
44
+ "42": "8.0",
45
+ "31": "7.0",
46
+ "21": "6.3"
47
+ }
48
+ },
49
+ {
50
+ name: "360EE",
51
+ priority: 320,
52
+ detect: /360EE/,
53
+ versionPattern: null,
54
+ chromeLookup: {
55
+ "86": "13.0",
56
+ "78": "12.0",
57
+ "69": "11.0",
58
+ "63": "9.5",
59
+ "55": "9.0",
60
+ "50": "8.7",
61
+ "30": "7.5"
62
+ }
63
+ },
64
+ { name: "UC", priority: 330, detect: /(UCBrowser|UBrowser|UCWEB)/, versionPattern: /UC?Browser\/([\d.]+)/ },
65
+ { name: "QQBrowser", priority: 340, detect: /QQBrowser/, versionPattern: /QQBrowser\/([\d.]+)/ },
66
+ { name: "QQ", priority: 345, detect: /QQ\//, versionPattern: /QQ\/([\d.]+)/ },
67
+ { name: "Baidu", priority: 350, detect: /(Baidu|BIDUBrowser|baidubrowser|baiduboxapp|BaiduHD)/, versionPattern: [/BIDUBrowser[\s/]([\d.]+)/, /baiduboxapp\/([\d.]+)/] },
68
+ { name: "Sogou", priority: 360, detect: /(MetaSr|Sogou)/, versionPattern: [/SE ([\d.X]+)/, /SogouMobileBrowser\/([\d.]+)/] },
69
+ {
70
+ name: "Liebao",
71
+ priority: 370,
72
+ detect: /(LBBROWSER|LieBaoFast)/,
73
+ versionPattern: /LieBaoFast\/([\d.]+)/,
74
+ chromeLookup: {
75
+ "57": "6.5",
76
+ "49": "6.0",
77
+ "46": "5.9",
78
+ "42": "5.3",
79
+ "39": "5.2",
80
+ "34": "5.0",
81
+ "29": "4.5",
82
+ "21": "4.0"
83
+ }
84
+ },
85
+ {
86
+ name: "2345Explorer",
87
+ priority: 380,
88
+ detect: /2345Explorer/,
89
+ versionPattern: [/2345Explorer\/([\d.]+)/, /Mb2345Browser\/([\d.]+)/],
90
+ chromeLookup: { "69": "10.0", "55": "9.9" }
91
+ },
92
+ { name: "115Browser", priority: 390, detect: /115Browser/, versionPattern: /115Browser\/([\d.]+)/ },
93
+ { name: "TheWorld", priority: 400, detect: /TheWorld/, versionPattern: /TheWorld ([\d.]+)/ },
94
+ { name: "XiaoMi", priority: 410, detect: /MiuiBrowser/, versionPattern: /MiuiBrowser\/([\d.]+)/ },
95
+ { name: "Vivo", priority: 420, detect: /VivoBrowser/, versionPattern: /VivoBrowser\/([\d.]+)/ },
96
+ { name: "Huawei", priority: 430, detect: /HuaweiBrowser/, versionPattern: [/HuaweiBrowser\/([\d.]+)/, /Version\/([\d.]+)/] },
97
+ { name: "OPPO", priority: 440, detect: /HeyTapBrowser/, versionPattern: /HeyTapBrowser\/([\d.]+)/ },
98
+ { name: "Quark", priority: 450, detect: /Quark/, versionPattern: /Quark\/([\d.]+)/ },
99
+ { name: "Qiyu", priority: 460, detect: /Qiyu/, versionPattern: /Qiyu\/([\d.]+)/ },
100
+ // ── App webviews — highest priority ───────────────────────────────────────
101
+ { name: "WechatWork", priority: 500, detect: /wxwork\//, versionPattern: /wxwork\/([\d.]+)/ },
102
+ { name: "Wechat", priority: 510, detect: /MicroMessenger/, versionPattern: /MicroMessenger\/([\d.]+)/ },
103
+ { name: "Taobao", priority: 520, detect: /AliApp\(TB/, versionPattern: /AliApp\(TB\/([\d.]+)/ },
104
+ { name: "Alipay", priority: 530, detect: /AliApp\(AP/, versionPattern: /AliApp\(AP\/([\d.]+)/ },
105
+ { name: "Weibo", priority: 540, detect: /Weibo/, versionPattern: /weibo__([\d.]+)/ },
106
+ { name: "Douban", priority: 550, detect: /com\.douban\.frodo/, versionPattern: /com\.douban\.frodo\/([\d.]+)/ },
107
+ { name: "Suning", priority: 560, detect: /SNEBUY-APP/, versionPattern: /SNEBUY-APP([\d.]+)/ },
108
+ { name: "iQiYi", priority: 570, detect: /IqiyiApp/, versionPattern: /IqiyiVersion\/([\d.]+)/ },
109
+ { name: "DingTalk", priority: 580, detect: /DingTalk/, versionPattern: /DingTalk\/([\d.]+)/ },
110
+ { name: "Douyin", priority: 590, detect: /aweme/, versionPattern: /app_version\/([\d.]+)/ }
111
+ ];
112
+
113
+ // src/utils/extract.ts
114
+ function extractVersion(ua, pattern) {
115
+ const m = pattern.exec(ua);
116
+ if (!m) return null;
117
+ const v = m[1];
118
+ return v != null && v !== "" ? v : null;
119
+ }
120
+ function extractVersionFromPatterns(ua, patterns) {
121
+ for (const p of patterns) {
122
+ const v = extractVersion(ua, p);
123
+ if (v !== null) return v;
124
+ }
125
+ return null;
126
+ }
127
+ function lookupFromChromeVersion(ua, table) {
128
+ const m = /Chrome\/([\d]+)/.exec(ua);
129
+ if (!m) return null;
130
+ const major = m[1];
131
+ return Object.prototype.hasOwnProperty.call(table, major) ? table[major] : null;
132
+ }
133
+
134
+ // src/detectors/browser.ts
135
+ function detectBrowser(ua) {
136
+ let best = null;
137
+ for (const def of BROWSER_DEFS) {
138
+ if (def.detect.test(ua)) {
139
+ if (best === null || def.priority >= best.priority) {
140
+ best = def;
141
+ }
142
+ }
143
+ }
144
+ if (!best) return { browser: "unknown", version: "unknown" };
145
+ let version = null;
146
+ if (best.chromeLookup) {
147
+ version = lookupFromChromeVersion(ua, best.chromeLookup);
148
+ }
149
+ if (version === null && best.versionPattern !== null) {
150
+ const patterns = Array.isArray(best.versionPattern) ? best.versionPattern : [best.versionPattern];
151
+ version = extractVersionFromPatterns(ua, patterns);
152
+ }
153
+ return { browser: best.name, version: version != null ? version : "unknown" };
154
+ }
155
+
156
+ // src/constants/engines.ts
157
+ var ENGINE_DEFS = [
158
+ { name: "KHTML", detect: /KHTML\// },
159
+ { name: "Trident", detect: /(Trident|NET CLR)/ },
160
+ { name: "Presto", detect: /Presto/ },
161
+ { name: "Gecko", detect: /Gecko\// },
162
+ { name: "WebKit", detect: /AppleWebKit/ }
163
+ ];
164
+
165
+ // src/detectors/engine.ts
166
+ function detectEngine(ua, browser, version) {
167
+ var _a, _b;
168
+ let engine = "unknown";
169
+ for (const def of ENGINE_DEFS) {
170
+ if (def.detect.test(ua)) {
171
+ engine = def.name;
172
+ }
173
+ }
174
+ if (engine === "WebKit" && /(Chrome|CriOS)/.test(ua) && parseInt((_b = ((_a = /Chrome\/([\d]+)/.exec(ua)) != null ? _a : [])[1]) != null ? _b : "0", 10) > 27) {
175
+ engine = "Blink";
176
+ } else if (browser === "Opera" && parseInt(version, 10) > 12) {
177
+ engine = "Blink";
178
+ } else if (browser === "Yandex") {
179
+ engine = "Blink";
180
+ }
181
+ if (browser === "Edge") {
182
+ engine = parseInt(version, 10) > 75 ? "Blink" : "EdgeHTML";
183
+ }
184
+ return engine;
185
+ }
186
+
187
+ // src/constants/os.ts
188
+ var OS_DEFS = [
189
+ { name: "WebOS", detect: /hpwOS/, versionPattern: /hpwOS\/([\d.]+)/ },
190
+ { name: "Symbian", detect: /Symbian/, versionPattern: null },
191
+ { name: "MeeGo", detect: /MeeGo/, versionPattern: null },
192
+ { name: "BlackBerry", detect: /(BlackBerry|RIM)/, versionPattern: null },
193
+ { name: "Windows Phone", detect: /(IEMobile|Windows Phone)/, versionPattern: /Windows Phone(?: OS)? ([\d.]+)/ },
194
+ { name: "FreeBSD", detect: /FreeBSD/, versionPattern: null },
195
+ { name: "Debian", detect: /Debian/, versionPattern: /Debian\/([\d.]+)/ },
196
+ { name: "Ubuntu", detect: /Ubuntu/, versionPattern: null },
197
+ { name: "Chrome OS", detect: /CrOS/, versionPattern: null },
198
+ { name: "Linux", detect: /(Linux|X11)/, versionPattern: null },
199
+ { name: "iOS", detect: /like Mac OS X/, versionPattern: /OS ([\d_]+) like/ },
200
+ { name: "MacOS", detect: /Macintosh/, versionPattern: /Mac OS X -?([\d_.]+)/ },
201
+ {
202
+ name: "HarmonyOS",
203
+ detect: /HarmonyOS/,
204
+ versionPattern: /Android ([\d.]+)[;)]/,
205
+ versionLookup: { "10": "2" }
206
+ },
207
+ { name: "Android", detect: /(Android|Adr)/, versionPattern: /(?:Android|Adr) ([\d.]+)/ },
208
+ {
209
+ name: "Windows",
210
+ detect: /Windows/,
211
+ versionPattern: /Windows NT ([\d.]+)/,
212
+ versionLookup: {
213
+ "10": "10",
214
+ "6.4": "10",
215
+ "6.3": "8.1",
216
+ "6.2": "8",
217
+ "6.1": "7",
218
+ "6.0": "Vista",
219
+ "5.2": "XP",
220
+ "5.1": "XP",
221
+ "5.0": "2000"
222
+ }
223
+ }
224
+ ];
225
+
226
+ // src/detectors/os.ts
227
+ function detectOs(ua, windowsVersion) {
228
+ let matchedDef = null;
229
+ for (const def of OS_DEFS) {
230
+ if (def.detect.test(ua)) {
231
+ matchedDef = def;
232
+ }
233
+ }
234
+ if (!matchedDef) return { os: "unknown", osVersion: "unknown" };
235
+ let osVersion = "unknown";
236
+ if (matchedDef.versionPattern) {
237
+ const raw = extractVersion(ua, matchedDef.versionPattern);
238
+ if (raw !== null) {
239
+ const normalised = raw.replace(/_/g, ".");
240
+ if (matchedDef.versionLookup) {
241
+ const mapped = Object.prototype.hasOwnProperty.call(matchedDef.versionLookup, normalised) ? matchedDef.versionLookup[normalised] : null;
242
+ if (mapped !== null) {
243
+ osVersion = mapped;
244
+ } else if (matchedDef.name === "Windows") {
245
+ osVersion = parseInt(normalised, 10).toString();
246
+ }
247
+ } else {
248
+ osVersion = normalised;
249
+ }
250
+ }
251
+ }
252
+ if (matchedDef.name === "Windows" && windowsVersion) {
253
+ osVersion = windowsVersion;
254
+ }
255
+ return { os: matchedDef.name, osVersion };
256
+ }
257
+
258
+ // src/constants/devices.ts
259
+ var DEVICE_DEFS = [
260
+ { name: "Mobile", detect: /(Mobi|iPh|480)/ },
261
+ { name: "Tablet", detect: /(Tablet|Pad|Nexus 7)/ }
262
+ ];
263
+
264
+ // src/detectors/device.ts
265
+ function detectDevice(ua, nav) {
266
+ if ((nav == null ? void 0 : nav.platform) === "MacIntel" && nav.maxTouchPoints > 1) {
267
+ return "Tablet";
268
+ }
269
+ if (/iPad/.test(ua)) {
270
+ return "Tablet";
271
+ }
272
+ for (const def of DEVICE_DEFS) {
273
+ if (def.detect.test(ua)) {
274
+ return def.name;
275
+ }
276
+ }
277
+ return "PC";
278
+ }
279
+
280
+ // src/constants/bots.ts
281
+ var BOT_DEFS = [
282
+ // Search engines
283
+ { name: "Googlebot", detect: /Googlebot/ },
284
+ { name: "Bingbot", detect: /(bingbot|BingPreview)/ },
285
+ { name: "Baiduspider", detect: /(Baiduspider|BaiduMobaider)/ },
286
+ { name: "Bytespider", detect: /Bytespider/ },
287
+ { name: "YandexBot", detect: /YandexBot/ },
288
+ { name: "DuckDuckBot", detect: /DuckDuckBot/ },
289
+ { name: "Slurp", detect: /Slurp/ },
290
+ { name: "Sogou", detect: /(Sogou|sogou).*[Ss]pider/ },
291
+ { name: "360Spider", detect: /360Spider/ },
292
+ { name: "PetalBot", detect: /PetalBot/ },
293
+ { name: "Applebot", detect: /Applebot/ },
294
+ // Social
295
+ { name: "Facebookbot", detect: /(facebookexternalhit|FacebookBot)/ },
296
+ { name: "Twitterbot", detect: /Twitterbot/ },
297
+ { name: "LinkedInBot", detect: /LinkedInBot/ },
298
+ // SEO tools
299
+ { name: "SemrushBot", detect: /SemrushBot/ },
300
+ { name: "AhrefsBot", detect: /AhrefsBot/ },
301
+ { name: "MJ12bot", detect: /MJ12bot/ },
302
+ // Generic catch-all (must be last)
303
+ { name: "GenericBot", detect: /(bot|crawler|spider|crawling|scraper)/i }
304
+ ];
305
+
306
+ // src/detectors/bot.ts
307
+ function detectBot(ua) {
308
+ for (const def of BOT_DEFS) {
309
+ if (def.detect.test(ua)) {
310
+ return { isBot: true, botName: def.name };
311
+ }
312
+ }
313
+ return { isBot: false, botName: "unknown" };
314
+ }
315
+
316
+ // src/constants/arch.ts
317
+ var ARCH_DEFS = [
318
+ { name: "arm64", detect: /(aarch64|arm64|ARM64)/ },
319
+ { name: "arm", detect: /\bARM\b/ },
320
+ { name: "x86_64", detect: /(x86_64|Win64|WOW64|x64;|amd64)/i },
321
+ { name: "x86", detect: /(i[36]86|i686|x86;)/ }
322
+ ];
323
+
324
+ // src/detectors/arch.ts
325
+ function detectArch(ua) {
326
+ for (const def of ARCH_DEFS) {
327
+ if (def.detect.test(ua)) {
328
+ return def.name;
329
+ }
330
+ }
331
+ return "unknown";
332
+ }
333
+
334
+ // src/detectors/headless.ts
335
+ var HEADLESS_PATTERN = /(HeadlessChrome|Headless|PhantomJS|Electron\/|Playwright)/;
336
+ function detectHeadless(ua) {
337
+ return HEADLESS_PATTERN.test(ua);
338
+ }
339
+
340
+ // src/utils/navigator.ts
341
+ function getNavContext() {
342
+ if (typeof navigator === "undefined") {
343
+ return { userAgent: "", platform: "", language: "", maxTouchPoints: 0 };
344
+ }
345
+ return navigator;
346
+ }
347
+ function getMimeType(nav, type) {
348
+ var _a;
349
+ try {
350
+ return !!((_a = nav.mimeTypes) == null ? void 0 : _a.namedItem(type));
351
+ } catch (e) {
352
+ return false;
353
+ }
354
+ }
355
+ function getLanguage(nav) {
356
+ var _a, _b;
357
+ const raw = (_b = (_a = nav.browserLanguage) != null ? _a : nav.language) != null ? _b : "";
358
+ const normalised = raw.replace(/-\w+/g, (w) => w.toUpperCase());
359
+ return normalised || "unknown";
360
+ }
361
+
362
+ // src/parse.ts
363
+ function parseUA(ua, options = {}) {
364
+ var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j;
365
+ const { nav, windowsVersion } = options;
366
+ const { browser: rawBrowser, version: rawVersion } = detectBrowser(ua);
367
+ const { os, osVersion } = detectOs(ua, windowsVersion);
368
+ const device = detectDevice(ua, nav);
369
+ const arch = detectArch(ua);
370
+ const { isBot, botName } = detectBot(ua);
371
+ const isHeadless = detectHeadless(ua);
372
+ const language = nav ? getLanguage(nav) : "unknown";
373
+ const platform = (_a = nav == null ? void 0 : nav.platform) != null ? _a : "unknown";
374
+ let browser = rawBrowser;
375
+ let version = rawVersion;
376
+ if (nav) {
377
+ const chromeGlobal = typeof chrome !== "undefined" ? chrome : void 0;
378
+ const chromeMajor = parseInt((_c = ((_b = /Chrome\/([\d]+)/.exec(ua)) != null ? _b : [])[1]) != null ? _c : "0", 10);
379
+ if (chromeGlobal) {
380
+ if (chromeGlobal.adblock2345 || chromeGlobal.common2345) {
381
+ browser = "2345Explorer";
382
+ version = "unknown";
383
+ } else {
384
+ let is360 = false;
385
+ if (getMimeType(nav, "application/360softmgrplugin") || getMimeType(nav, "application/mozilla-npqihooquicklogin") || chromeMajor > 36 && typeof showModalDialog !== "undefined") {
386
+ is360 = true;
387
+ } else if (chromeMajor > 45) {
388
+ is360 = getMimeType(nav, "application/vnd.chromium.remoting-viewer");
389
+ if (!is360 && chromeMajor >= 69) {
390
+ is360 = getMimeType(nav, "application/hwepass2001.installepass2001") || getMimeType(nav, "application/asx");
391
+ }
392
+ }
393
+ if (is360) {
394
+ if (getMimeType(nav, "application/gameplugin") || !((_d = nav.connection) == null ? void 0 : _d.saveData)) {
395
+ browser = "360SE";
396
+ } else {
397
+ browser = "360EE";
398
+ }
399
+ version = "unknown";
400
+ }
401
+ }
402
+ }
403
+ }
404
+ if (browser === "Baidu" && /(Opera|OPR|OPT)/.test(ua)) {
405
+ browser = "Opera";
406
+ version = (_j = (_i = (_g = ((_e = /OPR\/([\d.]+)/.exec(ua)) != null ? _e : [])[1]) != null ? _g : ((_f = /OPT\/([\d.]+)/.exec(ua)) != null ? _f : [])[1]) != null ? _i : ((_h = /Opera\/([\d.]+)/.exec(ua)) != null ? _h : [])[1]) != null ? _j : "unknown";
407
+ }
408
+ if (browser === "Chrome" && /\S+Browser\//.test(ua)) {
409
+ const m = /(\S+Browser)\/([\d.]+)/.exec(ua);
410
+ if (m) {
411
+ browser = m[1];
412
+ version = m[2];
413
+ }
414
+ }
415
+ if (browser === "Firefox" && nav) {
416
+ try {
417
+ if (typeof clientInformation !== "undefined" || typeof u2f === "undefined") {
418
+ browser = "Firefox Nightly";
419
+ }
420
+ } catch (e) {
421
+ }
422
+ }
423
+ if (browser === "Wechat") {
424
+ try {
425
+ if (typeof __wxjs_environment !== "undefined" && __wxjs_environment === "miniprogram") {
426
+ browser = "Wechat Miniapp";
427
+ }
428
+ } catch (e) {
429
+ }
430
+ }
431
+ const engine = detectEngine(ua, browser, version);
432
+ return {
433
+ browser,
434
+ version,
435
+ engine,
436
+ os,
437
+ osVersion,
438
+ device,
439
+ arch,
440
+ isWebview: /; wv/.test(ua),
441
+ isHeadless,
442
+ isBot,
443
+ botName,
444
+ language,
445
+ platform
446
+ };
447
+ }
448
+
449
+ // src/utils/windows-version.ts
450
+ async function getWindowsVersion(nav) {
451
+ var _a, _b;
452
+ if (!nav.userAgentData || nav.userAgentData.platform !== "Windows") {
453
+ return null;
454
+ }
455
+ try {
456
+ const data = await nav.userAgentData.getHighEntropyValues(["platformVersion"]);
457
+ const major = parseInt((_b = (_a = data["platformVersion"]) == null ? void 0 : _a.split(".")[0]) != null ? _b : "0", 10);
458
+ return major >= 13 ? "11" : "10";
459
+ } catch (e) {
460
+ return null;
461
+ }
462
+ }
463
+
464
+ // src/index.ts
465
+ var { version: VERSION } = package_default;
466
+ var isWebview = (ua) => /; wv/.test(ua);
467
+ var isWechatMiniapp = () => {
468
+ try {
469
+ return typeof __wxjs_environment !== "undefined" && __wxjs_environment === "miniprogram";
470
+ } catch (e) {
471
+ return false;
472
+ }
473
+ };
474
+ function uaBrowser(ua) {
475
+ const nav = getNavContext();
476
+ return parseUA(ua != null ? ua : nav.userAgent, { nav });
477
+ }
478
+ uaBrowser.isWebview = isWebview;
479
+ uaBrowser.isWechatMiniapp = isWechatMiniapp;
480
+ uaBrowser.getLanguage = () => getLanguage(getNavContext());
481
+ uaBrowser.VERSION = VERSION;
482
+ var src_default = uaBrowser;
483
+
484
+ export { VERSION, src_default as default, detectArch, detectBot, detectHeadless, getLanguage, getNavContext, getWindowsVersion, isWebview, isWechatMiniapp, parseUA };
485
+ //# sourceMappingURL=index.mjs.map
486
+ //# sourceMappingURL=index.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../package.json","../src/constants/browsers.ts","../src/utils/extract.ts","../src/detectors/browser.ts","../src/constants/engines.ts","../src/detectors/engine.ts","../src/constants/os.ts","../src/detectors/os.ts","../src/constants/devices.ts","../src/detectors/device.ts","../src/constants/bots.ts","../src/detectors/bot.ts","../src/constants/arch.ts","../src/detectors/arch.ts","../src/detectors/headless.ts","../src/utils/navigator.ts","../src/parse.ts","../src/utils/windows-version.ts","../src/index.ts"],"names":[],"mappings":"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","file":"index.mjs","sourcesContent":["{\n \"name\": \"ua-browser\",\n \"version\": \"1.0.0\",\n \"description\": \"uaBrowser - Browser, OS, engine and device detection from user agent strings. Supports Node.js. Zero dependencies.\",\n \"type\": \"module\",\n \"main\": \"./dist/index.cjs\",\n \"module\": \"./dist/index.mjs\",\n \"types\": \"./dist/index.d.ts\",\n \"exports\": {\n \".\": {\n \"require\": {\n \"types\": \"./dist/index.d.cts\",\n \"default\": \"./dist/index.cjs\"\n },\n \"import\": {\n \"types\": \"./dist/index.d.ts\",\n \"default\": \"./dist/index.mjs\"\n }\n }\n },\n \"files\": [\n \"dist\"\n ],\n \"sideEffects\": false,\n \"scripts\": {\n \"release\": \"pnpm build && changeset publish\",\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"test\": \"vitest run\",\n \"test:watch\": \"vitest\",\n \"test:coverage\": \"vitest run --coverage\",\n \"lint\": \"eslint src --ext .ts\",\n \"typecheck\": \"tsc -p tsconfig.build.json --noEmit\",\n \"docs:dev\": \"pnpm build && vitepress dev docs\",\n \"docs:build\": \"pnpm build && vitepress build docs\",\n \"docs:preview\": \"vitepress preview docs\"\n },\n \"repository\": {\n \"type\": \"git\",\n \"url\": \"git+https://github.com/yangtianxia/ua-browser.git\"\n },\n \"keywords\": [\n \"uaBrowser\",\n \"userAgent\",\n \"javascript\",\n \"typescript\",\n \"browser-detection\",\n \"user-agent-parser\"\n ],\n \"author\": \"yangtianxia\",\n \"license\": \"MIT\",\n \"bugs\": {\n \"url\": \"https://github.com/yangtianxia/ua-browser/issues\"\n },\n \"homepage\": \"https://github.com/yangtianxia/ua-browser#readme\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.29.4\",\n \"@typescript-eslint/eslint-plugin\": \"^7.0.0\",\n \"@typescript-eslint/parser\": \"^7.0.0\",\n \"@vitest/coverage-v8\": \"^1.6.0\",\n \"eslint\": \"^8.57.0\",\n \"eslint-plugin-import\": \"^2.29.1\",\n \"tsup\": \"^8.0.2\",\n \"typescript\": \"^5.4.0\",\n \"vitepress\": \"^1.6.4\",\n \"vitest\": \"^1.6.0\",\n \"vue\": \"^3.5.32\"\n }\n}\n","import type { BrowserName } from '../types.js'\n\nexport interface BrowserDef {\n name: BrowserName\n /** Detection regex — must match the UA for this browser to be a candidate. */\n detect: RegExp\n /**\n * Version extraction: capture-group regex (or array tried in order).\n * null = no direct version pattern (use chromeLookup only, or lookup table browsers).\n */\n versionPattern: RegExp | RegExp[] | null\n /** Chrome major-version → browser display version lookup (e.g. 360SE/EE, Liebao). */\n chromeLookup?: Record<string, string>\n /**\n * Detection priority. When multiple entries match the same UA, the one with\n * the highest priority wins. Explicit and verifiable — no reverse-iteration magic.\n */\n priority: number\n}\n\nexport const BROWSER_DEFS: readonly BrowserDef[] = [\n // ── Generic / low-priority base browsers ──────────────────────────────────\n { name: 'Safari', priority: 10, detect: /Safari/, versionPattern: /Version\\/([\\d.]+)/ },\n { name: 'Chrome', priority: 20, detect: /(Chrome|CriOS)/, versionPattern: [/Chrome\\/([\\d.]+)/, /CriOS\\/([\\d.]+)/] },\n { name: 'IE', priority: 30, detect: /(MSIE|Trident)/, versionPattern: [/MSIE ([\\d.]+)/, /rv:([\\d.]+)/] },\n { name: 'Edge', priority: 40, detect: /(Edge|Edg\\/|EdgA|EdgiOS)/, versionPattern: [/Edge\\/([\\d.]+)/, /Edg\\/([\\d.]+)/, /EdgA\\/([\\d.]+)/, /EdgiOS\\/([\\d.]+)/] },\n { name: 'Firefox', priority: 50, detect: /(Firefox|FxiOS)/, versionPattern: [/Firefox\\/([\\d.]+)/, /FxiOS\\/([\\d.]+)/] },\n { name: 'Firefox Focus', priority: 55, detect: /Focus/, versionPattern: /Focus\\/([\\d.]+)/ },\n { name: 'Chromium', priority: 60, detect: /Chromium/, versionPattern: /Chromium\\/([\\d.]+)/ },\n { name: 'Opera', priority: 70, detect: /(Opera|OPR|OPT)/, versionPattern: [/Opera\\/([\\d.]+)/, /OPR\\/([\\d.]+)/, /OPT\\/([\\d.]+)/] },\n { name: 'Vivaldi', priority: 80, detect: /Vivaldi/, versionPattern: /Vivaldi\\/([\\d.]+)/ },\n { name: 'Yandex', priority: 90, detect: /YaBrowser/, versionPattern: /YaBrowser\\/([\\d.]+)/ },\n { name: 'Arora', priority: 100, detect: /Arora/, versionPattern: /Arora\\/([\\d.]+)/ },\n { name: 'Lunascape', priority: 110, detect: /Lunascape/, versionPattern: /Lunascape[\\s]([\\d.]+)/ },\n { name: 'QupZilla', priority: 120, detect: /QupZilla/, versionPattern: /QupZilla[\\s]([\\d.]+)/ },\n { name: 'Coc Coc', priority: 130, detect: /coc_coc_browser/, versionPattern: /coc_coc_browser\\/([\\d.]+)/ },\n { name: 'Kindle', priority: 140, detect: /(Kindle|Silk\\/)/, versionPattern: /Version\\/([\\d.]+)/ },\n { name: 'Iceweasel', priority: 150, detect: /Iceweasel/, versionPattern: /Iceweasel\\/([\\d.]+)/ },\n { name: 'Konqueror', priority: 160, detect: /Konqueror/, versionPattern: /Konqueror\\/([\\d.]+)/ },\n { name: 'Iceape', priority: 170, detect: /Iceape/, versionPattern: /Iceape\\/([\\d.]+)/ },\n { name: 'SeaMonkey', priority: 180, detect: /SeaMonkey/, versionPattern: /SeaMonkey\\/([\\d.]+)/ },\n { name: 'Epiphany', priority: 190, detect: /Epiphany/, versionPattern: /Epiphany\\/([\\d.]+)/ },\n { name: 'Maxthon', priority: 200, detect: /Maxthon/, versionPattern: /Maxthon\\/([\\d.]+)/ },\n\n // ── Chinese / Asian browsers — higher priority than generic Chrome ─────────\n { name: '360', priority: 300, detect: /(QihooBrowser|QHBrowser)/, versionPattern: /QihooBrowser\\/([\\d.]+)/ },\n { name: '360SE', priority: 310, detect: /360SE/, versionPattern: null,\n chromeLookup: { '108': '14.0', '86': '13.0', '78': '12.0', '69': '11.0',\n '63': '10.0', '55': '9.1', '45': '8.1', '42': '8.0', '31': '7.0', '21': '6.3' } },\n { name: '360EE', priority: 320, detect: /360EE/, versionPattern: null,\n chromeLookup: { '86': '13.0', '78': '12.0', '69': '11.0', '63': '9.5',\n '55': '9.0', '50': '8.7', '30': '7.5' } },\n { name: 'UC', priority: 330, detect: /(UCBrowser|UBrowser|UCWEB)/, versionPattern: /UC?Browser\\/([\\d.]+)/ },\n { name: 'QQBrowser', priority: 340, detect: /QQBrowser/, versionPattern: /QQBrowser\\/([\\d.]+)/ },\n { name: 'QQ', priority: 345, detect: /QQ\\//, versionPattern: /QQ\\/([\\d.]+)/ },\n { name: 'Baidu', priority: 350, detect: /(Baidu|BIDUBrowser|baidubrowser|baiduboxapp|BaiduHD)/, versionPattern: [/BIDUBrowser[\\s/]([\\d.]+)/, /baiduboxapp\\/([\\d.]+)/] },\n { name: 'Sogou', priority: 360, detect: /(MetaSr|Sogou)/, versionPattern: [/SE ([\\d.X]+)/, /SogouMobileBrowser\\/([\\d.]+)/] },\n { name: 'Liebao', priority: 370, detect: /(LBBROWSER|LieBaoFast)/, versionPattern: /LieBaoFast\\/([\\d.]+)/,\n chromeLookup: { '57': '6.5', '49': '6.0', '46': '5.9', '42': '5.3',\n '39': '5.2', '34': '5.0', '29': '4.5', '21': '4.0' } },\n { name: '2345Explorer', priority: 380, detect: /2345Explorer/, versionPattern: [/2345Explorer\\/([\\d.]+)/, /Mb2345Browser\\/([\\d.]+)/],\n chromeLookup: { '69': '10.0', '55': '9.9' } },\n { name: '115Browser', priority: 390, detect: /115Browser/, versionPattern: /115Browser\\/([\\d.]+)/ },\n { name: 'TheWorld', priority: 400, detect: /TheWorld/, versionPattern: /TheWorld ([\\d.]+)/ },\n { name: 'XiaoMi', priority: 410, detect: /MiuiBrowser/, versionPattern: /MiuiBrowser\\/([\\d.]+)/ },\n { name: 'Vivo', priority: 420, detect: /VivoBrowser/, versionPattern: /VivoBrowser\\/([\\d.]+)/ },\n { name: 'Huawei', priority: 430, detect: /HuaweiBrowser/, versionPattern: [/HuaweiBrowser\\/([\\d.]+)/, /Version\\/([\\d.]+)/] },\n { name: 'OPPO', priority: 440, detect: /HeyTapBrowser/, versionPattern: /HeyTapBrowser\\/([\\d.]+)/ },\n { name: 'Quark', priority: 450, detect: /Quark/, versionPattern: /Quark\\/([\\d.]+)/ },\n { name: 'Qiyu', priority: 460, detect: /Qiyu/, versionPattern: /Qiyu\\/([\\d.]+)/ },\n\n // ── App webviews — highest priority ───────────────────────────────────────\n { name: 'WechatWork', priority: 500, detect: /wxwork\\//, versionPattern: /wxwork\\/([\\d.]+)/ },\n { name: 'Wechat', priority: 510, detect: /MicroMessenger/, versionPattern: /MicroMessenger\\/([\\d.]+)/ },\n { name: 'Taobao', priority: 520, detect: /AliApp\\(TB/, versionPattern: /AliApp\\(TB\\/([\\d.]+)/ },\n { name: 'Alipay', priority: 530, detect: /AliApp\\(AP/, versionPattern: /AliApp\\(AP\\/([\\d.]+)/ },\n { name: 'Weibo', priority: 540, detect: /Weibo/, versionPattern: /weibo__([\\d.]+)/ },\n { name: 'Douban', priority: 550, detect: /com\\.douban\\.frodo/, versionPattern: /com\\.douban\\.frodo\\/([\\d.]+)/ },\n { name: 'Suning', priority: 560, detect: /SNEBUY-APP/, versionPattern: /SNEBUY-APP([\\d.]+)/ },\n { name: 'iQiYi', priority: 570, detect: /IqiyiApp/, versionPattern: /IqiyiVersion\\/([\\d.]+)/ },\n { name: 'DingTalk', priority: 580, detect: /DingTalk/, versionPattern: /DingTalk\\/([\\d.]+)/ },\n { name: 'Douyin', priority: 590, detect: /aweme/, versionPattern: /app_version\\/([\\d.]+)/ }\n] as const\n","/**\n * Extract the first capture group from `ua` using `pattern`.\n * Returns the matched string, or null if the pattern does not match.\n * Unlike String.replace(), this never returns the original input on no-match.\n */\nexport function extractVersion(ua: string, pattern: RegExp): string | null {\n const m = pattern.exec(ua)\n if (!m) return null\n const v = m[1]\n return v != null && v !== '' ? v : null\n}\n\n/**\n * Try each pattern in order; return the first non-null match, or null.\n */\nexport function extractVersionFromPatterns(ua: string, patterns: RegExp[]): string | null {\n for (const p of patterns) {\n const v = extractVersion(ua, p)\n if (v !== null) return v\n }\n return null\n}\n\n/**\n * Extract the Chrome major version from `ua` and look it up in a table.\n * Returns the mapped string on hit, or null on miss / no Chrome token.\n */\nexport function lookupFromChromeVersion(ua: string, table: Record<string, string>): string | null {\n const m = /Chrome\\/([\\d]+)/.exec(ua)\n if (!m) return null\n const major = m[1]\n return Object.prototype.hasOwnProperty.call(table, major) ? table[major] : null\n}\n","import type { BrowserName } from '../types.js'\nimport { BROWSER_DEFS } from '../constants/browsers.js'\nimport { extractVersionFromPatterns, lookupFromChromeVersion } from '../utils/extract.js'\n\nexport interface BrowserResult {\n browser: BrowserName\n version: string\n}\n\n/**\n * Detect the browser name and version from a user agent string.\n *\n * When multiple BROWSER_DEFS entries match the same UA, the one with\n * the highest `priority` value wins (ties go to the later definition).\n */\nexport function detectBrowser(ua: string): BrowserResult {\n let best: (typeof BROWSER_DEFS)[number] | null = null\n\n for (const def of BROWSER_DEFS) {\n if (def.detect.test(ua)) {\n if (best === null || def.priority >= best.priority) {\n best = def\n }\n }\n }\n\n if (!best) return { browser: 'unknown', version: 'unknown' }\n\n let version: string | null = null\n\n // 1. Try Chrome-version lookup table (for browsers like 360SE/EE that version by Chrome major)\n if (best.chromeLookup) {\n version = lookupFromChromeVersion(ua, best.chromeLookup)\n }\n\n // 2. Fall back to direct regex extraction\n if (version === null && best.versionPattern !== null) {\n const patterns = Array.isArray(best.versionPattern)\n ? best.versionPattern\n : [best.versionPattern]\n version = extractVersionFromPatterns(ua, patterns)\n }\n\n return { browser: best.name, version: version ?? 'unknown' }\n}\n","export interface EngineDef {\n name: string\n detect: RegExp\n}\n\nexport const ENGINE_DEFS: readonly EngineDef[] = [\n { name: 'KHTML', detect: /KHTML\\// },\n { name: 'Trident', detect: /(Trident|NET CLR)/ },\n { name: 'Presto', detect: /Presto/ },\n { name: 'Gecko', detect: /Gecko\\// },\n { name: 'WebKit', detect: /AppleWebKit/ }\n] as const\n","import type { EngineName } from '../types.js'\nimport { ENGINE_DEFS } from '../constants/engines.js'\n\n/**\n * Detect the rendering engine, with post-detection upgrades for Blink and EdgeHTML.\n *\n * @param ua - Raw user agent string\n * @param browser - Already-detected browser name (for Blink/EdgeHTML disambiguation)\n * @param version - Already-detected browser version string\n */\nexport function detectEngine(ua: string, browser: string, version: string): EngineName {\n let engine: EngineName = 'unknown'\n\n for (const def of ENGINE_DEFS) {\n if (def.detect.test(ua)) {\n engine = def.name as EngineName\n }\n }\n\n // Upgrade WebKit to Blink for Chrome 28+, Opera 15+, Yandex\n if (\n engine === 'WebKit' &&\n /(Chrome|CriOS)/.test(ua) &&\n parseInt((/Chrome\\/([\\d]+)/.exec(ua) ?? [])[1] ?? '0', 10) > 27\n ) {\n engine = 'Blink'\n } else if (browser === 'Opera' && parseInt(version, 10) > 12) {\n engine = 'Blink'\n } else if (browser === 'Yandex') {\n engine = 'Blink'\n }\n\n // Edge: Chromium-based Edge uses Blink (version > 75), legacy EdgeHTML below that\n if (browser === 'Edge') {\n engine = parseInt(version, 10) > 75 ? 'Blink' : 'EdgeHTML'\n }\n\n return engine\n}\n","import type { OsName } from '../types.js'\n\nexport interface OsDef {\n name: OsName\n detect: RegExp\n /** Capture-group regex for OS version extraction. null = no version. */\n versionPattern: RegExp | null\n /** Lookup table: raw version token → display version. */\n versionLookup?: Record<string, string>\n}\n\nexport const OS_DEFS: readonly OsDef[] = [\n { name: 'WebOS', detect: /hpwOS/, versionPattern: /hpwOS\\/([\\d.]+)/ },\n { name: 'Symbian', detect: /Symbian/, versionPattern: null },\n { name: 'MeeGo', detect: /MeeGo/, versionPattern: null },\n { name: 'BlackBerry', detect: /(BlackBerry|RIM)/, versionPattern: null },\n { name: 'Windows Phone', detect: /(IEMobile|Windows Phone)/, versionPattern: /Windows Phone(?: OS)? ([\\d.]+)/ },\n { name: 'FreeBSD', detect: /FreeBSD/, versionPattern: null },\n { name: 'Debian', detect: /Debian/, versionPattern: /Debian\\/([\\d.]+)/ },\n { name: 'Ubuntu', detect: /Ubuntu/, versionPattern: null },\n { name: 'Chrome OS', detect: /CrOS/, versionPattern: null },\n { name: 'Linux', detect: /(Linux|X11)/, versionPattern: null },\n { name: 'iOS', detect: /like Mac OS X/, versionPattern: /OS ([\\d_]+) like/ },\n { name: 'MacOS', detect: /Macintosh/, versionPattern: /Mac OS X -?([\\d_.]+)/ },\n { name: 'HarmonyOS', detect: /HarmonyOS/, versionPattern: /Android ([\\d.]+)[;)]/,\n versionLookup: { '10': '2' } },\n { name: 'Android', detect: /(Android|Adr)/, versionPattern: /(?:Android|Adr) ([\\d.]+)/ },\n { name: 'Windows', detect: /Windows/, versionPattern: /Windows NT ([\\d.]+)/,\n versionLookup: {\n '10': '10', '6.4': '10', '6.3': '8.1', '6.2': '8',\n '6.1': '7', '6.0': 'Vista', '5.2': 'XP', '5.1': 'XP', '5.0': '2000'\n } }\n] as const\n","import type { OsName } from '../types.js'\nimport { OS_DEFS } from '../constants/os.js'\nimport { extractVersion } from '../utils/extract.js'\n\nexport interface OsResult {\n os: OsName\n osVersion: string\n}\n\n/**\n * Detect the operating system and its version from a user agent string.\n *\n * @param ua - Raw user agent string\n * @param windowsVersion - Pre-resolved Windows 11/10 string from getWindowsVersion()\n * (avoids the async race condition of the old implementation)\n */\nexport function detectOs(ua: string, windowsVersion?: string | null): OsResult {\n let matchedDef: (typeof OS_DEFS)[number] | null = null\n\n // Iterate in array order; later entries have higher priority (same as BROWSER_DEFS)\n for (const def of OS_DEFS) {\n if (def.detect.test(ua)) {\n matchedDef = def\n }\n }\n\n if (!matchedDef) return { os: 'unknown', osVersion: 'unknown' }\n\n let osVersion = 'unknown'\n\n if (matchedDef.versionPattern) {\n const raw = extractVersion(ua, matchedDef.versionPattern)\n\n if (raw !== null) {\n // Normalise iOS underscore-separated version: \"17_4_1\" → \"17.4.1\"\n const normalised = raw.replace(/_/g, '.')\n\n if (matchedDef.versionLookup) {\n // Use lookup table if available (Windows NT, HarmonyOS)\n const mapped = Object.prototype.hasOwnProperty.call(matchedDef.versionLookup, normalised)\n ? matchedDef.versionLookup[normalised]\n : null\n\n if (mapped !== null) {\n osVersion = mapped\n } else if (matchedDef.name === 'Windows') {\n // For unknown Windows NT versions, fall back to the integer part\n osVersion = parseInt(normalised, 10).toString()\n }\n } else {\n osVersion = normalised\n }\n }\n }\n\n // Windows 11 override — provided externally to avoid async race\n if (matchedDef.name === 'Windows' && windowsVersion) {\n osVersion = windowsVersion\n }\n\n return { os: matchedDef.name, osVersion }\n}\n","export interface DeviceDef {\n name: string\n detect: RegExp\n}\n\nexport const DEVICE_DEFS: readonly DeviceDef[] = [\n { name: 'Mobile', detect: /(Mobi|iPh|480)/ },\n { name: 'Tablet', detect: /(Tablet|Pad|Nexus 7)/ }\n] as const\n","import type { DeviceName } from '../types.js'\nimport { DEVICE_DEFS } from '../constants/devices.js'\nimport type { NavContext } from '../utils/navigator.js'\n\n/**\n * Detect the device type from a user agent string.\n *\n * @param ua - Raw user agent string\n * @param nav - Optional nav context; used to detect iPad on modern macOS\n * (where the UA reports \"Macintosh\" but maxTouchPoints > 1)\n */\nexport function detectDevice(ua: string, nav?: Pick<NavContext, 'platform' | 'maxTouchPoints'>): DeviceName {\n // Modern iPad reports platform='MacIntel' and UA contains 'Macintosh'\n if (nav?.platform === 'MacIntel' && nav.maxTouchPoints > 1) {\n return 'Tablet'\n }\n\n // iPad in UA string while device would otherwise be Mobile (older iPads)\n if (/iPad/.test(ua)) {\n return 'Tablet'\n }\n\n for (const def of DEVICE_DEFS) {\n if (def.detect.test(ua)) {\n return def.name as DeviceName\n }\n }\n\n return 'PC'\n}\n","export type BotName =\n | 'Googlebot'\n | 'Bingbot'\n | 'Baiduspider'\n | 'Bytespider'\n | 'YandexBot'\n | 'DuckDuckBot'\n | 'Slurp'\n | 'Sogou'\n | '360Spider'\n | 'Applebot'\n | 'Facebookbot'\n | 'Twitterbot'\n | 'LinkedInBot'\n | 'SemrushBot'\n | 'AhrefsBot'\n | 'MJ12bot'\n | 'PetalBot'\n | 'GenericBot'\n | 'unknown'\n\nexport interface BotDef {\n name: BotName\n detect: RegExp\n}\n\nexport const BOT_DEFS: readonly BotDef[] = [\n // Search engines\n { name: 'Googlebot', detect: /Googlebot/ },\n { name: 'Bingbot', detect: /(bingbot|BingPreview)/ },\n { name: 'Baiduspider', detect: /(Baiduspider|BaiduMobaider)/ },\n { name: 'Bytespider', detect: /Bytespider/ },\n { name: 'YandexBot', detect: /YandexBot/ },\n { name: 'DuckDuckBot', detect: /DuckDuckBot/ },\n { name: 'Slurp', detect: /Slurp/ },\n { name: 'Sogou', detect: /(Sogou|sogou).*[Ss]pider/ },\n { name: '360Spider', detect: /360Spider/ },\n { name: 'PetalBot', detect: /PetalBot/ },\n { name: 'Applebot', detect: /Applebot/ },\n // Social\n { name: 'Facebookbot', detect: /(facebookexternalhit|FacebookBot)/ },\n { name: 'Twitterbot', detect: /Twitterbot/ },\n { name: 'LinkedInBot', detect: /LinkedInBot/ },\n // SEO tools\n { name: 'SemrushBot', detect: /SemrushBot/ },\n { name: 'AhrefsBot', detect: /AhrefsBot/ },\n { name: 'MJ12bot', detect: /MJ12bot/ },\n // Generic catch-all (must be last)\n { name: 'GenericBot', detect: /(bot|crawler|spider|crawling|scraper)/i }\n] as const\n","import { BOT_DEFS, type BotName } from '../constants/bots.js'\n\nexport interface BotResult {\n isBot: boolean\n botName: BotName\n}\n\n/**\n * Detect whether the UA belongs to a bot, crawler, or spider.\n * Returns the specific bot name when recognised, 'GenericBot' for generic patterns,\n * or 'unknown' for regular user agents.\n */\nexport function detectBot(ua: string): BotResult {\n for (const def of BOT_DEFS) {\n if (def.detect.test(ua)) {\n return { isBot: true, botName: def.name }\n }\n }\n return { isBot: false, botName: 'unknown' }\n}\n","export type ArchName = 'x86' | 'x86_64' | 'arm' | 'arm64' | 'unknown'\n\nexport interface ArchDef {\n name: ArchName\n detect: RegExp\n}\n\n/**\n * Ordered from most specific to least specific.\n * First match wins (unlike browser/OS detection which keeps highest priority).\n */\nexport const ARCH_DEFS: readonly ArchDef[] = [\n { name: 'arm64', detect: /(aarch64|arm64|ARM64)/ },\n { name: 'arm', detect: /\\bARM\\b/ },\n { name: 'x86_64', detect: /(x86_64|Win64|WOW64|x64;|amd64)/i },\n { name: 'x86', detect: /(i[36]86|i686|x86;)/ }\n] as const\n","import { ARCH_DEFS, type ArchName } from '../constants/arch.js'\n\n/**\n * Detect the CPU architecture from a user agent string.\n * Returns 'unknown' when the UA provides no architecture hints.\n */\nexport function detectArch(ua: string): ArchName {\n for (const def of ARCH_DEFS) {\n if (def.detect.test(ua)) {\n return def.name\n }\n }\n return 'unknown'\n}\n","/**\n * Patterns that indicate a headless, automated, or embedded browser environment.\n *\n * | Pattern | Source |\n * |------------------|-----------------------------------------------------|\n * | HeadlessChrome | Chrome launched with --headless flag |\n * | Headless | Generic headless marker in some frameworks |\n * | PhantomJS | PhantomJS (deprecated but still used) |\n * | Electron | Electron apps (not strictly headless, but automated)|\n * | Playwright | Playwright may inject its own token |\n */\nconst HEADLESS_PATTERN = /(HeadlessChrome|Headless|PhantomJS|Electron\\/|Playwright)/\n\n/**\n * Detect whether the UA belongs to a headless or automation-driven browser.\n *\n * Note: modern Puppeteer/Playwright using stealth mode can hide these markers.\n * This catches the common/unmodified cases only.\n */\nexport function detectHeadless(ua: string): boolean {\n return HEADLESS_PATTERN.test(ua)\n}\n","/**\n * A subset of the Navigator interface that our detectors need.\n * Accepting NavContext as a parameter makes every detector pure and testable.\n */\nexport interface NavContext {\n userAgent: string\n platform: string\n language: string\n browserLanguage?: string\n maxTouchPoints: number\n mimeTypes?: MimeTypeArray\n connection?: { saveData?: boolean }\n userAgentData?: {\n platform: string\n getHighEntropyValues(hints: string[]): Promise<Record<string, string>>\n }\n}\n\n/** Build a NavContext from the real browser `navigator`, or return a safe default for Node.js. */\nexport function getNavContext(): NavContext {\n if (typeof navigator === 'undefined') {\n return { userAgent: '', platform: '', language: '', maxTouchPoints: 0 }\n }\n return navigator as unknown as NavContext\n}\n\n/** Safely query a MIME type from the nav context. Returns false in non-browser envs. */\nexport function getMimeType(nav: NavContext, type: string): boolean {\n try {\n return !!nav.mimeTypes?.namedItem(type)\n } catch {\n return false\n }\n}\n\n/** Returns the normalised browser language (e.g. \"zh-CN\" → \"zh-CN\", \"en-us\" → \"en-US\"). */\nexport function getLanguage(nav: NavContext): string {\n const raw = nav.browserLanguage ?? nav.language ?? ''\n const normalised = raw.replace(/-\\w+/g, (w) => w.toUpperCase())\n return normalised || 'unknown'\n}\n","import type { EnvOption, BrowserName } from './types.js'\nimport { detectBrowser } from './detectors/browser.js'\nimport { detectEngine } from './detectors/engine.js'\nimport { detectOs } from './detectors/os.js'\nimport { detectDevice } from './detectors/device.js'\nimport { detectBot } from './detectors/bot.js'\nimport { detectArch } from './detectors/arch.js'\nimport { detectHeadless } from './detectors/headless.js'\nimport { getMimeType, getLanguage, type NavContext } from './utils/navigator.js'\n\nexport interface ParseOptions {\n /** Nav context to use for language, platform, MIME-type checks, and device detection. */\n nav?: NavContext\n /** Pre-resolved Windows version string (from getWindowsVersion()). Pass to avoid async races. */\n windowsVersion?: string | null\n}\n\n/**\n * Parse a user agent string into a full browser/OS/engine/device description.\n *\n * Pure function — no global state, no singletons. All environment access is\n * supplied through `options.nav`; omit it for Node.js / testing contexts.\n */\nexport function parseUA(ua: string, options: ParseOptions = {}): EnvOption {\n const { nav, windowsVersion } = options\n\n const { browser: rawBrowser, version: rawVersion } = detectBrowser(ua)\n const { os, osVersion } = detectOs(ua, windowsVersion)\n const device = detectDevice(ua, nav)\n const arch = detectArch(ua)\n const { isBot, botName } = detectBot(ua)\n const isHeadless = detectHeadless(ua)\n const language = nav ? getLanguage(nav) : 'unknown'\n const platform = nav?.platform ?? 'unknown'\n\n let browser: BrowserName = rawBrowser\n let version = rawVersion\n\n // ── Post-detection overrides ────────────────────────────────────────────────\n\n // 360 browser disambiguation via Chrome global APIs and MIME types.\n // Only runs when a nav context is provided (browser environment).\n if (nav) {\n const chromeGlobal = typeof chrome !== 'undefined' ? chrome : undefined\n const chromeMajor = parseInt((/Chrome\\/([\\d]+)/.exec(ua) ?? [])[1] ?? '0', 10)\n\n if (chromeGlobal) {\n if (chromeGlobal.adblock2345 || chromeGlobal.common2345) {\n browser = '2345Explorer'\n version = 'unknown'\n } else {\n let is360 = false\n\n if (\n getMimeType(nav, 'application/360softmgrplugin') ||\n getMimeType(nav, 'application/mozilla-npqihooquicklogin') ||\n (chromeMajor > 36 && typeof showModalDialog !== 'undefined')\n ) {\n is360 = true\n } else if (chromeMajor > 45) {\n is360 = getMimeType(nav, 'application/vnd.chromium.remoting-viewer')\n if (!is360 && chromeMajor >= 69) {\n is360 =\n getMimeType(nav, 'application/hwepass2001.installepass2001') ||\n getMimeType(nav, 'application/asx')\n }\n }\n\n if (is360) {\n if (getMimeType(nav, 'application/gameplugin') || !nav.connection?.saveData) {\n browser = '360SE'\n } else {\n browser = '360EE'\n }\n version = 'unknown' // re-derived below via browser lookup\n }\n }\n }\n }\n\n // Baidu UA can include Opera token — Opera takes priority\n if (browser === 'Baidu' && /(Opera|OPR|OPT)/.test(ua)) {\n browser = 'Opera'\n version = ((/OPR\\/([\\d.]+)/.exec(ua) ?? [])[1]) ??\n ((/OPT\\/([\\d.]+)/.exec(ua) ?? [])[1]) ??\n ((/Opera\\/([\\d.]+)/.exec(ua) ?? [])[1]) ?? 'unknown'\n }\n\n // Generic \"SomethingBrowser/x.y\" catch-all: Chrome-based third-party browsers\n // that embed their own token alongside Chrome\n if (browser === 'Chrome' && /\\S+Browser\\//.test(ua)) {\n const m = /(\\S+Browser)\\/([\\d.]+)/.exec(ua)\n if (m) {\n browser = m[1] as BrowserName\n version = m[2]\n }\n }\n\n // Firefox Nightly detection — only meaningful in a real browser environment.\n // The heuristic checks for globals that exist in Chrome (clientInformation) but\n // not in standard Firefox, or where u2f was removed in Nightly builds.\n // Skip entirely in Node.js (no nav = not a browser).\n if (browser === 'Firefox' && nav) {\n try {\n if (typeof clientInformation !== 'undefined' || typeof u2f === 'undefined') {\n browser = 'Firefox Nightly'\n }\n } catch {\n // globals not accessible — leave as Firefox\n }\n }\n\n // WeChat Miniapp detection\n if (browser === 'Wechat') {\n try {\n if (typeof __wxjs_environment !== 'undefined' && __wxjs_environment === 'miniprogram') {\n browser = 'Wechat Miniapp'\n }\n } catch {\n // not in WeChat miniapp context\n }\n }\n\n const engine = detectEngine(ua, browser, version)\n\n return {\n browser,\n version,\n engine,\n os,\n osVersion,\n device,\n arch,\n isWebview: /; wv/.test(ua),\n isHeadless,\n isBot,\n botName,\n language,\n platform\n }\n}\n","import type { NavContext } from './navigator.js'\n\n/**\n * Asynchronously detect whether the Windows version is 10 or 11 using the\n * User-Agent Client Hints API (navigator.userAgentData).\n *\n * Returns '11', '10', or null (non-Windows / API unavailable / error).\n *\n * Because this is async, callers that need accurate Windows 11 detection\n * should await this result and pass it to parseUA() as `options.windowsVersion`.\n */\nexport async function getWindowsVersion(nav: NavContext): Promise<string | null> {\n if (!nav.userAgentData || nav.userAgentData.platform !== 'Windows') {\n return null\n }\n try {\n const data = await nav.userAgentData.getHighEntropyValues(['platformVersion'])\n const major = parseInt(data['platformVersion']?.split('.')[0] ?? '0', 10)\n return major >= 13 ? '11' : '10'\n } catch {\n return null\n }\n}\n","import pkg from '../package.json' with { type: 'json' }\nconst { version: VERSION } = pkg\nimport { parseUA } from './parse.js'\nimport { getNavContext, getLanguage } from './utils/navigator.js'\nimport type { EnvOption } from './types.js'\n\n// ── Named exports (tree-shakeable) ──────────────────────────────────────────\nexport type { EnvOption, BrowserName, OsName, EngineName, DeviceName, ArchName, BotName } from './types.js'\nexport { parseUA } from './parse.js'\nexport { getLanguage, getNavContext } from './utils/navigator.js'\nexport { getWindowsVersion } from './utils/windows-version.js'\nexport { detectBot } from './detectors/bot.js'\nexport { detectArch } from './detectors/arch.js'\nexport { detectHeadless } from './detectors/headless.js'\nexport { VERSION }\n\n/** Check whether a UA string indicates an Android webview environment. */\nexport const isWebview = (ua: string): boolean => /; wv/.test(ua)\n\n/** Check whether the current context is a WeChat mini-program. */\nexport const isWechatMiniapp = (): boolean => {\n try {\n return typeof __wxjs_environment !== 'undefined' && __wxjs_environment === 'miniprogram'\n } catch {\n return false\n }\n}\n\n// ── Default export — maintains v0.x call signature ──────────────────────────\n\n/**\n * Detect browser, OS, engine and device information.\n *\n * @param ua - Optional UA string override. Defaults to `navigator.userAgent`.\n */\nfunction uaBrowser(ua?: string): EnvOption {\n const nav = getNavContext()\n return parseUA(ua ?? nav.userAgent, { nav })\n}\n\nuaBrowser.isWebview = isWebview\nuaBrowser.isWechatMiniapp = isWechatMiniapp\nuaBrowser.getLanguage = (): string => getLanguage(getNavContext())\nuaBrowser.VERSION = VERSION\n\nexport default uaBrowser\n"]}