@whitesev/utils 2.6.8 → 2.7.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.umd.js CHANGED
@@ -230,6 +230,273 @@
230
230
  }
231
231
  }
232
232
 
233
+ const TryCatch = function (...args) {
234
+ /* 定义变量和函数 */
235
+ let callbackFunction = null;
236
+ let context = null;
237
+ let handleError = (error) => { };
238
+ let defaultDetails = {
239
+ log: true,
240
+ };
241
+ const TryCatchCore = {
242
+ /**
243
+ *
244
+ * @param paramDetails 配置
245
+ * @returns
246
+ */
247
+ config(paramDetails) {
248
+ defaultDetails = Object.assign(defaultDetails, paramDetails);
249
+ return TryCatchCore;
250
+ },
251
+ /**
252
+ * 处理错误
253
+ * @param handler
254
+ */
255
+ error(handler) {
256
+ // @ts-ignore
257
+ handleError = handler;
258
+ return TryCatchCore;
259
+ },
260
+ /**
261
+ * 执行传入的函数并捕获其可能抛出的错误,并通过传入的错误处理函数进行处理。
262
+ * @param callback 待执行函数,可以是 function 或者 string 类型。如果是 string 类型,则会被当做代码进行执行。
263
+ * @param __context__ 待执行函数的作用域,用于apply指定
264
+ * @returns 如果函数有返回值,则返回该返回值;否则返回 tryCatchObj 函数以支持链式调用。
265
+ * @throws {Error} 如果传入参数不符合要求,则会抛出相应类型的错误。
266
+ */
267
+ run(callback, __context__) {
268
+ callbackFunction = callback;
269
+ context = __context__ || this;
270
+ let result = executeTryCatch(callbackFunction, handleError, context);
271
+ // @ts-ignore
272
+ return result !== void 0 ? result : TryCatchCore;
273
+ },
274
+ };
275
+ /**
276
+ * 执行传入的函数并捕获其可能抛出的错误,并通过传入的错误处理函数进行处理。
277
+ * @param callback - 待执行函数,可以是 function 或者 string 类型。如果是 string 类型,则会被当做代码进行执行。
278
+ * @param handleErrorFunc - 错误处理函数,可以是 function 或者 string 类型。如果是 string 类型,则会被当做代码进行执行。
279
+ * @param funcThis - 待执行函数的作用域,用于apply指定
280
+ * @returns 如果函数有返回值,则返回该返回值;否则返回 undefined。
281
+ */
282
+ function executeTryCatch(callback, handleErrorFunc, funcThis) {
283
+ let result = void 0;
284
+ try {
285
+ if (typeof callback === "string") {
286
+ result = new Function(callback).apply(funcThis, args);
287
+ }
288
+ else {
289
+ result = callback.apply(funcThis, args);
290
+ }
291
+ }
292
+ catch (error) {
293
+ if (defaultDetails.log) {
294
+ callback = callback;
295
+ console.log(`%c ${callback?.name ? callback?.name : callback + "出现错误"} `, "color: #f20000");
296
+ console.log(`%c 错误原因:${error}`, "color: #f20000");
297
+ console.trace(callback);
298
+ }
299
+ if (handleErrorFunc) {
300
+ if (typeof handleErrorFunc === "string") {
301
+ result = new Function(handleErrorFunc).apply(funcThis, [
302
+ ...args,
303
+ error,
304
+ ]);
305
+ }
306
+ else {
307
+ result = handleErrorFunc.apply(funcThis, [...args, error]);
308
+ }
309
+ }
310
+ }
311
+ return result;
312
+ }
313
+ return TryCatchCore;
314
+ };
315
+
316
+ class CommonUtil {
317
+ assign(target = {}, source = {}, isAdd = false) {
318
+ let UtilsContext = this;
319
+ if (Array.isArray(source)) {
320
+ let canTraverse = source.filter((item) => {
321
+ return typeof item === "object";
322
+ });
323
+ if (!canTraverse.length) {
324
+ return source;
325
+ }
326
+ }
327
+ if (source == null) {
328
+ return target;
329
+ }
330
+ if (target == null) {
331
+ target = {};
332
+ }
333
+ if (isAdd) {
334
+ for (const sourceKeyName in source) {
335
+ const targetKeyName = sourceKeyName;
336
+ let targetValue = target[targetKeyName];
337
+ let sourceValue = source[sourceKeyName];
338
+ if (typeof sourceValue === "object" &&
339
+ sourceValue != null &&
340
+ sourceKeyName in target &&
341
+ !UtilsContext.isDOM(sourceValue)) {
342
+ /* 源端的值是object类型,且不是元素节点 */
343
+ target[sourceKeyName] = UtilsContext.assign(targetValue, sourceValue, isAdd);
344
+ continue;
345
+ }
346
+ target[sourceKeyName] = sourceValue;
347
+ }
348
+ }
349
+ else {
350
+ for (const targetKeyName in target) {
351
+ if (targetKeyName in source) {
352
+ let targetValue = target[targetKeyName];
353
+ let sourceValue = source[targetKeyName];
354
+ if (typeof sourceValue === "object" &&
355
+ sourceValue != null &&
356
+ !UtilsContext.isDOM(sourceValue) &&
357
+ Object.keys(sourceValue).length) {
358
+ /* 源端的值是object类型,且不是元素节点 */
359
+ target[targetKeyName] = UtilsContext.assign(targetValue, sourceValue, isAdd);
360
+ continue;
361
+ }
362
+ /* 直接赋值 */
363
+ target[targetKeyName] = sourceValue;
364
+ }
365
+ }
366
+ }
367
+ return target;
368
+ }
369
+ isNull(...args) {
370
+ let result = true;
371
+ let checkList = [...args];
372
+ for (const objItem of checkList) {
373
+ let itemResult = false;
374
+ if (objItem === null || objItem === undefined) {
375
+ itemResult = true;
376
+ }
377
+ else {
378
+ switch (typeof objItem) {
379
+ case "object":
380
+ if (typeof objItem[Symbol.iterator] === "function") {
381
+ /* 可迭代 */
382
+ itemResult = objItem.length === 0;
383
+ }
384
+ else {
385
+ itemResult = Object.keys(objItem).length === 0;
386
+ }
387
+ break;
388
+ case "number":
389
+ itemResult = objItem === 0;
390
+ break;
391
+ case "string":
392
+ itemResult =
393
+ objItem.trim() === "" ||
394
+ objItem === "null" ||
395
+ objItem === "undefined";
396
+ break;
397
+ case "boolean":
398
+ itemResult = !objItem;
399
+ break;
400
+ case "function":
401
+ let funcStr = objItem.toString().replace(/\s/g, "");
402
+ /* 排除()=>{}、(xxx="")=>{}、function(){}、function(xxx=""){} */
403
+ itemResult = Boolean(funcStr.match(/^\(.*?\)=>\{\}$|^function.*?\(.*?\)\{\}$/));
404
+ break;
405
+ }
406
+ }
407
+ result = result && itemResult;
408
+ }
409
+ return result;
410
+ }
411
+ /**
412
+ * 判断对象是否是元素
413
+ * @param target
414
+ * @returns
415
+ * + true 是元素
416
+ * + false 不是元素
417
+ * @example
418
+ * Utils.isDOM(document.querySelector("a"))
419
+ * > true
420
+ */
421
+ isDOM(target) {
422
+ return target instanceof Node;
423
+ }
424
+ isNotNull(...args) {
425
+ let UtilsContext = this;
426
+ return !UtilsContext.isNull.apply(this, args);
427
+ }
428
+ deepClone(obj) {
429
+ let UtilsContext = this;
430
+ if (obj === void 0)
431
+ return void 0;
432
+ if (obj === null)
433
+ return null;
434
+ let clone = obj instanceof Array ? [] : {};
435
+ for (const [key, value] of Object.entries(obj)) {
436
+ clone[key] =
437
+ typeof value === "object" ? UtilsContext.deepClone(value) : value;
438
+ }
439
+ return clone;
440
+ }
441
+ /**
442
+ * 覆盖对象中的函数this指向
443
+ * @param target 需要覆盖的对象
444
+ * @param [objectThis] 覆盖的this指向,如果为传入,则默认为对象本身
445
+ */
446
+ coverObjectFunctionThis(target, objectThis) {
447
+ if (typeof target !== "object" || target === null) {
448
+ throw new Error("target must be object");
449
+ }
450
+ objectThis = objectThis || target;
451
+ Object.keys(target).forEach((key) => {
452
+ if (typeof target[key] === "function") {
453
+ target[key] = target[key].bind(objectThis);
454
+ }
455
+ });
456
+ }
457
+ toJSON(data, errorCallBack) {
458
+ let result = {};
459
+ if (typeof data === "object") {
460
+ return data;
461
+ }
462
+ TryCatch()
463
+ .config({ log: false })
464
+ .error((error) => {
465
+ TryCatch()
466
+ .error(() => {
467
+ try {
468
+ result = new Function("return " + data)();
469
+ }
470
+ catch (error2) {
471
+ if (typeof errorCallBack === "function") {
472
+ errorCallBack(error2);
473
+ }
474
+ }
475
+ })
476
+ .run(() => {
477
+ if (data &&
478
+ /^[\],:{}\s]*$/.test(data
479
+ .replace(/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g, "@")
480
+ .replace(/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, "]")
481
+ .replace(/(?:^|:|,)(?:\s*\[)+/g, ""))) {
482
+ result = new Function("return " + data)();
483
+ }
484
+ else {
485
+ if (typeof errorCallBack === "function") {
486
+ errorCallBack(new Error("target is not a JSON"));
487
+ }
488
+ }
489
+ });
490
+ })
491
+ .run(() => {
492
+ data = data.trim();
493
+ result = JSON.parse(data);
494
+ });
495
+ return result;
496
+ }
497
+ }
498
+ let commonUtil = new CommonUtil();
499
+
233
500
  class UtilsGMCookie {
234
501
  windowApi = {
235
502
  window: window,
@@ -258,7 +525,7 @@
258
525
  throw new TypeError("Utils.GMCookie.get 参数cookieName 必须为字符串");
259
526
  }
260
527
  let cookies = this.getCookiesList();
261
- let findValue = undefined;
528
+ let findValue = void 0;
262
529
  for (const cookieItem of cookies) {
263
530
  let item = cookieItem.trim();
264
531
  let itemSplit = item.split("=");
@@ -302,7 +569,7 @@
302
569
  name: "",
303
570
  path: "/",
304
571
  };
305
- defaultOption = utils.assign(defaultOption, option);
572
+ defaultOption = commonUtil.assign(defaultOption, option);
306
573
  let cookies = this.getCookiesList();
307
574
  cookies.forEach((item) => {
308
575
  item = item.trim();
@@ -353,7 +620,7 @@
353
620
  name: "",
354
621
  path: "/",
355
622
  };
356
- defaultOption = utils.assign(defaultOption, option);
623
+ defaultOption = commonUtil.assign(defaultOption, option);
357
624
  let cookies = this.getCookiesList();
358
625
  cookies.forEach((item) => {
359
626
  item = item.trim();
@@ -402,7 +669,7 @@
402
669
  */
403
670
  expirationDate: Math.floor(Date.now()) + 60 * 60 * 24 * 30,
404
671
  };
405
- defaultOption = utils.assign(defaultOption, option);
672
+ defaultOption = commonUtil.assign(defaultOption, option);
406
673
  let life = defaultOption.expirationDate
407
674
  ? defaultOption.expirationDate
408
675
  : Math.floor(Date.now()) + 60 * 60 * 24 * 30;
@@ -412,7 +679,7 @@
412
679
  ";expires=" +
413
680
  new Date(life).toGMTString() +
414
681
  "; path=/";
415
- if (utils.isNotNull(defaultOption.domain)) {
682
+ if (commonUtil.isNull(defaultOption.domain)) {
416
683
  cookieStr += "; domain=" + defaultOption.domain;
417
684
  }
418
685
  this.windowApi.document.cookie = cookieStr;
@@ -440,9 +707,9 @@
440
707
  path: "/",
441
708
  firstPartyDomain: "",
442
709
  };
443
- defaultOption = utils.assign(defaultOption, option);
710
+ defaultOption = commonUtil.assign(defaultOption, option);
444
711
  let cookieStr = `${defaultOption.name}=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=${defaultOption.path}`;
445
- if (utils.isNotNull(defaultOption.firstPartyDomain)) {
712
+ if (commonUtil.isNull(defaultOption.firstPartyDomain)) {
446
713
  cookieStr += `; domain=${defaultOption.firstPartyDomain};`;
447
714
  }
448
715
  this.windowApi.document.cookie = cookieStr;
@@ -482,189 +749,189 @@
482
749
  }
483
750
  }
484
751
 
752
+ // ==UserScript==
485
753
  // @name ajaxHooker
486
754
  // @author cxxjackie
487
- // @version 1.4.4
488
- // @updateLog 修复头条、抖音部分站点下this引用错误的问题。
755
+ // @version 1.4.6
489
756
  // @supportURL https://bbs.tampermonkey.net.cn/thread-3284-1-1.html
757
+ // @license GNU LGPL-3.0
758
+ // ==/UserScript==
490
759
 
491
- const AjaxHooker = function () {
492
- return (function () {
493
- const version = "1.4.4";
494
- const hookInst = {
495
- hookFns: [],
496
- filters: [],
497
- };
498
- const win = window.unsafeWindow || document.defaultView || window;
499
- let winAh = win.__ajaxHooker;
500
- const resProto = win.Response.prototype;
501
- const xhrResponses = ["response", "responseText", "responseXML"];
502
- const fetchResponses = ["arrayBuffer", "blob", "formData", "json", "text"];
503
- const fetchInitProps = [
504
- "method",
505
- "headers",
506
- "body",
507
- "mode",
508
- "credentials",
509
- "cache",
510
- "redirect",
511
- "referrer",
512
- "referrerPolicy",
513
- "integrity",
514
- "keepalive",
515
- "signal",
516
- "priority",
517
- ];
518
- const xhrAsyncEvents = ["readystatechange", "load", "loadend"];
519
- const getType = {}.toString.call.bind({}.toString);
520
- const getDescriptor = Object.getOwnPropertyDescriptor.bind(Object);
521
- const emptyFn = () => {};
522
- const errorFn = (e) => console.error(e);
523
- function isThenable(obj) {
524
- return (
525
- obj &&
526
- ["object", "function"].includes(typeof obj) &&
527
- typeof obj.then === "function"
528
- );
529
- }
530
- function catchError(fn, ...args) {
531
- try {
532
- const result = fn(...args);
533
- if (isThenable(result)) return result.then(null, errorFn);
534
- return result;
535
- } catch (err) {
536
- console.error(err);
537
- }
538
- }
539
- function defineProp(obj, prop, getter, setter) {
540
- Object.defineProperty(obj, prop, {
541
- configurable: true,
542
- enumerable: true,
543
- get: getter,
544
- set: setter,
545
- });
546
- }
547
- function readonly(obj, prop, value = obj[prop]) {
548
- defineProp(obj, prop, () => value, emptyFn);
549
- }
550
- function writable(obj, prop, value = obj[prop]) {
551
- Object.defineProperty(obj, prop, {
552
- configurable: true,
553
- enumerable: true,
554
- writable: true,
555
- value: value,
556
- });
760
+ const ajaxHooker = function () {
761
+ const version = "1.4.6";
762
+ const hookInst = {
763
+ hookFns: [],
764
+ filters: [],
765
+ };
766
+ const win = window.unsafeWindow || document.defaultView || window;
767
+ let winAh = win.__ajaxHooker;
768
+ const resProto = win.Response.prototype;
769
+ const xhrResponses = ["response", "responseText", "responseXML"];
770
+ const fetchResponses = ["arrayBuffer", "blob", "formData", "json", "text"];
771
+ const fetchInitProps = [
772
+ "method",
773
+ "headers",
774
+ "body",
775
+ "mode",
776
+ "credentials",
777
+ "cache",
778
+ "redirect",
779
+ "referrer",
780
+ "referrerPolicy",
781
+ "integrity",
782
+ "keepalive",
783
+ "signal",
784
+ "priority",
785
+ ];
786
+ const xhrAsyncEvents = ["readystatechange", "load", "loadend"];
787
+ const getType = {}.toString.call.bind({}.toString);
788
+ const getDescriptor = Object.getOwnPropertyDescriptor.bind(Object);
789
+ const emptyFn = () => {};
790
+ const errorFn = (e) => console.error(e);
791
+ function isThenable(obj) {
792
+ return (
793
+ obj &&
794
+ ["object", "function"].includes(typeof obj) &&
795
+ typeof obj.then === "function"
796
+ );
797
+ }
798
+ function catchError(fn, ...args) {
799
+ try {
800
+ const result = fn(...args);
801
+ if (isThenable(result)) return result.then(null, errorFn);
802
+ return result;
803
+ } catch (err) {
804
+ console.error(err);
557
805
  }
558
- function parseHeaders(obj) {
559
- const headers = {};
560
- switch (getType(obj)) {
561
- case "[object String]":
562
- for (const line of obj.trim().split(/[\r\n]+/)) {
563
- const [header, value] = line.split(/\s*:\s*/);
564
- if (!header) break;
565
- const lheader = header.toLowerCase();
566
- headers[lheader] =
567
- lheader in headers ? `${headers[lheader]}, ${value}` : value;
568
- }
569
- break;
570
- case "[object Headers]":
571
- for (const [key, val] of obj) {
572
- headers[key] = val;
573
- }
574
- break;
575
- case "[object Object]":
576
- return { ...obj };
577
- }
578
- return headers;
806
+ }
807
+ function defineProp(obj, prop, getter, setter) {
808
+ Object.defineProperty(obj, prop, {
809
+ configurable: true,
810
+ enumerable: true,
811
+ get: getter,
812
+ set: setter,
813
+ });
814
+ }
815
+ function readonly(obj, prop, value = obj[prop]) {
816
+ defineProp(obj, prop, () => value, emptyFn);
817
+ }
818
+ function writable(obj, prop, value = obj[prop]) {
819
+ Object.defineProperty(obj, prop, {
820
+ configurable: true,
821
+ enumerable: true,
822
+ writable: true,
823
+ value: value,
824
+ });
825
+ }
826
+ function parseHeaders(obj) {
827
+ const headers = {};
828
+ switch (getType(obj)) {
829
+ case "[object String]":
830
+ for (const line of obj.trim().split(/[\r\n]+/)) {
831
+ const [header, value] = line.split(/(?<=^[^:]+)\s*:\s*/);
832
+ if (!value) continue;
833
+ const lheader = header.toLowerCase();
834
+ headers[lheader] =
835
+ lheader in headers ? `${headers[lheader]}, ${value}` : value;
836
+ }
837
+ break;
838
+ case "[object Headers]":
839
+ for (const [key, val] of obj) {
840
+ headers[key] = val;
841
+ }
842
+ break;
843
+ case "[object Object]":
844
+ return { ...obj };
845
+ }
846
+ return headers;
847
+ }
848
+ function stopImmediatePropagation() {
849
+ this.ajaxHooker_isStopped = true;
850
+ }
851
+ class SyncThenable {
852
+ then(fn) {
853
+ fn && fn();
854
+ return new SyncThenable();
855
+ }
856
+ }
857
+ class AHRequest {
858
+ constructor(request) {
859
+ this.request = request;
860
+ this.requestClone = { ...this.request };
579
861
  }
580
- function stopImmediatePropagation() {
581
- this.ajaxHooker_isStopped = true;
862
+ shouldFilter(filters) {
863
+ const { type, url, method, async } = this.request;
864
+ return (
865
+ filters.length &&
866
+ !filters.find((obj) => {
867
+ switch (true) {
868
+ case obj.type && obj.type !== type:
869
+ case getType(obj.url) === "[object String]" &&
870
+ !url.includes(obj.url):
871
+ case getType(obj.url) === "[object RegExp]" && !obj.url.test(url):
872
+ case obj.method &&
873
+ obj.method.toUpperCase() !== method.toUpperCase():
874
+ case "async" in obj && obj.async !== async:
875
+ return false;
876
+ }
877
+ return true;
878
+ })
879
+ );
582
880
  }
583
- class SyncThenable {
584
- then(fn) {
585
- fn && fn();
881
+ waitForRequestKeys() {
882
+ const requestKeys = ["url", "method", "abort", "headers", "data"];
883
+ if (!this.request.async) {
884
+ win.__ajaxHooker.hookInsts.forEach(({ hookFns, filters }) => {
885
+ if (this.shouldFilter(filters)) return;
886
+ hookFns.forEach((fn) => {
887
+ if (getType(fn) === "[object Function]")
888
+ catchError(fn, this.request);
889
+ });
890
+ requestKeys.forEach((key) => {
891
+ if (isThenable(this.request[key]))
892
+ this.request[key] = this.requestClone[key];
893
+ });
894
+ });
586
895
  return new SyncThenable();
587
896
  }
897
+ const promises = [];
898
+ win.__ajaxHooker.hookInsts.forEach(({ hookFns, filters }) => {
899
+ if (this.shouldFilter(filters)) return;
900
+ promises.push(
901
+ Promise.all(hookFns.map((fn) => catchError(fn, this.request))).then(
902
+ () =>
903
+ Promise.all(
904
+ requestKeys.map((key) =>
905
+ Promise.resolve(this.request[key]).then(
906
+ (val) => (this.request[key] = val),
907
+ () => (this.request[key] = this.requestClone[key])
908
+ )
909
+ )
910
+ )
911
+ )
912
+ );
913
+ });
914
+ return Promise.all(promises);
588
915
  }
589
- class AHRequest {
590
- constructor(request) {
591
- this.request = request;
592
- this.requestClone = { ...this.request };
593
- }
594
- shouldFilter(filters) {
595
- const { type, url, method, async } = this.request;
596
- return (
597
- filters.length &&
598
- !filters.find((obj) => {
599
- switch (true) {
600
- case obj.type && obj.type !== type:
601
- case getType(obj.url) === "[object String]" &&
602
- !url.includes(obj.url):
603
- case getType(obj.url) === "[object RegExp]" && !obj.url.test(url):
604
- case obj.method &&
605
- obj.method.toUpperCase() !== method.toUpperCase():
606
- case "async" in obj && obj.async !== async:
607
- return false;
916
+ waitForResponseKeys(response) {
917
+ const responseKeys =
918
+ this.request.type === "xhr" ? xhrResponses : fetchResponses;
919
+ if (!this.request.async) {
920
+ if (getType(this.request.response) === "[object Function]") {
921
+ catchError(this.request.response, response);
922
+ responseKeys.forEach((key) => {
923
+ if (
924
+ "get" in getDescriptor(response, key) ||
925
+ isThenable(response[key])
926
+ ) {
927
+ delete response[key];
608
928
  }
609
- return true;
610
- })
611
- );
612
- }
613
- waitForRequestKeys() {
614
- const requestKeys = ["url", "method", "abort", "headers", "data"];
615
- if (!this.request.async) {
616
- win.__ajaxHooker.hookInsts.forEach(({ hookFns, filters }) => {
617
- if (this.shouldFilter(filters)) return;
618
- hookFns.forEach((fn) => {
619
- if (getType(fn) === "[object Function]")
620
- catchError(fn, this.request);
621
- });
622
- requestKeys.forEach((key) => {
623
- if (isThenable(this.request[key]))
624
- this.request[key] = this.requestClone[key];
625
- });
626
929
  });
627
- return new SyncThenable();
628
930
  }
629
- const promises = [];
630
- win.__ajaxHooker.hookInsts.forEach(({ hookFns, filters }) => {
631
- if (this.shouldFilter(filters)) return;
632
- promises.push(
633
- Promise.all(hookFns.map((fn) => catchError(fn, this.request))).then(
634
- () =>
635
- Promise.all(
636
- requestKeys.map((key) =>
637
- Promise.resolve(this.request[key]).then(
638
- (val) => (this.request[key] = val),
639
- () => (this.request[key] = this.requestClone[key])
640
- )
641
- )
642
- )
643
- )
644
- );
645
- });
646
- return Promise.all(promises);
931
+ return new SyncThenable();
647
932
  }
648
- waitForResponseKeys(response) {
649
- const responseKeys =
650
- this.request.type === "xhr" ? xhrResponses : fetchResponses;
651
- if (!this.request.async) {
652
- if (getType(this.request.response) === "[object Function]") {
653
- catchError(this.request.response, response);
654
- responseKeys.forEach((key) => {
655
- if (
656
- "get" in getDescriptor(response, key) ||
657
- isThenable(response[key])
658
- ) {
659
- delete response[key];
660
- }
661
- });
662
- }
663
- return new SyncThenable();
664
- }
665
- return Promise.resolve(
666
- catchError(this.request.response, response)
667
- ).then(() =>
933
+ return Promise.resolve(catchError(this.request.response, response)).then(
934
+ () =>
668
935
  Promise.all(
669
936
  responseKeys.map((key) => {
670
937
  const descriptor = getDescriptor(response, key);
@@ -678,424 +945,406 @@
678
945
  }
679
946
  })
680
947
  )
681
- );
682
- }
948
+ );
683
949
  }
684
- const proxyHandler = {
685
- get(target, prop) {
686
- const descriptor = getDescriptor(target, prop);
687
- if (
688
- descriptor &&
689
- !descriptor.configurable &&
690
- !descriptor.writable &&
691
- !descriptor.get
692
- )
693
- return target[prop];
694
- const ah = target.__ajaxHooker;
695
- if (ah && ah.proxyProps) {
696
- if (prop in ah.proxyProps) {
697
- const pDescriptor = ah.proxyProps[prop];
698
- if ("get" in pDescriptor) return pDescriptor.get();
699
- if (typeof pDescriptor.value === "function")
700
- return pDescriptor.value.bind(ah);
701
- return pDescriptor.value;
702
- }
703
- if (typeof target[prop] === "function")
704
- return target[prop].bind(target);
705
- }
950
+ }
951
+ const proxyHandler = {
952
+ get(target, prop) {
953
+ const descriptor = getDescriptor(target, prop);
954
+ if (
955
+ descriptor &&
956
+ !descriptor.configurable &&
957
+ !descriptor.writable &&
958
+ !descriptor.get
959
+ )
706
960
  return target[prop];
707
- },
708
- set(target, prop, value) {
709
- const descriptor = getDescriptor(target, prop);
710
- if (
711
- descriptor &&
712
- !descriptor.configurable &&
713
- !descriptor.writable &&
714
- !descriptor.set
715
- )
716
- return true;
717
- const ah = target.__ajaxHooker;
718
- if (ah && ah.proxyProps && prop in ah.proxyProps) {
961
+ const ah = target.__ajaxHooker;
962
+ if (ah && ah.proxyProps) {
963
+ if (prop in ah.proxyProps) {
719
964
  const pDescriptor = ah.proxyProps[prop];
720
- pDescriptor.set
721
- ? pDescriptor.set(value)
722
- : (pDescriptor.value = value);
723
- } else {
724
- target[prop] = value;
725
- }
726
- return true;
727
- },
728
- };
729
- class XhrHooker {
730
- constructor(xhr) {
731
- const ah = this;
732
- Object.assign(ah, {
733
- originalXhr: xhr,
734
- proxyXhr: new Proxy(xhr, proxyHandler),
735
- resThenable: new SyncThenable(),
736
- proxyProps: {},
737
- proxyEvents: {},
738
- });
739
- xhr.addEventListener("readystatechange", (e) => {
740
- if (
741
- ah.proxyXhr.readyState === 4 &&
742
- ah.request &&
743
- typeof ah.request.response === "function"
744
- ) {
745
- const response = {
746
- finalUrl: ah.proxyXhr.responseURL,
747
- status: ah.proxyXhr.status,
748
- responseHeaders: parseHeaders(
749
- ah.proxyXhr.getAllResponseHeaders()
750
- ),
751
- };
752
- const tempValues = {};
753
- for (const key of xhrResponses) {
754
- try {
755
- tempValues[key] = ah.originalXhr[key];
756
- } catch (err) {}
757
- defineProp(
758
- response,
759
- key,
760
- () => {
761
- return (response[key] = tempValues[key]);
762
- },
763
- (val) => {
764
- delete response[key];
765
- response[key] = val;
766
- }
767
- );
768
- }
769
- ah.resThenable = new AHRequest(ah.request)
770
- .waitForResponseKeys(response)
771
- .then(() => {
772
- for (const key of xhrResponses) {
773
- ah.proxyProps[key] = {
774
- get: () => {
775
- if (!(key in response)) response[key] = tempValues[key];
776
- return response[key];
777
- },
778
- };
779
- }
780
- });
781
- }
782
- ah.dispatchEvent(e);
783
- });
784
- xhr.addEventListener("load", (e) => ah.dispatchEvent(e));
785
- xhr.addEventListener("loadend", (e) => ah.dispatchEvent(e));
786
- for (const evt of xhrAsyncEvents) {
787
- const onEvt = "on" + evt;
788
- ah.proxyProps[onEvt] = {
789
- get: () => ah.proxyEvents[onEvt] || null,
790
- set: (val) => ah.addEvent(onEvt, val),
791
- };
792
- }
793
- for (const method of [
794
- "setRequestHeader",
795
- "addEventListener",
796
- "removeEventListener",
797
- "open",
798
- "send",
799
- ]) {
800
- ah.proxyProps[method] = { value: ah[method] };
801
- }
802
- }
803
- toJSON() {} // Converting circular structure to JSON
804
- addEvent(type, event) {
805
- if (type.startsWith("on")) {
806
- this.proxyEvents[type] = typeof event === "function" ? event : null;
807
- } else {
808
- if (typeof event === "object" && event !== null)
809
- event = event.handleEvent;
810
- if (typeof event !== "function") return;
811
- this.proxyEvents[type] = this.proxyEvents[type] || new Set();
812
- this.proxyEvents[type].add(event);
965
+ if ("get" in pDescriptor) return pDescriptor.get();
966
+ if (typeof pDescriptor.value === "function")
967
+ return pDescriptor.value.bind(ah);
968
+ return pDescriptor.value;
813
969
  }
970
+ if (typeof target[prop] === "function")
971
+ return target[prop].bind(target);
814
972
  }
815
- removeEvent(type, event) {
816
- if (type.startsWith("on")) {
817
- this.proxyEvents[type] = null;
818
- } else {
819
- if (typeof event === "object" && event !== null)
820
- event = event.handleEvent;
821
- this.proxyEvents[type] && this.proxyEvents[type].delete(event);
822
- }
973
+ return target[prop];
974
+ },
975
+ set(target, prop, value) {
976
+ const descriptor = getDescriptor(target, prop);
977
+ if (
978
+ descriptor &&
979
+ !descriptor.configurable &&
980
+ !descriptor.writable &&
981
+ !descriptor.set
982
+ )
983
+ return true;
984
+ const ah = target.__ajaxHooker;
985
+ if (ah && ah.proxyProps && prop in ah.proxyProps) {
986
+ const pDescriptor = ah.proxyProps[prop];
987
+ pDescriptor.set ? pDescriptor.set(value) : (pDescriptor.value = value);
988
+ } else {
989
+ target[prop] = value;
823
990
  }
824
- dispatchEvent(e) {
825
- e.stopImmediatePropagation = stopImmediatePropagation;
826
- defineProp(e, "target", () => this.proxyXhr);
827
- defineProp(e, "currentTarget", () => this.proxyXhr);
828
- this.proxyEvents[e.type] &&
829
- this.proxyEvents[e.type].forEach((fn) => {
830
- this.resThenable.then(
831
- () => !e.ajaxHooker_isStopped && fn.call(this.proxyXhr, e)
991
+ return true;
992
+ },
993
+ };
994
+ class XhrHooker {
995
+ constructor(xhr) {
996
+ const ah = this;
997
+ Object.assign(ah, {
998
+ originalXhr: xhr,
999
+ proxyXhr: new Proxy(xhr, proxyHandler),
1000
+ resThenable: new SyncThenable(),
1001
+ proxyProps: {},
1002
+ proxyEvents: {},
1003
+ });
1004
+ xhr.addEventListener("readystatechange", (e) => {
1005
+ if (
1006
+ ah.proxyXhr.readyState === 4 &&
1007
+ ah.request &&
1008
+ typeof ah.request.response === "function"
1009
+ ) {
1010
+ const response = {
1011
+ finalUrl: ah.proxyXhr.responseURL,
1012
+ status: ah.proxyXhr.status,
1013
+ responseHeaders: parseHeaders(ah.proxyXhr.getAllResponseHeaders()),
1014
+ };
1015
+ const tempValues = {};
1016
+ for (const key of xhrResponses) {
1017
+ try {
1018
+ tempValues[key] = ah.originalXhr[key];
1019
+ } catch (err) {}
1020
+ defineProp(
1021
+ response,
1022
+ key,
1023
+ () => {
1024
+ return (response[key] = tempValues[key]);
1025
+ },
1026
+ (val) => {
1027
+ delete response[key];
1028
+ response[key] = val;
1029
+ }
832
1030
  );
833
- });
834
- if (e.ajaxHooker_isStopped) return;
835
- const onEvent = this.proxyEvents["on" + e.type];
836
- onEvent && this.resThenable.then(onEvent.bind(this.proxyXhr, e));
1031
+ }
1032
+ ah.resThenable = new AHRequest(ah.request)
1033
+ .waitForResponseKeys(response)
1034
+ .then(() => {
1035
+ for (const key of xhrResponses) {
1036
+ ah.proxyProps[key] = {
1037
+ get: () => {
1038
+ if (!(key in response)) response[key] = tempValues[key];
1039
+ return response[key];
1040
+ },
1041
+ };
1042
+ }
1043
+ });
1044
+ }
1045
+ ah.dispatchEvent(e);
1046
+ });
1047
+ xhr.addEventListener("load", (e) => ah.dispatchEvent(e));
1048
+ xhr.addEventListener("loadend", (e) => ah.dispatchEvent(e));
1049
+ for (const evt of xhrAsyncEvents) {
1050
+ const onEvt = "on" + evt;
1051
+ ah.proxyProps[onEvt] = {
1052
+ get: () => ah.proxyEvents[onEvt] || null,
1053
+ set: (val) => ah.addEvent(onEvt, val),
1054
+ };
837
1055
  }
838
- setRequestHeader(header, value) {
839
- this.originalXhr.setRequestHeader(header, value);
840
- if (!this.request) return;
841
- const headers = this.request.headers;
842
- headers[header] =
843
- header in headers ? `${headers[header]}, ${value}` : value;
1056
+ for (const method of [
1057
+ "setRequestHeader",
1058
+ "addEventListener",
1059
+ "removeEventListener",
1060
+ "open",
1061
+ "send",
1062
+ ]) {
1063
+ ah.proxyProps[method] = { value: ah[method] };
844
1064
  }
845
- addEventListener(...args) {
846
- if (xhrAsyncEvents.includes(args[0])) {
847
- this.addEvent(args[0], args[1]);
848
- } else {
849
- this.originalXhr.addEventListener(...args);
850
- }
1065
+ }
1066
+ toJSON() {} // Converting circular structure to JSON
1067
+ addEvent(type, event) {
1068
+ if (type.startsWith("on")) {
1069
+ this.proxyEvents[type] = typeof event === "function" ? event : null;
1070
+ } else {
1071
+ if (typeof event === "object" && event !== null)
1072
+ event = event.handleEvent;
1073
+ if (typeof event !== "function") return;
1074
+ this.proxyEvents[type] = this.proxyEvents[type] || new Set();
1075
+ this.proxyEvents[type].add(event);
851
1076
  }
852
- removeEventListener(...args) {
853
- if (xhrAsyncEvents.includes(args[0])) {
854
- this.removeEvent(args[0], args[1]);
855
- } else {
856
- this.originalXhr.removeEventListener(...args);
857
- }
1077
+ }
1078
+ removeEvent(type, event) {
1079
+ if (type.startsWith("on")) {
1080
+ this.proxyEvents[type] = null;
1081
+ } else {
1082
+ if (typeof event === "object" && event !== null)
1083
+ event = event.handleEvent;
1084
+ this.proxyEvents[type] && this.proxyEvents[type].delete(event);
858
1085
  }
859
- open(method, url, async = true, ...args) {
860
- this.request = {
861
- type: "xhr",
862
- url: url.toString(),
863
- method: method.toUpperCase(),
864
- abort: false,
865
- headers: {},
866
- data: null,
867
- response: null,
868
- async: !!async,
869
- };
870
- this.openArgs = args;
871
- this.resThenable = new SyncThenable();
872
- [
873
- "responseURL",
874
- "readyState",
875
- "status",
876
- "statusText",
877
- ...xhrResponses,
878
- ].forEach((key) => {
879
- delete this.proxyProps[key];
1086
+ }
1087
+ dispatchEvent(e) {
1088
+ e.stopImmediatePropagation = stopImmediatePropagation;
1089
+ defineProp(e, "target", () => this.proxyXhr);
1090
+ defineProp(e, "currentTarget", () => this.proxyXhr);
1091
+ this.proxyEvents[e.type] &&
1092
+ this.proxyEvents[e.type].forEach((fn) => {
1093
+ this.resThenable.then(
1094
+ () => !e.ajaxHooker_isStopped && fn.call(this.proxyXhr, e)
1095
+ );
880
1096
  });
881
- return this.originalXhr.open(method, url, async, ...args);
1097
+ if (e.ajaxHooker_isStopped) return;
1098
+ const onEvent = this.proxyEvents["on" + e.type];
1099
+ onEvent && this.resThenable.then(onEvent.bind(this.proxyXhr, e));
1100
+ }
1101
+ setRequestHeader(header, value) {
1102
+ this.originalXhr.setRequestHeader(header, value);
1103
+ if (!this.request) return;
1104
+ const headers = this.request.headers;
1105
+ headers[header] =
1106
+ header in headers ? `${headers[header]}, ${value}` : value;
1107
+ }
1108
+ addEventListener(...args) {
1109
+ if (xhrAsyncEvents.includes(args[0])) {
1110
+ this.addEvent(args[0], args[1]);
1111
+ } else {
1112
+ this.originalXhr.addEventListener(...args);
882
1113
  }
883
- send(data) {
884
- const ah = this;
885
- const xhr = ah.originalXhr;
886
- const request = ah.request;
887
- if (!request) return xhr.send(data);
888
- request.data = data;
889
- new AHRequest(request).waitForRequestKeys().then(() => {
890
- if (request.abort) {
891
- if (typeof request.response === "function") {
892
- Object.assign(ah.proxyProps, {
893
- responseURL: { value: request.url },
894
- readyState: { value: 4 },
895
- status: { value: 200 },
896
- statusText: { value: "OK" },
897
- });
898
- xhrAsyncEvents.forEach((evt) =>
899
- xhr.dispatchEvent(new Event(evt))
900
- );
901
- }
902
- } else {
903
- xhr.open(
904
- request.method,
905
- request.url,
906
- request.async,
907
- ...ah.openArgs
908
- );
909
- for (const header in request.headers) {
910
- xhr.setRequestHeader(header, request.headers[header]);
911
- }
912
- xhr.send(request.data);
913
- }
914
- });
1114
+ }
1115
+ removeEventListener(...args) {
1116
+ if (xhrAsyncEvents.includes(args[0])) {
1117
+ this.removeEvent(args[0], args[1]);
1118
+ } else {
1119
+ this.originalXhr.removeEventListener(...args);
915
1120
  }
916
1121
  }
917
- function fakeXHR() {
918
- const xhr = new winAh.realXHR();
919
- if ("__ajaxHooker" in xhr)
920
- console.warn("检测到不同版本的ajaxHooker,可能发生冲突!");
921
- xhr.__ajaxHooker = new XhrHooker(xhr);
922
- return xhr.__ajaxHooker.proxyXhr;
1122
+ open(method, url, async = true, ...args) {
1123
+ this.request = {
1124
+ type: "xhr",
1125
+ url: url.toString(),
1126
+ method: method.toUpperCase(),
1127
+ abort: false,
1128
+ headers: {},
1129
+ data: null,
1130
+ response: null,
1131
+ async: !!async,
1132
+ };
1133
+ this.openArgs = args;
1134
+ this.resThenable = new SyncThenable();
1135
+ [
1136
+ "responseURL",
1137
+ "readyState",
1138
+ "status",
1139
+ "statusText",
1140
+ ...xhrResponses,
1141
+ ].forEach((key) => {
1142
+ delete this.proxyProps[key];
1143
+ });
1144
+ return this.originalXhr.open(method, url, async, ...args);
923
1145
  }
924
- fakeXHR.prototype = win.XMLHttpRequest.prototype;
925
- Object.keys(win.XMLHttpRequest).forEach(
926
- (key) => (fakeXHR[key] = win.XMLHttpRequest[key])
927
- );
928
- function fakeFetch(url, options = {}) {
929
- if (!url) return winAh.realFetch.call(win, url, options);
930
- return new Promise(async (resolve, reject) => {
931
- const init = {};
932
- if (getType(url) === "[object Request]") {
933
- for (const prop of fetchInitProps) init[prop] = url[prop];
934
- if (url.body) init.body = await url.arrayBuffer();
935
- url = url.url;
936
- }
937
- url = url.toString();
938
- Object.assign(init, options);
939
- init.method = init.method || "GET";
940
- init.headers = init.headers || {};
941
- const request = {
942
- type: "fetch",
943
- url: url,
944
- method: init.method.toUpperCase(),
945
- abort: false,
946
- headers: parseHeaders(init.headers),
947
- data: init.body,
948
- response: null,
949
- async: true,
950
- };
951
- const req = new AHRequest(request);
952
- await req.waitForRequestKeys();
1146
+ send(data) {
1147
+ const ah = this;
1148
+ const xhr = ah.originalXhr;
1149
+ const request = ah.request;
1150
+ if (!request) return xhr.send(data);
1151
+ request.data = data;
1152
+ new AHRequest(request).waitForRequestKeys().then(() => {
953
1153
  if (request.abort) {
954
1154
  if (typeof request.response === "function") {
955
- const response = {
956
- finalUrl: request.url,
957
- status: 200,
958
- responseHeaders: {},
959
- };
960
- await req.waitForResponseKeys(response);
961
- const key = fetchResponses.find((k) => k in response);
962
- let val = response[key];
963
- if (key === "json" && typeof val === "object") {
964
- val = catchError(JSON.stringify.bind(JSON), val);
965
- }
966
- const res = new Response(val, {
967
- status: 200,
968
- statusText: "OK",
1155
+ Object.assign(ah.proxyProps, {
1156
+ responseURL: { value: request.url },
1157
+ readyState: { value: 4 },
1158
+ status: { value: 200 },
1159
+ statusText: { value: "OK" },
969
1160
  });
970
- defineProp(res, "type", () => "basic");
971
- defineProp(res, "url", () => request.url);
972
- resolve(res);
973
- } else {
974
- reject(new DOMException("aborted", "AbortError"));
1161
+ xhrAsyncEvents.forEach((evt) => xhr.dispatchEvent(new Event(evt)));
975
1162
  }
976
- return;
977
- }
978
- init.method = request.method;
979
- init.headers = request.headers;
980
- init.body = request.data;
981
- winAh.realFetch.call(win, request.url, init).then((res) => {
982
- if (typeof request.response === "function") {
983
- const response = {
984
- finalUrl: res.url,
985
- status: res.status,
986
- responseHeaders: parseHeaders(res.headers),
987
- };
988
- fetchResponses.forEach(
989
- (key) =>
990
- (res[key] = function () {
991
- if (key in response) return Promise.resolve(response[key]);
992
- return resProto[key].call(this).then((val) => {
993
- response[key] = val;
994
- return req
995
- .waitForResponseKeys(response)
996
- .then(() => (key in response ? response[key] : val));
997
- });
998
- })
999
- );
1163
+ } else {
1164
+ xhr.open(request.method, request.url, request.async, ...ah.openArgs);
1165
+ for (const header in request.headers) {
1166
+ xhr.setRequestHeader(header, request.headers[header]);
1000
1167
  }
1001
- resolve(res);
1002
- }, reject);
1168
+ xhr.send(request.data);
1169
+ }
1003
1170
  });
1004
1171
  }
1005
- function fakeFetchClone() {
1006
- const descriptors = Object.getOwnPropertyDescriptors(this);
1007
- const res = winAh.realFetchClone.call(this);
1008
- Object.defineProperties(res, descriptors);
1009
- return res;
1010
- }
1011
- winAh = win.__ajaxHooker = winAh || {
1012
- version,
1013
- fakeXHR,
1014
- fakeFetch,
1015
- fakeFetchClone,
1016
- realXHR: win.XMLHttpRequest,
1017
- realFetch: win.fetch,
1018
- realFetchClone: resProto.clone,
1019
- hookInsts: new Set(),
1020
- };
1021
- if (winAh.version !== version)
1172
+ }
1173
+ function fakeXHR() {
1174
+ const xhr = new winAh.realXHR();
1175
+ if ("__ajaxHooker" in xhr)
1022
1176
  console.warn("检测到不同版本的ajaxHooker,可能发生冲突!");
1023
- win.XMLHttpRequest = winAh.fakeXHR;
1024
- win.fetch = winAh.fakeFetch;
1025
- resProto.clone = winAh.fakeFetchClone;
1026
- winAh.hookInsts.add(hookInst);
1027
- // 针对头条、抖音 secsdk.umd.js 的兼容性处理
1028
- class AHFunction {
1029
- call(thisArg, ...args) {
1030
- if (
1031
- thisArg &&
1032
- thisArg.__ajaxHooker &&
1033
- thisArg.__ajaxHooker.proxyXhr === thisArg
1034
- ) {
1035
- thisArg = thisArg.__ajaxHooker.originalXhr;
1177
+ xhr.__ajaxHooker = new XhrHooker(xhr);
1178
+ return xhr.__ajaxHooker.proxyXhr;
1179
+ }
1180
+ fakeXHR.prototype = win.XMLHttpRequest.prototype;
1181
+ Object.keys(win.XMLHttpRequest).forEach(
1182
+ (key) => (fakeXHR[key] = win.XMLHttpRequest[key])
1183
+ );
1184
+ function fakeFetch(url, options = {}) {
1185
+ if (!url) return winAh.realFetch.call(win, url, options);
1186
+ return new Promise(async (resolve, reject) => {
1187
+ const init = {};
1188
+ if (getType(url) === "[object Request]") {
1189
+ for (const prop of fetchInitProps) init[prop] = url[prop];
1190
+ if (url.body) init.body = await url.arrayBuffer();
1191
+ url = url.url;
1192
+ }
1193
+ url = url.toString();
1194
+ Object.assign(init, options);
1195
+ init.method = init.method || "GET";
1196
+ init.headers = init.headers || {};
1197
+ const request = {
1198
+ type: "fetch",
1199
+ url: url,
1200
+ method: init.method.toUpperCase(),
1201
+ abort: false,
1202
+ headers: parseHeaders(init.headers),
1203
+ data: init.body,
1204
+ response: null,
1205
+ async: true,
1206
+ };
1207
+ const req = new AHRequest(request);
1208
+ await req.waitForRequestKeys();
1209
+ if (request.abort) {
1210
+ if (typeof request.response === "function") {
1211
+ const response = {
1212
+ finalUrl: request.url,
1213
+ status: 200,
1214
+ responseHeaders: {},
1215
+ };
1216
+ await req.waitForResponseKeys(response);
1217
+ const key = fetchResponses.find((k) => k in response);
1218
+ let val = response[key];
1219
+ if (key === "json" && typeof val === "object") {
1220
+ val = catchError(JSON.stringify.bind(JSON), val);
1221
+ }
1222
+ const res = new Response(val, {
1223
+ status: 200,
1224
+ statusText: "OK",
1225
+ });
1226
+ defineProp(res, "type", () => "basic");
1227
+ defineProp(res, "url", () => request.url);
1228
+ resolve(res);
1229
+ } else {
1230
+ reject(new DOMException("aborted", "AbortError"));
1036
1231
  }
1037
- return Reflect.apply(this, thisArg, args);
1232
+ return;
1038
1233
  }
1039
- apply(thisArg, args) {
1040
- if (
1041
- thisArg &&
1042
- thisArg.__ajaxHooker &&
1043
- thisArg.__ajaxHooker.proxyXhr === thisArg
1044
- ) {
1045
- thisArg = thisArg.__ajaxHooker.originalXhr;
1234
+ init.method = request.method;
1235
+ init.headers = request.headers;
1236
+ init.body = request.data;
1237
+ winAh.realFetch.call(win, request.url, init).then((res) => {
1238
+ if (typeof request.response === "function") {
1239
+ const response = {
1240
+ finalUrl: res.url,
1241
+ status: res.status,
1242
+ responseHeaders: parseHeaders(res.headers),
1243
+ };
1244
+ fetchResponses.forEach(
1245
+ (key) =>
1246
+ (res[key] = function () {
1247
+ if (key in response) return Promise.resolve(response[key]);
1248
+ return resProto[key].call(this).then((val) => {
1249
+ response[key] = val;
1250
+ return req
1251
+ .waitForResponseKeys(response)
1252
+ .then(() => (key in response ? response[key] : val));
1253
+ });
1254
+ })
1255
+ );
1046
1256
  }
1047
- return Reflect.apply(this, thisArg, args || []);
1257
+ resolve(res);
1258
+ }, reject);
1259
+ });
1260
+ }
1261
+ function fakeFetchClone() {
1262
+ const descriptors = Object.getOwnPropertyDescriptors(this);
1263
+ const res = winAh.realFetchClone.call(this);
1264
+ Object.defineProperties(res, descriptors);
1265
+ return res;
1266
+ }
1267
+ winAh = win.__ajaxHooker = winAh || {
1268
+ version,
1269
+ fakeXHR,
1270
+ fakeFetch,
1271
+ fakeFetchClone,
1272
+ realXHR: win.XMLHttpRequest,
1273
+ realFetch: win.fetch,
1274
+ realFetchClone: resProto.clone,
1275
+ hookInsts: new Set(),
1276
+ };
1277
+ if (winAh.version !== version)
1278
+ console.warn("检测到不同版本的ajaxHooker,可能发生冲突!");
1279
+ win.XMLHttpRequest = winAh.fakeXHR;
1280
+ win.fetch = winAh.fakeFetch;
1281
+ resProto.clone = winAh.fakeFetchClone;
1282
+ winAh.hookInsts.add(hookInst);
1283
+ // 针对头条、抖音 secsdk.umd.js 的兼容性处理
1284
+ class AHFunction extends Function {
1285
+ call(thisArg, ...args) {
1286
+ if (
1287
+ thisArg &&
1288
+ thisArg.__ajaxHooker &&
1289
+ thisArg.__ajaxHooker.proxyXhr === thisArg
1290
+ ) {
1291
+ thisArg = thisArg.__ajaxHooker.originalXhr;
1048
1292
  }
1293
+ return Reflect.apply(this, thisArg, args);
1049
1294
  }
1050
- function hookSecsdk(csrf) {
1051
- Object.setPrototypeOf(
1052
- csrf.nativeXMLHttpRequestSetRequestHeader,
1053
- AHFunction.prototype
1054
- );
1055
- Object.setPrototypeOf(
1056
- csrf.nativeXMLHttpRequestOpen,
1057
- AHFunction.prototype
1058
- );
1059
- Object.setPrototypeOf(
1060
- csrf.nativeXMLHttpRequestSend,
1061
- AHFunction.prototype
1062
- );
1295
+ apply(thisArg, args) {
1296
+ if (
1297
+ thisArg &&
1298
+ thisArg.__ajaxHooker &&
1299
+ thisArg.__ajaxHooker.proxyXhr === thisArg
1300
+ ) {
1301
+ thisArg = thisArg.__ajaxHooker.originalXhr;
1302
+ }
1303
+ return Reflect.apply(this, thisArg, args || []);
1063
1304
  }
1064
- if (win.secsdk) {
1065
- if (win.secsdk.csrf && win.secsdk.csrf.nativeXMLHttpRequestOpen)
1066
- hookSecsdk(win.secsdk.csrf);
1067
- } else {
1068
- defineProp(win, "secsdk", emptyFn, (secsdk) => {
1069
- delete win.secsdk;
1070
- win.secsdk = secsdk;
1071
- defineProp(secsdk, "csrf", emptyFn, (csrf) => {
1072
- delete secsdk.csrf;
1073
- secsdk.csrf = csrf;
1074
- if (csrf.nativeXMLHttpRequestOpen) hookSecsdk(csrf);
1075
- });
1305
+ }
1306
+ function hookSecsdk(csrf) {
1307
+ Object.setPrototypeOf(
1308
+ csrf.nativeXMLHttpRequestSetRequestHeader,
1309
+ AHFunction.prototype
1310
+ );
1311
+ Object.setPrototypeOf(csrf.nativeXMLHttpRequestOpen, AHFunction.prototype);
1312
+ Object.setPrototypeOf(csrf.nativeXMLHttpRequestSend, AHFunction.prototype);
1313
+ }
1314
+ if (win.secsdk) {
1315
+ if (win.secsdk.csrf && win.secsdk.csrf.nativeXMLHttpRequestOpen)
1316
+ hookSecsdk(win.secsdk.csrf);
1317
+ } else {
1318
+ defineProp(win, "secsdk", emptyFn, (secsdk) => {
1319
+ delete win.secsdk;
1320
+ win.secsdk = secsdk;
1321
+ defineProp(secsdk, "csrf", emptyFn, (csrf) => {
1322
+ delete secsdk.csrf;
1323
+ secsdk.csrf = csrf;
1324
+ if (csrf.nativeXMLHttpRequestOpen) hookSecsdk(csrf);
1076
1325
  });
1077
- }
1078
- return {
1079
- hook: (fn) => hookInst.hookFns.push(fn),
1080
- filter: (arr) => {
1081
- if (Array.isArray(arr)) hookInst.filters = arr;
1082
- },
1083
- protect: () => {
1084
- readonly(win, "XMLHttpRequest", winAh.fakeXHR);
1085
- readonly(win, "fetch", winAh.fakeFetch);
1086
- readonly(resProto, "clone", winAh.fakeFetchClone);
1087
- },
1088
- unhook: () => {
1089
- winAh.hookInsts.delete(hookInst);
1090
- if (!winAh.hookInsts.size) {
1091
- writable(win, "XMLHttpRequest", winAh.realXHR);
1092
- writable(win, "fetch", winAh.realFetch);
1093
- writable(resProto, "clone", winAh.realFetchClone);
1094
- delete win.__ajaxHooker;
1095
- }
1096
- },
1097
- };
1098
- })();
1326
+ });
1327
+ }
1328
+ return {
1329
+ hook: (fn) => hookInst.hookFns.push(fn),
1330
+ filter: (arr) => {
1331
+ if (Array.isArray(arr)) hookInst.filters = arr;
1332
+ },
1333
+ protect: () => {
1334
+ readonly(win, "XMLHttpRequest", winAh.fakeXHR);
1335
+ readonly(win, "fetch", winAh.fakeFetch);
1336
+ readonly(resProto, "clone", winAh.fakeFetchClone);
1337
+ },
1338
+ unhook: () => {
1339
+ winAh.hookInsts.delete(hookInst);
1340
+ if (!winAh.hookInsts.size) {
1341
+ writable(win, "XMLHttpRequest", winAh.realXHR);
1342
+ writable(win, "fetch", winAh.realFetch);
1343
+ writable(resProto, "clone", winAh.realFetchClone);
1344
+ delete win.__ajaxHooker;
1345
+ }
1346
+ },
1347
+ };
1099
1348
  };
1100
1349
 
1101
1350
  // ==UserScript==
@@ -1627,7 +1876,7 @@
1627
1876
  menuOptions = [menuOptions];
1628
1877
  }
1629
1878
  for (let index = 0; index < menuOptions.length; index++) {
1630
- let cloneMenuOptionData = utils.deepClone(menuOptions[index].data);
1879
+ let cloneMenuOptionData = commonUtil.deepClone(menuOptions[index].data);
1631
1880
  const { showText, clickCallBack } = this.handleMenuData(cloneMenuOptionData);
1632
1881
  let menuId = that.context.GM_Api.registerMenuCommand(showText, clickCallBack);
1633
1882
  menuOptions[index].id = menuId;
@@ -1799,14 +2048,14 @@
1799
2048
  const option = menuOption[index];
1800
2049
  this.MenuHandle.$data.data.push({
1801
2050
  data: option,
1802
- id: undefined,
2051
+ id: void 0,
1803
2052
  });
1804
2053
  }
1805
2054
  }
1806
2055
  else {
1807
2056
  this.MenuHandle.$data.data.push({
1808
2057
  data: menuOption,
1809
- id: undefined,
2058
+ id: void 0,
1810
2059
  });
1811
2060
  }
1812
2061
  }
@@ -2029,16 +2278,12 @@
2029
2278
  return "";
2030
2279
  }
2031
2280
  try {
2032
- eval("_context[_funcName] = function " +
2033
- _funcName +
2034
- "(){\n" +
2035
- "let args = Array.prototype.slice.call(arguments,0);\n" +
2036
- "let obj = this;\n" +
2037
- "hookFunc.apply(obj,args);\n" +
2038
- "return _context['realFunc_" +
2039
- _funcName +
2040
- "'].apply(obj,args);\n" +
2041
- "};");
2281
+ new Function("_context", "_funcName", "hookFunc", `_context[_funcName] = function ${_funcName}() {
2282
+ let args = Array.prototype.slice.call(arguments, 0);
2283
+ let obj = this;
2284
+ hookFunc.apply(obj, args);
2285
+ return _context['realFunc_${_funcName}'].apply(obj, args);
2286
+ };`)(_context, _funcName, hookFunc);
2042
2287
  _context[_funcName].prototype.isHooked = true;
2043
2288
  return true;
2044
2289
  }
@@ -2298,14 +2543,14 @@
2298
2543
  if (typeof args[1] === "object") {
2299
2544
  /* 处理第二个参数details */
2300
2545
  let optionArg = args[1];
2301
- utils.assign(option, optionArg, true);
2546
+ commonUtil.assign(option, optionArg, true);
2302
2547
  option.url = url;
2303
2548
  }
2304
2549
  }
2305
2550
  else {
2306
2551
  /* 传入的是配置 */
2307
2552
  let optionArg = args[0];
2308
- utils.assign(option, optionArg, true);
2553
+ commonUtil.assign(option, optionArg, true);
2309
2554
  }
2310
2555
  return option;
2311
2556
  },
@@ -2338,7 +2583,7 @@
2338
2583
  responseType: userRequestOption.responseType ||
2339
2584
  this.context.#defaultRequestOption.responseType,
2340
2585
  /* 对象使用深拷贝 */
2341
- headers: utils.deepClone(this.context.#defaultRequestOption.headers),
2586
+ headers: commonUtil.deepClone(this.context.#defaultRequestOption.headers),
2342
2587
  data: userRequestOption.data || this.context.#defaultRequestOption.data,
2343
2588
  redirect: userRequestOption.redirect ||
2344
2589
  this.context.#defaultRequestOption.redirect,
@@ -2351,7 +2596,7 @@
2351
2596
  revalidate: userRequestOption.revalidate ||
2352
2597
  this.context.#defaultRequestOption.revalidate,
2353
2598
  /* 对象使用深拷贝 */
2354
- context: utils.deepClone(userRequestOption.context ||
2599
+ context: commonUtil.deepClone(userRequestOption.context ||
2355
2600
  this.context.#defaultRequestOption.context),
2356
2601
  overrideMimeType: userRequestOption.overrideMimeType ||
2357
2602
  this.context.#defaultRequestOption.overrideMimeType,
@@ -2359,7 +2604,7 @@
2359
2604
  this.context.#defaultRequestOption.anonymous,
2360
2605
  fetch: userRequestOption.fetch || this.context.#defaultRequestOption.fetch,
2361
2606
  /* 对象使用深拷贝 */
2362
- fetchInit: utils.deepClone(this.context.#defaultRequestOption.fetchInit),
2607
+ fetchInit: commonUtil.deepClone(this.context.#defaultRequestOption.fetchInit),
2363
2608
  allowInterceptConfig: {
2364
2609
  beforeRequest: this.context.#defaultRequestOption
2365
2610
  .allowInterceptConfig.beforeRequest,
@@ -2585,12 +2830,12 @@
2585
2830
  Object.keys(option).forEach((keyName) => {
2586
2831
  if (option[keyName] == null ||
2587
2832
  (option[keyName] instanceof Function &&
2588
- utils.isNull(option[keyName]))) {
2833
+ commonUtil.isNull(option[keyName]))) {
2589
2834
  Reflect.deleteProperty(option, keyName);
2590
2835
  return;
2591
2836
  }
2592
2837
  });
2593
- if (utils.isNull(option.url)) {
2838
+ if (commonUtil.isNull(option.url)) {
2594
2839
  throw new TypeError(`Utils.Httpx 参数 url不符合要求: ${option.url}`);
2595
2840
  }
2596
2841
  return option;
@@ -2789,10 +3034,10 @@
2789
3034
  /* X浏览器会因为设置了responseType导致不返回responseText */
2790
3035
  let originResponse = argsResult[0];
2791
3036
  /* responseText为空,response不为空的情况 */
2792
- if (utils.isNull(originResponse["responseText"]) &&
2793
- utils.isNotNull(originResponse["response"])) {
3037
+ if (commonUtil.isNull(originResponse["responseText"]) &&
3038
+ commonUtil.isNotNull(originResponse["response"])) {
2794
3039
  if (typeof originResponse["response"] === "object") {
2795
- utils.tryCatch().run(() => {
3040
+ TryCatch().run(() => {
2796
3041
  originResponse["responseText"] = JSON.stringify(originResponse["response"]);
2797
3042
  });
2798
3043
  }
@@ -2809,7 +3054,7 @@
2809
3054
  // 自定义个新的response
2810
3055
  let httpxResponse = httpxResponseText;
2811
3056
  if (details.responseType === "json") {
2812
- httpxResponse = utils.toJSON(httpxResponseText);
3057
+ httpxResponse = commonUtil.toJSON(httpxResponseText);
2813
3058
  }
2814
3059
  else if (details.responseType === "document") {
2815
3060
  let parser = new DOMParser();
@@ -2953,13 +3198,13 @@
2953
3198
  status: fetchResponse.status,
2954
3199
  statusText: fetchResponse.statusText,
2955
3200
  // @ts-ignore
2956
- response: undefined,
3201
+ response: void 0,
2957
3202
  responseFetchHeaders: fetchResponse.headers,
2958
3203
  responseHeaders: "",
2959
3204
  // @ts-ignore
2960
- responseText: undefined,
3205
+ responseText: void 0,
2961
3206
  responseType: option.responseType,
2962
- responseXML: undefined,
3207
+ responseXML: void 0,
2963
3208
  };
2964
3209
  Object.assign(httpxResponse, option.context || {});
2965
3210
  // 把headers转为字符串
@@ -3019,7 +3264,7 @@
3019
3264
  (typeof fetchResponseType === "string" &&
3020
3265
  fetchResponseType.includes("application/json"))) {
3021
3266
  // response返回格式是JSON格式
3022
- response = utils.toJSON(responseText);
3267
+ response = commonUtil.toJSON(responseText);
3023
3268
  }
3024
3269
  else if (option.responseType === "document" ||
3025
3270
  option.responseType == null) {
@@ -3071,30 +3316,30 @@
3071
3316
  * 默认配置
3072
3317
  */
3073
3318
  #defaultRequestOption = {
3074
- url: undefined,
3319
+ url: void 0,
3075
3320
  timeout: 5000,
3076
3321
  async: false,
3077
- responseType: undefined,
3078
- headers: undefined,
3079
- data: undefined,
3080
- redirect: undefined,
3081
- cookie: undefined,
3082
- cookiePartition: undefined,
3083
- binary: undefined,
3084
- nocache: undefined,
3085
- revalidate: undefined,
3086
- context: undefined,
3087
- overrideMimeType: undefined,
3088
- anonymous: undefined,
3089
- fetch: undefined,
3090
- fetchInit: undefined,
3322
+ responseType: void 0,
3323
+ headers: void 0,
3324
+ data: void 0,
3325
+ redirect: void 0,
3326
+ cookie: void 0,
3327
+ cookiePartition: void 0,
3328
+ binary: void 0,
3329
+ nocache: void 0,
3330
+ revalidate: void 0,
3331
+ context: void 0,
3332
+ overrideMimeType: void 0,
3333
+ anonymous: void 0,
3334
+ fetch: void 0,
3335
+ fetchInit: void 0,
3091
3336
  allowInterceptConfig: {
3092
3337
  beforeRequest: true,
3093
3338
  afterResponseSuccess: true,
3094
3339
  afterResponseError: true,
3095
3340
  },
3096
- user: undefined,
3097
- password: undefined,
3341
+ user: void 0,
3342
+ password: void 0,
3098
3343
  onabort() { },
3099
3344
  onerror() { },
3100
3345
  ontimeout() { },
@@ -3106,7 +3351,7 @@
3106
3351
  /**
3107
3352
  * `baseURL` 将自动加在 `url` 前面,除非 `url` 是一个绝对 URL。
3108
3353
  */
3109
- baseURL: undefined,
3354
+ baseURL: void 0,
3110
3355
  /**
3111
3356
  * 当前使用请求时,输出请求的配置,一般用于DEBUG|DEV
3112
3357
  */
@@ -3120,7 +3365,7 @@
3120
3365
  if (typeof option.xmlHttpRequest !== "function") {
3121
3366
  console.warn("[Httpx-constructor] 未传入GM_xmlhttpRequest函数或传入的GM_xmlhttpRequest不是Function,将默认使用window.fetch");
3122
3367
  }
3123
- utils.coverObjectFunctionThis(this);
3368
+ commonUtil.coverObjectFunctionThis(this);
3124
3369
  this.interceptors.request.context = this;
3125
3370
  this.interceptors.response.context = this;
3126
3371
  this.config(option);
@@ -3133,8 +3378,8 @@
3133
3378
  if (typeof option.xmlHttpRequest === "function") {
3134
3379
  this.GM_Api.xmlHttpRequest = option.xmlHttpRequest;
3135
3380
  }
3136
- this.#defaultRequestOption = utils.assign(this.#defaultRequestOption, option);
3137
- this.#defaultInitOption = utils.assign(this.#defaultInitOption, option);
3381
+ this.#defaultRequestOption = commonUtil.assign(this.#defaultRequestOption, option);
3382
+ this.#defaultInitOption = commonUtil.assign(this.#defaultInitOption, option);
3138
3383
  }
3139
3384
  /**
3140
3385
  * 拦截器
@@ -3511,7 +3756,7 @@
3511
3756
  success: false,
3512
3757
  code: that.#statusCode.getFailed.code,
3513
3758
  msg: that.#statusCode.getFailed.msg,
3514
- data: undefined,
3759
+ data: void 0,
3515
3760
  });
3516
3761
  }
3517
3762
  else {
@@ -3521,7 +3766,7 @@
3521
3766
  let result = target.result;
3522
3767
  /* result 返回的是 {key: string, value: any} */
3523
3768
  /* 键值对存储 */
3524
- let data = result ? result.value : undefined;
3769
+ let data = result ? result.value : void 0;
3525
3770
  if (data == null) {
3526
3771
  resolve({
3527
3772
  success: true,
@@ -3548,7 +3793,7 @@
3548
3793
  success: false,
3549
3794
  code: that.#statusCode.getFailed.code,
3550
3795
  msg: that.#statusCode.getFailed.msg,
3551
- data: undefined,
3796
+ data: void 0,
3552
3797
  event: event,
3553
3798
  });
3554
3799
  };
@@ -3698,7 +3943,7 @@
3698
3943
  #flag = false;
3699
3944
  #delayTime = 0;
3700
3945
  #callback;
3701
- #context;
3946
+ #timeId = void 0;
3702
3947
  lock;
3703
3948
  unlock;
3704
3949
  run;
@@ -3708,23 +3953,22 @@
3708
3953
  this.#callback = callback;
3709
3954
  if (typeof context === "number") {
3710
3955
  this.#delayTime = context;
3711
- this.#context = utils;
3712
3956
  }
3713
3957
  else {
3714
3958
  this.#delayTime = delayTime;
3715
- this.#context = context;
3716
3959
  }
3717
3960
  /**
3718
3961
  * 锁
3719
3962
  */
3720
3963
  this.lock = function () {
3721
3964
  that.#flag = true;
3965
+ clearTimeout(that.#timeId);
3722
3966
  };
3723
3967
  /**
3724
3968
  * 解锁
3725
3969
  */
3726
3970
  this.unlock = function () {
3727
- utils.workerSetTimeout(() => {
3971
+ that.#timeId = setTimeout(() => {
3728
3972
  that.#flag = false;
3729
3973
  }, that.#delayTime);
3730
3974
  };
@@ -3742,7 +3986,7 @@
3742
3986
  return;
3743
3987
  }
3744
3988
  that.lock();
3745
- await that.#callback.apply(that.#context, args);
3989
+ await that.#callback.apply(this, args);
3746
3990
  that.unlock();
3747
3991
  };
3748
3992
  }
@@ -4030,7 +4274,7 @@
4030
4274
  * @param paramConfig 配置信息
4031
4275
  */
4032
4276
  constructor(paramConfig) {
4033
- this.#config = utils.assign(this.#config, paramConfig);
4277
+ this.#config = commonUtil.assign(this.#config, paramConfig);
4034
4278
  if (!(this.#config.canvasNode instanceof HTMLCanvasElement)) {
4035
4279
  throw new Error("Utils.Progress 参数 canvasNode 必须是 HTMLCanvasElement");
4036
4280
  }
@@ -4082,97 +4326,12 @@
4082
4326
  let txt = parseInt(this.#config.progress.toString()) + "%";
4083
4327
  this.#ctx.font = this.#config.fontSize + "px SimHei";
4084
4328
  /* 获取文本宽度 */
4085
- let w = this.#ctx.measureText(txt).width;
4086
- let h = this.#config.fontSize / 2;
4087
- this.#ctx.fillStyle = this.#config.textColor;
4088
- this.#ctx.fillText(txt, this.#width / 2 - w / 2, this.#height / 2 + h / 2);
4089
- }
4090
- }
4091
-
4092
- const TryCatch = function (...args) {
4093
- /* 定义变量和函数 */
4094
- let callbackFunction = null;
4095
- let context = null;
4096
- let handleError = (error) => { };
4097
- let defaultDetails = {
4098
- log: true,
4099
- };
4100
- const TryCatchCore = {
4101
- /**
4102
- *
4103
- * @param paramDetails 配置
4104
- * @returns
4105
- */
4106
- config(paramDetails) {
4107
- defaultDetails = utils.assign(defaultDetails, paramDetails);
4108
- return TryCatchCore;
4109
- },
4110
- /**
4111
- * 处理错误
4112
- * @param handler
4113
- */
4114
- error(handler) {
4115
- // @ts-ignore
4116
- handleError = handler;
4117
- return TryCatchCore;
4118
- },
4119
- /**
4120
- * 执行传入的函数并捕获其可能抛出的错误,并通过传入的错误处理函数进行处理。
4121
- * @param callback 待执行函数,可以是 function 或者 string 类型。如果是 string 类型,则会被当做代码进行执行。
4122
- * @param __context__ 待执行函数的作用域,用于apply指定
4123
- * @returns 如果函数有返回值,则返回该返回值;否则返回 tryCatchObj 函数以支持链式调用。
4124
- * @throws {Error} 如果传入参数不符合要求,则会抛出相应类型的错误。
4125
- */
4126
- run(callback, __context__) {
4127
- callbackFunction = callback;
4128
- context = __context__ || this;
4129
- let result = executeTryCatch(callbackFunction, handleError, context);
4130
- // @ts-ignore
4131
- return result !== undefined ? result : TryCatchCore;
4132
- },
4133
- };
4134
- /**
4135
- * 执行传入的函数并捕获其可能抛出的错误,并通过传入的错误处理函数进行处理。
4136
- * @param callback - 待执行函数,可以是 function 或者 string 类型。如果是 string 类型,则会被当做代码进行执行。
4137
- * @param handleErrorFunc - 错误处理函数,可以是 function 或者 string 类型。如果是 string 类型,则会被当做代码进行执行。
4138
- * @param funcThis - 待执行函数的作用域,用于apply指定
4139
- * @returns 如果函数有返回值,则返回该返回值;否则返回 undefined。
4140
- */
4141
- function executeTryCatch(callback, handleErrorFunc, funcThis) {
4142
- let result = undefined;
4143
- try {
4144
- if (typeof callback === "string") {
4145
- (function () {
4146
- eval(callback);
4147
- }).apply(funcThis, args);
4148
- }
4149
- else {
4150
- result = callback.apply(funcThis, args);
4151
- }
4152
- }
4153
- catch (error) {
4154
- if (defaultDetails.log) {
4155
- callback = callback;
4156
- console.log(`%c ${callback?.name ? callback?.name : callback + "出现错误"} `, "color: #f20000");
4157
- console.log(`%c 错误原因:${error}`, "color: #f20000");
4158
- console.trace(callback);
4159
- }
4160
- if (handleErrorFunc) {
4161
- if (typeof handleErrorFunc === "string") {
4162
- result = function () {
4163
- return eval(handleErrorFunc);
4164
- // @ts-ignore
4165
- }.apply(funcThis, [...args, error]);
4166
- }
4167
- else {
4168
- result = handleErrorFunc.apply(funcThis, [...args, error]);
4169
- }
4170
- }
4171
- }
4172
- return result;
4329
+ let w = this.#ctx.measureText(txt).width;
4330
+ let h = this.#config.fontSize / 2;
4331
+ this.#ctx.fillStyle = this.#config.textColor;
4332
+ this.#ctx.fillText(txt, this.#width / 2 - w / 2, this.#height / 2 + h / 2);
4173
4333
  }
4174
- return TryCatchCore;
4175
- };
4334
+ }
4176
4335
 
4177
4336
  class UtilsDictionary {
4178
4337
  items = {};
@@ -4207,7 +4366,7 @@
4207
4366
  */
4208
4367
  getStartsWith(key) {
4209
4368
  let allKeys = this.keys();
4210
- let result = undefined;
4369
+ let result = void 0;
4211
4370
  for (const keyName of allKeys) {
4212
4371
  if (String(keyName).startsWith(String(key))) {
4213
4372
  result = this.get(keyName);
@@ -4222,7 +4381,7 @@
4222
4381
  * @param val 值,默认为""
4223
4382
  */
4224
4383
  set(key, val) {
4225
- if (key === undefined) {
4384
+ if (key === void 0) {
4226
4385
  throw new Error("Utils.Dictionary().set 参数 key 不能为空");
4227
4386
  }
4228
4387
  Reflect.set(this.items, key, val);
@@ -4289,7 +4448,7 @@
4289
4448
  * @param data 需要合并的字典
4290
4449
  */
4291
4450
  concat(data) {
4292
- this.items = utils.assign(this.items, data.getItems());
4451
+ this.items = commonUtil.assign(this.items, data.getItems());
4293
4452
  }
4294
4453
  forEach(callbackfn) {
4295
4454
  for (const key in this.getItems()) {
@@ -4848,7 +5007,7 @@
4848
5007
 
4849
5008
  const loadOrReturnBroker = createLoadOrReturnBroker(load, worker);
4850
5009
  const clearInterval = (timerId) => loadOrReturnBroker().clearInterval(timerId);
4851
- const clearTimeout = (timerId) => loadOrReturnBroker().clearTimeout(timerId);
5010
+ const clearTimeout$1 = (timerId) => loadOrReturnBroker().clearTimeout(timerId);
4852
5011
  const setInterval = (...args) => loadOrReturnBroker().setInterval(...args);
4853
5012
  const setTimeout$1 = (...args) => loadOrReturnBroker().setTimeout(...args);
4854
5013
 
@@ -5250,13 +5409,194 @@
5250
5409
  }
5251
5410
  }
5252
5411
 
5412
+ class DOMUtils {
5413
+ windowApi;
5414
+ constructor(option) {
5415
+ this.windowApi = new WindowApi(option);
5416
+ }
5417
+ selector(selector, parent) {
5418
+ return this.selectorAll(selector, parent)[0];
5419
+ }
5420
+ selectorAll(selector, parent) {
5421
+ const context = this;
5422
+ parent = parent || context.windowApi.document;
5423
+ selector = selector.trim();
5424
+ if (selector.match(/[^\s]{1}:empty$/gi)) {
5425
+ // empty 语法
5426
+ selector = selector.replace(/:empty$/gi, "");
5427
+ return Array.from(parent.querySelectorAll(selector)).filter(($ele) => {
5428
+ return $ele?.innerHTML?.trim() === "";
5429
+ });
5430
+ }
5431
+ else if (selector.match(/[^\s]{1}:contains\("(.*)"\)$/i) ||
5432
+ selector.match(/[^\s]{1}:contains\('(.*)'\)$/i)) {
5433
+ // contains 语法
5434
+ let textMatch = selector.match(/:contains\(("|')(.*)("|')\)$/i);
5435
+ let text = textMatch[2];
5436
+ selector = selector.replace(/:contains\(("|')(.*)("|')\)$/gi, "");
5437
+ return Array.from(parent.querySelectorAll(selector)).filter(($ele) => {
5438
+ // @ts-ignore
5439
+ return ($ele?.textContent || $ele?.innerText)?.includes(text);
5440
+ });
5441
+ }
5442
+ else if (selector.match(/[^\s]{1}:regexp\("(.*)"\)$/i) ||
5443
+ selector.match(/[^\s]{1}:regexp\('(.*)'\)$/i)) {
5444
+ // regexp 语法
5445
+ let textMatch = selector.match(/:regexp\(("|')(.*)("|')\)$/i);
5446
+ let pattern = textMatch[2];
5447
+ let flagMatch = pattern.match(/("|'),[\s]*("|')([igm]{0,3})$/i);
5448
+ let flags = "";
5449
+ if (flagMatch) {
5450
+ pattern = pattern.replace(/("|'),[\s]*("|')([igm]{0,3})$/gi, "");
5451
+ flags = flagMatch[3];
5452
+ }
5453
+ let regexp = new RegExp(pattern, flags);
5454
+ selector = selector.replace(/:regexp\(("|')(.*)("|')\)$/gi, "");
5455
+ return Array.from(parent.querySelectorAll(selector)).filter(($ele) => {
5456
+ // @ts-ignore
5457
+ return Boolean(($ele?.textContent || $ele?.innerText)?.match(regexp));
5458
+ });
5459
+ }
5460
+ else {
5461
+ // 普通语法
5462
+ return Array.from(parent.querySelectorAll(selector));
5463
+ }
5464
+ }
5465
+ /**
5466
+ * 匹配元素,可使用以下的额外语法
5467
+ *
5468
+ * + :contains([text]) 作用: 找到包含指定文本内容的指定元素
5469
+ * + :empty 作用:找到既没有文本内容也没有子元素的指定元素
5470
+ * + :regexp([text]) 作用: 找到符合正则表达式的内容的指定元素
5471
+ * @param $el 元素
5472
+ * @param selector 选择器
5473
+ * @example
5474
+ * DOMUtils.matches("div:contains('测试')")
5475
+ * > true
5476
+ * @example
5477
+ * DOMUtils.matches("div:empty")
5478
+ * > true
5479
+ * @example
5480
+ * DOMUtils.matches("div:regexp('^xxxx$')")
5481
+ * > true
5482
+ * @example
5483
+ * DOMUtils.matches("div:regexp(/^xxx/ig)")
5484
+ * > false
5485
+ */
5486
+ matches($el, selector) {
5487
+ selector = selector.trim();
5488
+ if ($el == null) {
5489
+ return false;
5490
+ }
5491
+ if (selector.match(/[^\s]{1}:empty$/gi)) {
5492
+ // empty 语法
5493
+ selector = selector.replace(/:empty$/gi, "");
5494
+ return $el.matches(selector) && $el?.innerHTML?.trim() === "";
5495
+ }
5496
+ else if (selector.match(/[^\s]{1}:contains\("(.*)"\)$/i) ||
5497
+ selector.match(/[^\s]{1}:contains\('(.*)'\)$/i)) {
5498
+ // contains 语法
5499
+ let textMatch = selector.match(/:contains\(("|')(.*)("|')\)$/i);
5500
+ let text = textMatch[2];
5501
+ selector = selector.replace(/:contains\(("|')(.*)("|')\)$/gi, "");
5502
+ // @ts-ignore
5503
+ let content = $el?.textContent || $el?.innerText;
5504
+ if (typeof content !== "string") {
5505
+ content = "";
5506
+ }
5507
+ return $el.matches(selector) && content?.includes(text);
5508
+ }
5509
+ else if (selector.match(/[^\s]{1}:regexp\("(.*)"\)$/i) ||
5510
+ selector.match(/[^\s]{1}:regexp\('(.*)'\)$/i)) {
5511
+ // regexp 语法
5512
+ let textMatch = selector.match(/:regexp\(("|')(.*)("|')\)$/i);
5513
+ let pattern = textMatch[2];
5514
+ let flagMatch = pattern.match(/("|'),[\s]*("|')([igm]{0,3})$/i);
5515
+ let flags = "";
5516
+ if (flagMatch) {
5517
+ pattern = pattern.replace(/("|'),[\s]*("|')([igm]{0,3})$/gi, "");
5518
+ flags = flagMatch[3];
5519
+ }
5520
+ let regexp = new RegExp(pattern, flags);
5521
+ selector = selector.replace(/:regexp\(("|')(.*)("|')\)$/gi, "");
5522
+ // @ts-ignore
5523
+ let content = $el?.textContent || $el?.innerText;
5524
+ if (typeof content !== "string") {
5525
+ content = "";
5526
+ }
5527
+ return $el.matches(selector) && Boolean(content?.match(regexp));
5528
+ }
5529
+ else {
5530
+ // 普通语法
5531
+ return $el.matches(selector);
5532
+ }
5533
+ }
5534
+ closest($el, selector) {
5535
+ selector = selector.trim();
5536
+ if (selector.match(/[^\s]{1}:empty$/gi)) {
5537
+ // empty 语法
5538
+ selector = selector.replace(/:empty$/gi, "");
5539
+ let $closest = $el?.closest(selector);
5540
+ if ($closest && $closest?.innerHTML?.trim() === "") {
5541
+ return $closest;
5542
+ }
5543
+ return null;
5544
+ }
5545
+ else if (selector.match(/[^\s]{1}:contains\("(.*)"\)$/i) ||
5546
+ selector.match(/[^\s]{1}:contains\('(.*)'\)$/i)) {
5547
+ // contains 语法
5548
+ let textMatch = selector.match(/:contains\(("|')(.*)("|')\)$/i);
5549
+ let text = textMatch[2];
5550
+ selector = selector.replace(/:contains\(("|')(.*)("|')\)$/gi, "");
5551
+ let $closest = $el?.closest(selector);
5552
+ if ($closest) {
5553
+ // @ts-ignore
5554
+ let content = $el?.textContent || $el?.innerText;
5555
+ if (typeof content === "string" && content.includes(text)) {
5556
+ return $closest;
5557
+ }
5558
+ }
5559
+ return null;
5560
+ }
5561
+ else if (selector.match(/[^\s]{1}:regexp\("(.*)"\)$/i) ||
5562
+ selector.match(/[^\s]{1}:regexp\('(.*)'\)$/i)) {
5563
+ // regexp 语法
5564
+ let textMatch = selector.match(/:regexp\(("|')(.*)("|')\)$/i);
5565
+ let pattern = textMatch[2];
5566
+ let flagMatch = pattern.match(/("|'),[\s]*("|')([igm]{0,3})$/i);
5567
+ let flags = "";
5568
+ if (flagMatch) {
5569
+ pattern = pattern.replace(/("|'),[\s]*("|')([igm]{0,3})$/gi, "");
5570
+ flags = flagMatch[3];
5571
+ }
5572
+ let regexp = new RegExp(pattern, flags);
5573
+ selector = selector.replace(/:regexp\(("|')(.*)("|')\)$/gi, "");
5574
+ let $closest = $el?.closest(selector);
5575
+ if ($closest) {
5576
+ // @ts-ignore
5577
+ let content = $el?.textContent || $el?.innerText;
5578
+ if (typeof content === "string" && content.match(regexp)) {
5579
+ return $closest;
5580
+ }
5581
+ }
5582
+ return null;
5583
+ }
5584
+ else {
5585
+ // 普通语法
5586
+ let $closest = $el?.closest(selector);
5587
+ return $closest;
5588
+ }
5589
+ }
5590
+ }
5591
+ let domUtils = new DOMUtils();
5592
+
5253
5593
  class Utils {
5254
5594
  windowApi;
5255
5595
  constructor(option) {
5256
5596
  this.windowApi = new WindowApi(option);
5257
5597
  }
5258
5598
  /** 版本号 */
5259
- version = "2025.5.28";
5599
+ version = "2025.6.26";
5260
5600
  addStyle(cssText) {
5261
5601
  if (typeof cssText !== "string") {
5262
5602
  throw new Error("Utils.addStyle 参数cssText 必须为String类型");
@@ -5282,58 +5622,22 @@
5282
5622
  }
5283
5623
  return cssNode;
5284
5624
  }
5285
- assign(target = {}, source = {}, isAdd = false) {
5286
- let UtilsContext = this;
5287
- if (Array.isArray(source)) {
5288
- let canTraverse = source.filter((item) => {
5289
- return typeof item === "object";
5290
- });
5291
- if (!canTraverse.length) {
5292
- return source;
5293
- }
5294
- }
5295
- if (source == null) {
5296
- return target;
5297
- }
5298
- if (target == null) {
5299
- target = {};
5300
- }
5301
- if (isAdd) {
5302
- for (const sourceKeyName in source) {
5303
- const targetKeyName = sourceKeyName;
5304
- let targetValue = target[targetKeyName];
5305
- let sourceValue = source[sourceKeyName];
5306
- if (typeof sourceValue === "object" &&
5307
- sourceValue != null &&
5308
- sourceKeyName in target &&
5309
- !UtilsContext.isDOM(sourceValue)) {
5310
- /* 源端的值是object类型,且不是元素节点 */
5311
- target[sourceKeyName] = UtilsContext.assign(targetValue, sourceValue, isAdd);
5312
- continue;
5313
- }
5314
- target[sourceKeyName] = sourceValue;
5315
- }
5316
- }
5317
- else {
5318
- for (const targetKeyName in target) {
5319
- if (targetKeyName in source) {
5320
- let targetValue = target[targetKeyName];
5321
- let sourceValue = source[targetKeyName];
5322
- if (typeof sourceValue === "object" &&
5323
- sourceValue != null &&
5324
- !UtilsContext.isDOM(sourceValue) &&
5325
- Object.keys(sourceValue).length) {
5326
- /* 源端的值是object类型,且不是元素节点 */
5327
- target[targetKeyName] = UtilsContext.assign(targetValue, sourceValue, isAdd);
5328
- continue;
5329
- }
5330
- /* 直接赋值 */
5331
- target[targetKeyName] = sourceValue;
5332
- }
5625
+ /**
5626
+ * JSON数据从源端替换到目标端中,如果目标端存在该数据则替换,不添加,返回结果为目标端替换完毕的结果
5627
+ * @param target 目标数据
5628
+ * @param source 源数据
5629
+ * @param isAdd 是否可以追加键,默认false
5630
+ * @example
5631
+ * Utils.assign({"1":1,"2":{"3":3}}, {"2":{"3":4}});
5632
+ * >
5633
+ * {
5634
+ "1": 1,
5635
+ "2": {
5636
+ "3": 4
5333
5637
  }
5334
5638
  }
5335
- return target;
5336
- }
5639
+ */
5640
+ assign = commonUtil.assign.bind(commonUtil);
5337
5641
  async asyncReplaceAll(string, pattern, asyncFn) {
5338
5642
  let UtilsContext = this;
5339
5643
  if (typeof string !== "string") {
@@ -5376,7 +5680,7 @@
5376
5680
  * ajax劫持库,支持xhr和fetch劫持。
5377
5681
  * + 来源:https://bbs.tampermonkey.net.cn/thread-3284-1-1.html
5378
5682
  * + 作者:cxxjackie
5379
- * + 版本:1.4.4
5683
+ * + 版本:1.4.6
5380
5684
  * + 旧版本:1.2.4
5381
5685
  * + 文档:https://scriptcat.org/zh-CN/script-show-page/637/
5382
5686
  * @param useOldVersion 是否使用旧版本,默认false
@@ -5386,7 +5690,7 @@
5386
5690
  return AjaxHooker1_2_4();
5387
5691
  }
5388
5692
  else {
5389
- return AjaxHooker();
5693
+ return ajaxHooker();
5390
5694
  }
5391
5695
  };
5392
5696
  canvasClickByPosition(canvasElement, clientX = 0, clientY = 0, view = globalThis) {
@@ -5486,19 +5790,11 @@
5486
5790
  * @returns
5487
5791
  */
5488
5792
  ColorConversion = ColorConversion;
5489
- deepClone(obj) {
5490
- let UtilsContext = this;
5491
- if (obj === undefined)
5492
- return undefined;
5493
- if (obj === null)
5494
- return null;
5495
- let clone = obj instanceof Array ? [] : {};
5496
- for (const [key, value] of Object.entries(obj)) {
5497
- clone[key] =
5498
- typeof value === "object" ? UtilsContext.deepClone(value) : value;
5499
- }
5500
- return clone;
5501
- }
5793
+ /**
5794
+ * 深拷贝
5795
+ * @param obj 对象
5796
+ */
5797
+ deepClone = commonUtil.deepClone.bind(commonUtil);
5502
5798
  debounce(fn, delay = 0) {
5503
5799
  let timer = null;
5504
5800
  let UtilsContext = this;
@@ -5521,7 +5817,7 @@
5521
5817
  throw new Error("Utils.deleteParentNode 参数 targetSelector 必须为 string 类型");
5522
5818
  }
5523
5819
  let result = false;
5524
- let needRemoveDOM = element.closest(targetSelector);
5820
+ let needRemoveDOM = domUtils.closest(element, targetSelector);
5525
5821
  if (needRemoveDOM) {
5526
5822
  needRemoveDOM.remove();
5527
5823
  result = true;
@@ -6509,9 +6805,17 @@
6509
6805
  throw new TypeError("参数1类型错误" + typeof firstArg);
6510
6806
  }
6511
6807
  }
6512
- isDOM(target) {
6513
- return target instanceof Node;
6514
- }
6808
+ /**
6809
+ * 判断对象是否是元素
6810
+ * @param target
6811
+ * @returns
6812
+ * + true 是元素
6813
+ * + false 不是元素
6814
+ * @example
6815
+ * Utils.isDOM(document.querySelector("a"))
6816
+ * > true
6817
+ */
6818
+ isDOM = commonUtil.isDOM.bind(commonUtil);
6515
6819
  isFullscreenEnabled() {
6516
6820
  return !!(this.windowApi.document.fullscreenEnabled ||
6517
6821
  this.windowApi.document.webkitFullScreenEnabled ||
@@ -6702,52 +7006,62 @@
6702
7006
  }
6703
7007
  return result;
6704
7008
  }
6705
- isNotNull(...args) {
6706
- let UtilsContext = this;
6707
- return !UtilsContext.isNull.apply(this, args);
6708
- }
6709
- isNull(...args) {
6710
- let result = true;
6711
- let checkList = [...args];
6712
- for (const objItem of checkList) {
6713
- let itemResult = false;
6714
- if (objItem === null || objItem === undefined) {
6715
- itemResult = true;
6716
- }
6717
- else {
6718
- switch (typeof objItem) {
6719
- case "object":
6720
- if (typeof objItem[Symbol.iterator] === "function") {
6721
- /* 可迭代 */
6722
- itemResult = objItem.length === 0;
6723
- }
6724
- else {
6725
- itemResult = Object.keys(objItem).length === 0;
6726
- }
6727
- break;
6728
- case "number":
6729
- itemResult = objItem === 0;
6730
- break;
6731
- case "string":
6732
- itemResult =
6733
- objItem.trim() === "" ||
6734
- objItem === "null" ||
6735
- objItem === "undefined";
6736
- break;
6737
- case "boolean":
6738
- itemResult = !objItem;
6739
- break;
6740
- case "function":
6741
- let funcStr = objItem.toString().replace(/\s/g, "");
6742
- /* 排除()=>{}、(xxx="")=>{}、function(){}、function(xxx=""){} */
6743
- itemResult = Boolean(funcStr.match(/^\(.*?\)=>\{\}$|^function.*?\(.*?\)\{\}$/));
6744
- break;
6745
- }
6746
- }
6747
- result = result && itemResult;
6748
- }
6749
- return result;
6750
- }
7009
+ /**
7010
+ * 判断对象是否不为空
7011
+ * @returns {boolean}
7012
+ * + true 不为空
7013
+ * + false 为空
7014
+ * @example
7015
+ * Utils.isNotNull("123");
7016
+ * > true
7017
+ */
7018
+ isNotNull = commonUtil.isNotNull.bind(commonUtil);
7019
+ /**
7020
+ * 判断对象或数据是否为空
7021
+ * + `String`判空的值,如 ""、"null"、"undefined"、" "
7022
+ * + `Number`判空的值,如 0
7023
+ * + `Object`判空的值,如 {}、null、undefined
7024
+ * + `Array`(存在属性Symbol.iterator)判空的值,如 []
7025
+ * + `Boolean`判空的值,如false
7026
+ * + `Function`判空的值,如()=>{}、(xxx="")=>{}、function(){}、function(xxx=""){}
7027
+ * @returns
7028
+ * + true 为空
7029
+ * + false 不为空
7030
+ * @example
7031
+ Utils.isNull({});
7032
+ > true
7033
+ * @example
7034
+ Utils.isNull([]);
7035
+ > true
7036
+ * @example
7037
+ Utils.isNull(" ");
7038
+ > true
7039
+ * @example
7040
+ Utils.isNull(function(){});
7041
+ > true
7042
+ * @example
7043
+ Utils.isNull(()=>{}));
7044
+ > true
7045
+ * @example
7046
+ Utils.isNull("undefined");
7047
+ > true
7048
+ * @example
7049
+ Utils.isNull("null");
7050
+ > true
7051
+ * @example
7052
+ Utils.isNull(" ", false);
7053
+ > true
7054
+ * @example
7055
+ Utils.isNull([1],[]);
7056
+ > false
7057
+ * @example
7058
+ Utils.isNull([],[1]);
7059
+ > false
7060
+ * @example
7061
+ Utils.isNull(false,[123]);
7062
+ > false
7063
+ **/
7064
+ isNull = commonUtil.isNull.bind(commonUtil);
6751
7065
  isThemeDark() {
6752
7066
  return this.windowApi.globalThis.matchMedia("(prefers-color-scheme: dark)")
6753
7067
  .matches;
@@ -6937,36 +7251,36 @@
6937
7251
  * + true 监听以 target 为根节点的整个子树。包括子树中所有节点的属性,而不仅仅是针对 target
6938
7252
  * + false (默认) 不生效
6939
7253
  */
6940
- subtree: undefined,
7254
+ subtree: void 0,
6941
7255
  /**
6942
7256
  * + true 监听 target 节点中发生的节点的新增与删除(同时,如果 subtree 为 true,会针对整个子树生效)
6943
7257
  * + false (默认) 不生效
6944
7258
  */
6945
- childList: undefined,
7259
+ childList: void 0,
6946
7260
  /**
6947
7261
  * + true 观察所有监听的节点属性值的变化。默认值为 true,当声明了 attributeFilter 或 attributeOldValue
6948
7262
  * + false (默认) 不生效
6949
7263
  */
6950
- attributes: undefined,
7264
+ attributes: void 0,
6951
7265
  /**
6952
7266
  * 一个用于声明哪些属性名会被监听的数组。如果不声明该属性,所有属性的变化都将触发通知
6953
7267
  */
6954
- attributeFilter: undefined,
7268
+ attributeFilter: void 0,
6955
7269
  /**
6956
7270
  * + true 记录上一次被监听的节点的属性变化;可查阅 MutationObserver 中的 Monitoring attribute values 了解关于观察属性变化和属性值记录的详情
6957
7271
  * + false (默认) 不生效
6958
7272
  */
6959
- attributeOldValue: undefined,
7273
+ attributeOldValue: void 0,
6960
7274
  /**
6961
7275
  * + true 监听声明的 target 节点上所有字符的变化。默认值为 true,如果声明了 characterDataOldValue
6962
7276
  * + false (默认) 不生效
6963
7277
  */
6964
- characterData: undefined,
7278
+ characterData: void 0,
6965
7279
  /**
6966
7280
  * + true 记录前一个被监听的节点中发生的文本变化
6967
7281
  * + false (默认) 不生效
6968
7282
  */
6969
- characterDataOldValue: undefined,
7283
+ characterDataOldValue: void 0,
6970
7284
  },
6971
7285
  immediate: false,
6972
7286
  };
@@ -7542,7 +7856,7 @@
7542
7856
  }
7543
7857
  return new Promise((resolve) => {
7544
7858
  UtilsContext.workerSetTimeout(() => {
7545
- resolve(undefined);
7859
+ resolve(void 0);
7546
7860
  }, delayTime);
7547
7861
  });
7548
7862
  }
@@ -7556,7 +7870,7 @@
7556
7870
  return mouseEvent;
7557
7871
  }
7558
7872
  let sliderElement = typeof selector === "string"
7559
- ? this.windowApi.document.querySelector(selector)
7873
+ ? domUtils.selector(selector)
7560
7874
  : selector;
7561
7875
  if (!(sliderElement instanceof Node) ||
7562
7876
  !(sliderElement instanceof Element)) {
@@ -7766,47 +8080,15 @@
7766
8080
  }
7767
8081
  return newTargetString;
7768
8082
  }
7769
- toJSON(data, errorCallBack) {
7770
- let UtilsContext = this;
7771
- let result = {};
7772
- if (typeof data === "object") {
7773
- return data;
7774
- }
7775
- UtilsContext.tryCatch()
7776
- .config({ log: false })
7777
- .error((error) => {
7778
- UtilsContext.tryCatch()
7779
- .error(() => {
7780
- try {
7781
- result = UtilsContext.windowApi.window.eval("(" + data + ")");
7782
- }
7783
- catch (error2) {
7784
- if (typeof errorCallBack === "function") {
7785
- errorCallBack(error2);
7786
- }
7787
- }
7788
- })
7789
- .run(() => {
7790
- if (data &&
7791
- /^[\],:{}\s]*$/.test(data
7792
- .replace(/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g, "@")
7793
- .replace(/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, "]")
7794
- .replace(/(?:^|:|,)(?:\s*\[)+/g, ""))) {
7795
- result = new Function("return " + data)();
7796
- }
7797
- else {
7798
- if (typeof errorCallBack === "function") {
7799
- errorCallBack(new Error("target is not a JSON"));
7800
- }
7801
- }
7802
- });
7803
- })
7804
- .run(() => {
7805
- data = data.trim();
7806
- result = JSON.parse(data);
7807
- });
7808
- return result;
7809
- }
8083
+ /**
8084
+ * 字符串转Object对象,类似'{"test":""}' => {"test":""}
8085
+ * @param data
8086
+ * @param errorCallBack (可选)错误回调
8087
+ * @example
8088
+ * Utils.toJSON("{123:123}")
8089
+ * > {123:123}
8090
+ */
8091
+ toJSON = commonUtil.toJSON.bind(commonUtil);
7810
8092
  toSearchParamsStr(obj, addPrefix) {
7811
8093
  let UtilsContext = this;
7812
8094
  let searhParamsStr = "";
@@ -7917,7 +8199,7 @@
7917
8199
  }
7918
8200
  waitNode(...args) {
7919
8201
  // 过滤掉undefined
7920
- args = args.filter((arg) => arg !== undefined);
8202
+ args = args.filter((arg) => arg !== void 0);
7921
8203
  let UtilsContext = this;
7922
8204
  // 选择器
7923
8205
  let selector = args[0];
@@ -7972,7 +8254,7 @@
7972
8254
  if (Array.isArray(selector)) {
7973
8255
  let result = [];
7974
8256
  for (let index = 0; index < selector.length; index++) {
7975
- let node = parent.querySelector(selector[index]);
8257
+ let node = domUtils.selector(selector[index]);
7976
8258
  if (node) {
7977
8259
  result.push(node);
7978
8260
  }
@@ -7985,7 +8267,7 @@
7985
8267
  return selector();
7986
8268
  }
7987
8269
  else {
7988
- return parent.querySelector(selector);
8270
+ return domUtils.selector(selector, parent);
7989
8271
  }
7990
8272
  }
7991
8273
  return UtilsContext.wait(() => {
@@ -8006,7 +8288,7 @@
8006
8288
  }
8007
8289
  waitAnyNode(...args) {
8008
8290
  // 过滤掉undefined
8009
- args = args.filter((arg) => arg !== undefined);
8291
+ args = args.filter((arg) => arg !== void 0);
8010
8292
  let UtilsContext = this;
8011
8293
  // 选择器
8012
8294
  let selectorList = args[0];
@@ -8062,7 +8344,7 @@
8062
8344
  }
8063
8345
  waitNodeList(...args) {
8064
8346
  // 过滤掉undefined
8065
- args = args.filter((arg) => arg !== undefined);
8347
+ args = args.filter((arg) => arg !== void 0);
8066
8348
  let UtilsContext = this;
8067
8349
  // 选择器数组
8068
8350
  let selector = args[0];
@@ -8115,7 +8397,7 @@
8115
8397
  if (Array.isArray(selector)) {
8116
8398
  let result = [];
8117
8399
  for (let index = 0; index < selector.length; index++) {
8118
- let nodeList = parent.querySelectorAll(selector[index]);
8400
+ let nodeList = domUtils.selectorAll(selector[index], parent);
8119
8401
  if (nodeList.length) {
8120
8402
  result.push(nodeList);
8121
8403
  }
@@ -8125,7 +8407,7 @@
8125
8407
  }
8126
8408
  }
8127
8409
  else {
8128
- let nodeList = parent.querySelectorAll(selector);
8410
+ let nodeList = domUtils.selectorAll(selector, parent);
8129
8411
  if (nodeList.length) {
8130
8412
  return nodeList;
8131
8413
  }
@@ -8149,7 +8431,7 @@
8149
8431
  }
8150
8432
  waitAnyNodeList(...args) {
8151
8433
  // 过滤掉undefined
8152
- args = args.filter((arg) => arg !== undefined);
8434
+ args = args.filter((arg) => arg !== void 0);
8153
8435
  let UtilsContext = this;
8154
8436
  // 选择器数组
8155
8437
  let selectorList = args[0];
@@ -8434,17 +8716,7 @@
8434
8716
  * @param target 需要覆盖的对象
8435
8717
  * @param [objectThis] 覆盖的this指向,如果为传入,则默认为对象本身
8436
8718
  */
8437
- coverObjectFunctionThis(target, objectThis) {
8438
- if (typeof target !== "object" || target === null) {
8439
- throw new Error("target must be object");
8440
- }
8441
- objectThis = objectThis || target;
8442
- Object.keys(target).forEach((key) => {
8443
- if (typeof target[key] === "function") {
8444
- target[key] = target[key].bind(objectThis);
8445
- }
8446
- });
8447
- }
8719
+ coverObjectFunctionThis = commonUtil.coverObjectFunctionThis.bind(commonUtil);
8448
8720
  /**
8449
8721
  * 生成uuid
8450
8722
  * @example
@@ -8485,7 +8757,7 @@
8485
8757
  workerClearTimeout(timeId) {
8486
8758
  try {
8487
8759
  if (timeId != null) {
8488
- clearTimeout(timeId);
8760
+ clearTimeout$1(timeId);
8489
8761
  }
8490
8762
  }
8491
8763
  catch (error) {