@andrew_l/toolkit 0.0.1 → 0.0.2
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/README.md +15 -3
- package/dist/index.cjs +1027 -31
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1308 -120
- package/dist/index.d.mts +1308 -120
- package/dist/index.d.ts +1308 -120
- package/dist/index.mjs +989 -32
- package/dist/index.mjs.map +1 -1
- package/package.json +6 -1
package/dist/index.cjs
CHANGED
|
@@ -6,7 +6,6 @@ const _cloneDeepWith = require('lodash/cloneDeepWith');
|
|
|
6
6
|
const _defaultsDeep = require('lodash/defaultsDeep');
|
|
7
7
|
const _set = require('lodash/set');
|
|
8
8
|
const _unset = require('lodash/unset');
|
|
9
|
-
const lodash = require('lodash');
|
|
10
9
|
|
|
11
10
|
function _interopDefaultCompat (e) { return e && typeof e === 'object' && 'default' in e ? e.default : e; }
|
|
12
11
|
|
|
@@ -27,8 +26,21 @@ const isBigInt = (val) => typeof val === "bigint";
|
|
|
27
26
|
const isBoolean = (val) => typeof val === "boolean";
|
|
28
27
|
const isFunction = (val) => typeof val === "function";
|
|
29
28
|
const isNumber = (val) => typeof val === "number" && !isNaN(val);
|
|
29
|
+
const isInfinity = (val) => val === Infinity || val === -Infinity;
|
|
30
30
|
const isString = (val) => typeof val === "string";
|
|
31
31
|
const isObject = (val) => toString.call(val) === "[object Object]";
|
|
32
|
+
const isPlainObject = (val) => {
|
|
33
|
+
let ctor, prot;
|
|
34
|
+
if (!isObject(val)) return false;
|
|
35
|
+
ctor = val.constructor;
|
|
36
|
+
if (ctor === void 0) return true;
|
|
37
|
+
prot = ctor.prototype;
|
|
38
|
+
if (isObject(prot) === false) return false;
|
|
39
|
+
if (prot.hasOwnProperty("isPrototypeOf") === false) {
|
|
40
|
+
return false;
|
|
41
|
+
}
|
|
42
|
+
return true;
|
|
43
|
+
};
|
|
32
44
|
const isDate = (val) => val instanceof Date && !isNaN(val);
|
|
33
45
|
const noop = () => {
|
|
34
46
|
};
|
|
@@ -43,28 +55,89 @@ function isEqual(a, b) {
|
|
|
43
55
|
if (Object.is(a, b)) {
|
|
44
56
|
return true;
|
|
45
57
|
}
|
|
46
|
-
if (a
|
|
58
|
+
if (typeof a !== "object" || typeof b !== "object" || a === null || b === null) {
|
|
59
|
+
return false;
|
|
60
|
+
}
|
|
61
|
+
if (a.constructor !== b.constructor) {
|
|
62
|
+
return false;
|
|
63
|
+
}
|
|
64
|
+
if (Array.isArray(a)) {
|
|
65
|
+
const { length } = a;
|
|
66
|
+
if (length !== b.length) {
|
|
67
|
+
return false;
|
|
68
|
+
}
|
|
69
|
+
for (let i = length; i-- !== 0; ) {
|
|
70
|
+
if (!isEqual(a[i], b[i])) {
|
|
71
|
+
return false;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
return true;
|
|
75
|
+
}
|
|
76
|
+
if (a instanceof Date) {
|
|
47
77
|
return a.getTime() === b.getTime();
|
|
48
78
|
}
|
|
49
|
-
if (a instanceof RegExp
|
|
79
|
+
if (a instanceof RegExp) {
|
|
50
80
|
return a.source === b.source && a.flags === b.flags;
|
|
51
81
|
}
|
|
52
|
-
if (
|
|
53
|
-
|
|
82
|
+
if (a instanceof Set) {
|
|
83
|
+
if (a.size !== b.size) {
|
|
84
|
+
return false;
|
|
85
|
+
}
|
|
86
|
+
for (const value of a) {
|
|
87
|
+
if (!b.has(value)) {
|
|
88
|
+
return false;
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
return true;
|
|
92
|
+
}
|
|
93
|
+
if (a instanceof Map) {
|
|
94
|
+
if (a.size !== b.size) {
|
|
95
|
+
return false;
|
|
96
|
+
}
|
|
97
|
+
for (const entry of a) {
|
|
98
|
+
if (!b.has(entry[0]) || !isEqual(entry[1], b.get(entry[0]))) {
|
|
99
|
+
return false;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
return true;
|
|
103
|
+
}
|
|
104
|
+
if (a instanceof DataView) {
|
|
105
|
+
const { byteLength } = a;
|
|
106
|
+
if (byteLength !== b.byteLength) {
|
|
107
|
+
return false;
|
|
108
|
+
}
|
|
109
|
+
for (let i = byteLength; i-- !== 0; ) {
|
|
110
|
+
if (a.getUint8(i) !== b.getUint8(i)) {
|
|
111
|
+
return false;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
return true;
|
|
115
|
+
}
|
|
116
|
+
if (a instanceof ArrayBuffer && b instanceof ArrayBuffer) {
|
|
117
|
+
a = new Uint8Array(a);
|
|
118
|
+
b = new Uint8Array(b);
|
|
119
|
+
}
|
|
120
|
+
if (ArrayBuffer.isView(a) && ArrayBuffer.isView(b)) {
|
|
121
|
+
const { length } = a;
|
|
122
|
+
if (length !== b.length) {
|
|
123
|
+
return false;
|
|
124
|
+
}
|
|
125
|
+
for (let i = length; i-- !== 0; ) {
|
|
126
|
+
if (a[i] !== b[i]) {
|
|
127
|
+
return false;
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
return true;
|
|
54
131
|
}
|
|
55
132
|
const aKeys = Object.keys(a);
|
|
56
133
|
const bKeys = Object.keys(b);
|
|
57
134
|
if (aKeys.length !== bKeys.length) {
|
|
58
135
|
return false;
|
|
59
136
|
}
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
const propKey = aKeys[i];
|
|
65
|
-
const aProp = a[propKey];
|
|
66
|
-
const bProp = b[propKey];
|
|
67
|
-
if (!isEqual(aProp, bProp)) {
|
|
137
|
+
let key;
|
|
138
|
+
for (let i = aKeys.length; i-- !== 0; ) {
|
|
139
|
+
key = aKeys[i];
|
|
140
|
+
if (!Object.hasOwn(b, key) || !isEqual(a[key], b[key])) {
|
|
68
141
|
return false;
|
|
69
142
|
}
|
|
70
143
|
}
|
|
@@ -155,6 +228,35 @@ function chunkSeries(list, step = 1) {
|
|
|
155
228
|
return result;
|
|
156
229
|
}
|
|
157
230
|
|
|
231
|
+
function difference(...arrays) {
|
|
232
|
+
if (arrays.length === 0) return [];
|
|
233
|
+
if (arrays.length === 1) return [...arrays[0]];
|
|
234
|
+
const [first, ...rest] = arrays;
|
|
235
|
+
const blacklist = /* @__PURE__ */ new Set();
|
|
236
|
+
const set = new Set(first);
|
|
237
|
+
for (const items of rest) {
|
|
238
|
+
for (const item of items) {
|
|
239
|
+
if (blacklist.has(item)) continue;
|
|
240
|
+
if (set.has(item)) {
|
|
241
|
+
set.delete(item);
|
|
242
|
+
blacklist.add(item);
|
|
243
|
+
continue;
|
|
244
|
+
}
|
|
245
|
+
set.add(item);
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
return Array.from(set);
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
function intersection(...arrays) {
|
|
252
|
+
if (arrays.length === 0) return [];
|
|
253
|
+
if (arrays.length === 1) return arrays[0];
|
|
254
|
+
return arrays.reduce((acc, curr) => {
|
|
255
|
+
const set = new Set(curr);
|
|
256
|
+
return acc.filter((item) => set.has(item));
|
|
257
|
+
});
|
|
258
|
+
}
|
|
259
|
+
|
|
158
260
|
function keyBy(array, keyBy2, objectMode) {
|
|
159
261
|
const getItemKey = isFunction(keyBy2) ? keyBy2 : (item) => item?.[keyBy2];
|
|
160
262
|
if (objectMode === true) {
|
|
@@ -205,6 +307,15 @@ function orderBy(array, fields, orders) {
|
|
|
205
307
|
});
|
|
206
308
|
}
|
|
207
309
|
|
|
310
|
+
function shuffle(arr) {
|
|
311
|
+
const result = arr.slice();
|
|
312
|
+
for (let i = result.length - 1; i >= 1; i--) {
|
|
313
|
+
const j = Math.floor(Math.random() * (i + 1));
|
|
314
|
+
[result[i], result[j]] = [result[j], result[i]];
|
|
315
|
+
}
|
|
316
|
+
return result;
|
|
317
|
+
}
|
|
318
|
+
|
|
208
319
|
const sum = (values) => {
|
|
209
320
|
return values.reduce((a, b) => a + (isNumber(b) ? b : 0), 0);
|
|
210
321
|
};
|
|
@@ -216,8 +327,11 @@ function uniq(value) {
|
|
|
216
327
|
return [...new Set(value)];
|
|
217
328
|
}
|
|
218
329
|
|
|
219
|
-
function union(
|
|
220
|
-
|
|
330
|
+
function union(...arrays) {
|
|
331
|
+
if (arrays.length === 0) return [];
|
|
332
|
+
if (arrays.length === 1) return [...arrays[0]];
|
|
333
|
+
const [first, ...rest] = arrays;
|
|
334
|
+
return uniq(first.concat(...rest));
|
|
221
335
|
}
|
|
222
336
|
|
|
223
337
|
const get = _get__default;
|
|
@@ -336,6 +450,202 @@ const assert = {
|
|
|
336
450
|
string: string
|
|
337
451
|
};
|
|
338
452
|
|
|
453
|
+
class Base64Encoding {
|
|
454
|
+
alphabet;
|
|
455
|
+
padding;
|
|
456
|
+
decodeMap = /* @__PURE__ */ new Map();
|
|
457
|
+
constructor(alphabet, options) {
|
|
458
|
+
if (alphabet.length !== 64) {
|
|
459
|
+
throw new Error("Invalid alphabet");
|
|
460
|
+
}
|
|
461
|
+
this.alphabet = alphabet;
|
|
462
|
+
this.padding = options?.padding ?? "=";
|
|
463
|
+
if (this.alphabet.includes(this.padding) || this.padding.length !== 1) {
|
|
464
|
+
throw new Error("Invalid padding");
|
|
465
|
+
}
|
|
466
|
+
for (let i = 0; i < alphabet.length; i++) {
|
|
467
|
+
this.decodeMap.set(alphabet[i], i);
|
|
468
|
+
}
|
|
469
|
+
}
|
|
470
|
+
encode(data, options) {
|
|
471
|
+
let result = "";
|
|
472
|
+
let buffer = 0;
|
|
473
|
+
let shift = 0;
|
|
474
|
+
for (let i = 0; i < data.length; i++) {
|
|
475
|
+
buffer = buffer << 8 | data[i];
|
|
476
|
+
shift += 8;
|
|
477
|
+
while (shift >= 6) {
|
|
478
|
+
shift += -6;
|
|
479
|
+
result += this.alphabet[buffer >> shift & 63];
|
|
480
|
+
}
|
|
481
|
+
}
|
|
482
|
+
if (shift > 0) {
|
|
483
|
+
result += this.alphabet[buffer << 6 - shift & 63];
|
|
484
|
+
}
|
|
485
|
+
const includePadding = options?.includePadding ?? true;
|
|
486
|
+
if (includePadding) {
|
|
487
|
+
const padCount = (4 - result.length % 4) % 4;
|
|
488
|
+
for (let i = 0; i < padCount; i++) {
|
|
489
|
+
result += "=";
|
|
490
|
+
}
|
|
491
|
+
}
|
|
492
|
+
return result;
|
|
493
|
+
}
|
|
494
|
+
decode(data, options) {
|
|
495
|
+
const strict = options?.strict ?? true;
|
|
496
|
+
const chunkCount = Math.ceil(data.length / 4);
|
|
497
|
+
const result = [];
|
|
498
|
+
for (let i = 0; i < chunkCount; i++) {
|
|
499
|
+
let padCount = 0;
|
|
500
|
+
let buffer = 0;
|
|
501
|
+
for (let j = 0; j < 4; j++) {
|
|
502
|
+
const encoded = data[i * 4 + j];
|
|
503
|
+
if (encoded === "=") {
|
|
504
|
+
if (i + 1 !== chunkCount) {
|
|
505
|
+
throw new Error(`Invalid character: ${encoded}`);
|
|
506
|
+
}
|
|
507
|
+
padCount += 1;
|
|
508
|
+
continue;
|
|
509
|
+
}
|
|
510
|
+
if (encoded === void 0) {
|
|
511
|
+
if (strict) {
|
|
512
|
+
throw new Error("Invalid data");
|
|
513
|
+
}
|
|
514
|
+
padCount += 1;
|
|
515
|
+
continue;
|
|
516
|
+
}
|
|
517
|
+
const value = this.decodeMap.get(encoded) ?? null;
|
|
518
|
+
if (value === null) {
|
|
519
|
+
throw new Error(`Invalid character: ${encoded}`);
|
|
520
|
+
}
|
|
521
|
+
buffer += value << 6 * (3 - j);
|
|
522
|
+
}
|
|
523
|
+
result.push(buffer >> 16 & 255);
|
|
524
|
+
if (padCount < 2) {
|
|
525
|
+
result.push(buffer >> 8 & 255);
|
|
526
|
+
}
|
|
527
|
+
if (padCount < 1) {
|
|
528
|
+
result.push(buffer & 255);
|
|
529
|
+
}
|
|
530
|
+
}
|
|
531
|
+
return Uint8Array.from(result);
|
|
532
|
+
}
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
const base64 = new Base64Encoding(
|
|
536
|
+
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
|
|
537
|
+
);
|
|
538
|
+
const base64url = new Base64Encoding(
|
|
539
|
+
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"
|
|
540
|
+
);
|
|
541
|
+
|
|
542
|
+
function base64ToBytes(data, { encoding = "base64", strict } = {}) {
|
|
543
|
+
if (encoding === "base64") {
|
|
544
|
+
return base64.decode(data, { strict: strict ?? true });
|
|
545
|
+
} else if (encoding === "base64url") {
|
|
546
|
+
return base64url.decode(data, { strict: strict ?? false });
|
|
547
|
+
}
|
|
548
|
+
ok(false, "Invalid encoding options: " + encoding);
|
|
549
|
+
}
|
|
550
|
+
|
|
551
|
+
function bigIntBytes(value) {
|
|
552
|
+
if (value < 0n) {
|
|
553
|
+
value = value * -1n;
|
|
554
|
+
}
|
|
555
|
+
let byteLength = 1;
|
|
556
|
+
while (value > 2n ** BigInt(byteLength * 8) - 1n) {
|
|
557
|
+
byteLength++;
|
|
558
|
+
}
|
|
559
|
+
const encoded = new Uint8Array(byteLength);
|
|
560
|
+
for (let i = 0; i < encoded.byteLength; i++) {
|
|
561
|
+
encoded[i] = Number(
|
|
562
|
+
value >> BigInt((encoded.byteLength - i - 1) * 8) & 0xffn
|
|
563
|
+
);
|
|
564
|
+
}
|
|
565
|
+
return encoded;
|
|
566
|
+
}
|
|
567
|
+
|
|
568
|
+
function bigIntFromBytes(bytes) {
|
|
569
|
+
ok(bytes.byteLength > 0, "Empty Uint8Array");
|
|
570
|
+
let decoded = 0n;
|
|
571
|
+
for (let i = 0; i < bytes.byteLength; i++) {
|
|
572
|
+
decoded += BigInt(bytes[i]) << BigInt((bytes.byteLength - 1 - i) * 8);
|
|
573
|
+
}
|
|
574
|
+
return decoded;
|
|
575
|
+
}
|
|
576
|
+
|
|
577
|
+
function bytesToBase64(data, { encoding = "base64", padding } = {}) {
|
|
578
|
+
if (encoding === "base64") {
|
|
579
|
+
return base64.encode(data, { includePadding: padding ?? true });
|
|
580
|
+
} else if (encoding === "base64url") {
|
|
581
|
+
return base64url.encode(data, { includePadding: padding ?? false });
|
|
582
|
+
}
|
|
583
|
+
ok(false, "Invalid encoding options: " + encoding);
|
|
584
|
+
}
|
|
585
|
+
|
|
586
|
+
function compareBytes(a, b) {
|
|
587
|
+
if (a.byteLength !== b.byteLength) {
|
|
588
|
+
return false;
|
|
589
|
+
}
|
|
590
|
+
for (let i = 0; i < b.byteLength; i++) {
|
|
591
|
+
if (a[i] !== b[i]) {
|
|
592
|
+
return false;
|
|
593
|
+
}
|
|
594
|
+
}
|
|
595
|
+
return true;
|
|
596
|
+
}
|
|
597
|
+
|
|
598
|
+
function concatenateBytes(a, b) {
|
|
599
|
+
const result = new Uint8Array(a.byteLength + b.byteLength);
|
|
600
|
+
result.set(a);
|
|
601
|
+
result.set(b, a.byteLength);
|
|
602
|
+
return result;
|
|
603
|
+
}
|
|
604
|
+
|
|
605
|
+
function uint16ToUint8(value) {
|
|
606
|
+
const uint8Array = new Uint8Array(value.length * 2);
|
|
607
|
+
for (let i = 0; i < value.length; i++) {
|
|
608
|
+
uint8Array[i * 2] = value[i] & 255;
|
|
609
|
+
uint8Array[i * 2 + 1] = value[i] >> 8;
|
|
610
|
+
}
|
|
611
|
+
return uint8Array;
|
|
612
|
+
}
|
|
613
|
+
|
|
614
|
+
function uint32ToUint8(value) {
|
|
615
|
+
const uint8Array = new Uint8Array(value.length * 4);
|
|
616
|
+
for (let i = 0; i < value.length; i++) {
|
|
617
|
+
uint8Array[i * 4] = value[i] & 255;
|
|
618
|
+
uint8Array[i * 4 + 1] = value[i] >> 8 & 255;
|
|
619
|
+
uint8Array[i * 4 + 2] = value[i] >> 16 & 255;
|
|
620
|
+
uint8Array[i * 4 + 3] = value[i] >> 24 & 255;
|
|
621
|
+
}
|
|
622
|
+
return uint8Array;
|
|
623
|
+
}
|
|
624
|
+
|
|
625
|
+
function uint8ToUint16(value) {
|
|
626
|
+
ok(
|
|
627
|
+
value.length % 2 === 0,
|
|
628
|
+
"Uint8Array length must be even for conversion to Uint16Array"
|
|
629
|
+
);
|
|
630
|
+
const uint16Array = new Uint16Array(value.length / 2);
|
|
631
|
+
for (let i = 0; i < uint16Array.length; i++) {
|
|
632
|
+
uint16Array[i] = value[i * 2] << 8 | value[i * 2 + 1];
|
|
633
|
+
}
|
|
634
|
+
return uint16Array;
|
|
635
|
+
}
|
|
636
|
+
|
|
637
|
+
function uint8ToUint32(value) {
|
|
638
|
+
ok(
|
|
639
|
+
value.length % 4 === 0,
|
|
640
|
+
"Uint8Array length must be a multiple of 4 for conversion to Uint32Array"
|
|
641
|
+
);
|
|
642
|
+
const uint32Array = new Uint32Array(value.length / 4);
|
|
643
|
+
for (let i = 0; i < uint32Array.length; i++) {
|
|
644
|
+
uint32Array[i] = value[i * 4] << 24 | value[i * 4 + 1] << 16 | value[i * 4 + 2] << 8 | value[i * 4 + 3];
|
|
645
|
+
}
|
|
646
|
+
return uint32Array;
|
|
647
|
+
}
|
|
648
|
+
|
|
339
649
|
const def = (obj, key, value, writable = false) => {
|
|
340
650
|
Object.defineProperty(obj, key, {
|
|
341
651
|
configurable: true,
|
|
@@ -1739,18 +2049,6 @@ function percentOf(value, percent, digits) {
|
|
|
1739
2049
|
return result;
|
|
1740
2050
|
}
|
|
1741
2051
|
|
|
1742
|
-
function timestamp(fromValue = Date.now()) {
|
|
1743
|
-
if (isDate(fromValue)) {
|
|
1744
|
-
fromValue = fromValue.getTime();
|
|
1745
|
-
}
|
|
1746
|
-
return Math.floor(fromValue / 1e3);
|
|
1747
|
-
}
|
|
1748
|
-
|
|
1749
|
-
function timestampToDate(value) {
|
|
1750
|
-
if (!isNumber(value)) return null;
|
|
1751
|
-
return new Date(value * 1e3);
|
|
1752
|
-
}
|
|
1753
|
-
|
|
1754
2052
|
const rgb3Numbers = new RegExp(
|
|
1755
2053
|
`^
|
|
1756
2054
|
rgba?\\(
|
|
@@ -2054,6 +2352,664 @@ function crc32(str, seed = 0) {
|
|
|
2054
2352
|
return ~C;
|
|
2055
2353
|
}
|
|
2056
2354
|
|
|
2355
|
+
function isDateObject(value) {
|
|
2356
|
+
return has(value, ["year", "month", "date"]) && isNumber(value.year) && isNumber(value.month) && isNumber(value.date);
|
|
2357
|
+
}
|
|
2358
|
+
|
|
2359
|
+
function createDateObject(value, returnsNullWhenInvalid = false) {
|
|
2360
|
+
let result = null;
|
|
2361
|
+
let inputValue = value;
|
|
2362
|
+
if (isNumber(inputValue) || isString(inputValue)) {
|
|
2363
|
+
inputValue = new Date(inputValue);
|
|
2364
|
+
}
|
|
2365
|
+
if (isDate(inputValue)) {
|
|
2366
|
+
result = {
|
|
2367
|
+
year: inputValue.getFullYear(),
|
|
2368
|
+
month: inputValue.getMonth() + 1,
|
|
2369
|
+
date: inputValue.getDate()
|
|
2370
|
+
};
|
|
2371
|
+
} else if (isDateObject(inputValue)) {
|
|
2372
|
+
result = { ...inputValue };
|
|
2373
|
+
}
|
|
2374
|
+
ok(
|
|
2375
|
+
returnsNullWhenInvalid || !!result,
|
|
2376
|
+
`Failed to date parse: ${value}.`
|
|
2377
|
+
);
|
|
2378
|
+
return result;
|
|
2379
|
+
}
|
|
2380
|
+
|
|
2381
|
+
function isTimeObject(value) {
|
|
2382
|
+
return isPlainObject(value) && "h" in value && "m" in value && isNumber(value.h) && Number.isInteger(value.h) && isNumber(value.m) && Number.isInteger(value.m) && value.h >= 0 && value.h < 24 && value.m >= 0 && value.m < 60;
|
|
2383
|
+
}
|
|
2384
|
+
|
|
2385
|
+
function createTimeObject(value, returnsNullWhenInvalid = false) {
|
|
2386
|
+
let result = null;
|
|
2387
|
+
let inputValue = value;
|
|
2388
|
+
if (isNumber(inputValue)) {
|
|
2389
|
+
inputValue = new Date(inputValue);
|
|
2390
|
+
} else if (isString(inputValue)) {
|
|
2391
|
+
const [h, m] = inputValue.split(":").map((v) => v.trim().padStart(2, "0")).map((v) => parseInt(v));
|
|
2392
|
+
inputValue = { h, m };
|
|
2393
|
+
}
|
|
2394
|
+
if (isDate(inputValue)) {
|
|
2395
|
+
result = {
|
|
2396
|
+
h: inputValue.getHours(),
|
|
2397
|
+
m: inputValue.getMinutes()
|
|
2398
|
+
};
|
|
2399
|
+
} else if (isTimeObject(inputValue)) {
|
|
2400
|
+
result = { ...inputValue };
|
|
2401
|
+
}
|
|
2402
|
+
ok(
|
|
2403
|
+
returnsNullWhenInvalid || !!result,
|
|
2404
|
+
`Failed to time parse: ${value}.`
|
|
2405
|
+
);
|
|
2406
|
+
return result;
|
|
2407
|
+
}
|
|
2408
|
+
|
|
2409
|
+
const UNIT_TO_MS = {
|
|
2410
|
+
ms: 1,
|
|
2411
|
+
s: 1e3,
|
|
2412
|
+
m: 1e3 * 60,
|
|
2413
|
+
h: 1e3 * 60 * 60,
|
|
2414
|
+
d: 1e3 * 60 * 60 * 24,
|
|
2415
|
+
w: 1e3 * 60 * 60 * 24 * 7
|
|
2416
|
+
};
|
|
2417
|
+
class TimeSpan {
|
|
2418
|
+
constructor(value, unit) {
|
|
2419
|
+
this.value = value;
|
|
2420
|
+
this.unit = unit;
|
|
2421
|
+
}
|
|
2422
|
+
/**
|
|
2423
|
+
* The numeric value of the time span
|
|
2424
|
+
*/
|
|
2425
|
+
value;
|
|
2426
|
+
/**
|
|
2427
|
+
* The unit of the time span.
|
|
2428
|
+
*/
|
|
2429
|
+
unit;
|
|
2430
|
+
/**
|
|
2431
|
+
* Converts the time span to milliseconds.
|
|
2432
|
+
*
|
|
2433
|
+
* @returns {number} The equivalent time span in milliseconds.
|
|
2434
|
+
* @example
|
|
2435
|
+
* const ts = new TimeSpan(2, 'h');
|
|
2436
|
+
* ts.milliseconds(); // Returns 7200000
|
|
2437
|
+
*/
|
|
2438
|
+
milliseconds() {
|
|
2439
|
+
const multiplier = UNIT_TO_MS[this.unit];
|
|
2440
|
+
return this.value * multiplier;
|
|
2441
|
+
}
|
|
2442
|
+
/**
|
|
2443
|
+
* Converts the time span to seconds.
|
|
2444
|
+
*
|
|
2445
|
+
* @returns {number} The equivalent time span in seconds.
|
|
2446
|
+
* @example
|
|
2447
|
+
* const ts = new TimeSpan(2, 'm');
|
|
2448
|
+
* ts.seconds(); // Returns 120
|
|
2449
|
+
*/
|
|
2450
|
+
seconds() {
|
|
2451
|
+
return this.milliseconds() / UNIT_TO_MS.s;
|
|
2452
|
+
}
|
|
2453
|
+
/**
|
|
2454
|
+
* Converts the time span to minutes.
|
|
2455
|
+
*
|
|
2456
|
+
* @returns {number} The equivalent time span in minutes.
|
|
2457
|
+
* @example
|
|
2458
|
+
* const ts = new TimeSpan(120, 's');
|
|
2459
|
+
* ts.minutes(); // Returns 2
|
|
2460
|
+
*/
|
|
2461
|
+
minutes() {
|
|
2462
|
+
return this.milliseconds() / UNIT_TO_MS.m;
|
|
2463
|
+
}
|
|
2464
|
+
/**
|
|
2465
|
+
* Converts the time span to hours.
|
|
2466
|
+
*
|
|
2467
|
+
* @returns {number} The equivalent time span in hours.
|
|
2468
|
+
* @example
|
|
2469
|
+
* const ts = new TimeSpan(120, 'm');
|
|
2470
|
+
* ts.hours(); // Returns 2
|
|
2471
|
+
*/
|
|
2472
|
+
hours() {
|
|
2473
|
+
return this.milliseconds() / UNIT_TO_MS.h;
|
|
2474
|
+
}
|
|
2475
|
+
/**
|
|
2476
|
+
* Converts the time span to days.
|
|
2477
|
+
*
|
|
2478
|
+
* @returns {number} The equivalent time span in days.
|
|
2479
|
+
* @example
|
|
2480
|
+
* const ts = new TimeSpan(48, 'h');
|
|
2481
|
+
* ts.days(); // Returns 2
|
|
2482
|
+
*/
|
|
2483
|
+
days() {
|
|
2484
|
+
return this.milliseconds() / UNIT_TO_MS.d;
|
|
2485
|
+
}
|
|
2486
|
+
/**
|
|
2487
|
+
* Converts the time span to weeks.
|
|
2488
|
+
*
|
|
2489
|
+
* @returns {number} The equivalent time span in weeks.
|
|
2490
|
+
* @example
|
|
2491
|
+
* const ts = new TimeSpan(14, 'd');
|
|
2492
|
+
* ts.weeks(); // Returns 2
|
|
2493
|
+
*/
|
|
2494
|
+
weeks() {
|
|
2495
|
+
return this.milliseconds() / UNIT_TO_MS.w;
|
|
2496
|
+
}
|
|
2497
|
+
/**
|
|
2498
|
+
* Adds a specified value and unit to the current time span.
|
|
2499
|
+
*
|
|
2500
|
+
* Returns new instance.
|
|
2501
|
+
*
|
|
2502
|
+
* @param {number} value - The value to add.
|
|
2503
|
+
* @param {TimeSpanUnit} [unit='ms'] - The unit of the value to add (default is milliseconds).
|
|
2504
|
+
* @returns {TimeSpan} A new TimeSpan instance with the added value.
|
|
2505
|
+
* @example
|
|
2506
|
+
* const ts = new TimeSpan(1, 'h');
|
|
2507
|
+
* ts.add(30, 'm'); // Represents 1.5 hours
|
|
2508
|
+
*/
|
|
2509
|
+
add(value, unit = "ms") {
|
|
2510
|
+
const multiplier = UNIT_TO_MS[unit];
|
|
2511
|
+
return new TimeSpan(this.milliseconds() + value * multiplier, "ms");
|
|
2512
|
+
}
|
|
2513
|
+
/**
|
|
2514
|
+
* Subtracts a specified value and unit from the current time span.
|
|
2515
|
+
*
|
|
2516
|
+
* Returns new instance.
|
|
2517
|
+
*
|
|
2518
|
+
* @param {number} value - The value to subtract.
|
|
2519
|
+
* @param {TimeSpanUnit} [unit='ms'] - The unit of the value to subtract (default is milliseconds).
|
|
2520
|
+
* @returns {TimeSpan} A new TimeSpan instance with the subtracted value.
|
|
2521
|
+
* @example
|
|
2522
|
+
* const ts = new TimeSpan(1, 'h');
|
|
2523
|
+
* ts.subtract(30, 'm'); // Represents 30 minutes less than 1 hour
|
|
2524
|
+
*/
|
|
2525
|
+
subtract(value, unit = "ms") {
|
|
2526
|
+
const multiplier = UNIT_TO_MS[unit];
|
|
2527
|
+
return new TimeSpan(this.milliseconds() - value * multiplier, "ms");
|
|
2528
|
+
}
|
|
2529
|
+
}
|
|
2530
|
+
|
|
2531
|
+
function createTimeSpan(value, unit = "ms") {
|
|
2532
|
+
return new TimeSpan(value, unit);
|
|
2533
|
+
}
|
|
2534
|
+
|
|
2535
|
+
function timestampMs(fromValue = Date.now()) {
|
|
2536
|
+
if (isDate(fromValue)) {
|
|
2537
|
+
fromValue = fromValue.getTime();
|
|
2538
|
+
} else if (isString(fromValue)) {
|
|
2539
|
+
const dt = new Date(fromValue);
|
|
2540
|
+
fromValue = isDate(dt) ? dt.getTime() : 0;
|
|
2541
|
+
}
|
|
2542
|
+
return isNumber(fromValue) ? fromValue : 0;
|
|
2543
|
+
}
|
|
2544
|
+
|
|
2545
|
+
function dateInDays(days, fromValue = Date.now()) {
|
|
2546
|
+
return new Date(timestampMs(fromValue) + days * 60 * 60 * 24 * 1e3);
|
|
2547
|
+
}
|
|
2548
|
+
|
|
2549
|
+
function dateInSeconds(seconds, fromValue = Date.now()) {
|
|
2550
|
+
return new Date(timestampMs(fromValue) + seconds * 1e3);
|
|
2551
|
+
}
|
|
2552
|
+
|
|
2553
|
+
function getRandomTime(startTime = { h: 0, m: 0 }, endTime = { h: 23, m: 59 }) {
|
|
2554
|
+
const h = getRandomInt(startTime.h, endTime.h);
|
|
2555
|
+
if (startTime.h === endTime.h) {
|
|
2556
|
+
return { h, m: getRandomInt(startTime.m, endTime.m) };
|
|
2557
|
+
}
|
|
2558
|
+
if (h === startTime.h) {
|
|
2559
|
+
return { h, m: getRandomInt(startTime.m, 59) };
|
|
2560
|
+
}
|
|
2561
|
+
if (h === endTime.h) {
|
|
2562
|
+
return { h, m: getRandomInt(0, endTime.m) };
|
|
2563
|
+
}
|
|
2564
|
+
return { h, m: getRandomInt(0, 59) };
|
|
2565
|
+
}
|
|
2566
|
+
|
|
2567
|
+
function hmToSeconds(hm) {
|
|
2568
|
+
hm = Number(hm);
|
|
2569
|
+
number$1(hm, "expected number value");
|
|
2570
|
+
const h = Math.floor(hm);
|
|
2571
|
+
const m = round2digits(hm - h) * 100;
|
|
2572
|
+
return h * 3600 + m * 60;
|
|
2573
|
+
}
|
|
2574
|
+
|
|
2575
|
+
function isTimeString(value) {
|
|
2576
|
+
if (!isString(value)) return false;
|
|
2577
|
+
const parts = value.split(":").map(Number);
|
|
2578
|
+
if (parts.length !== 2) return false;
|
|
2579
|
+
const [h, m] = parts;
|
|
2580
|
+
return h >= 0 && h < 24 && m >= 0 && m < 60;
|
|
2581
|
+
}
|
|
2582
|
+
|
|
2583
|
+
function isTimeValue(value) {
|
|
2584
|
+
return isTimeString(value) || isTimeObject(value);
|
|
2585
|
+
}
|
|
2586
|
+
|
|
2587
|
+
function isValidWeekDay(value) {
|
|
2588
|
+
return isNumber(value) && Number.isInteger(value) && value >= 1 && value <= 7;
|
|
2589
|
+
}
|
|
2590
|
+
|
|
2591
|
+
function secondsToHm(seconds) {
|
|
2592
|
+
const value = Number(seconds);
|
|
2593
|
+
number$1(value, "expected number value");
|
|
2594
|
+
const h = Math.floor(value / 3600);
|
|
2595
|
+
const m = Math.floor(value % 3600 / 60);
|
|
2596
|
+
return round2digits(h + m / 100, 2);
|
|
2597
|
+
}
|
|
2598
|
+
|
|
2599
|
+
function timeFromMinutes(value, returnsNullWhenInvalid = false) {
|
|
2600
|
+
if (!isNumber(value)) {
|
|
2601
|
+
ok(
|
|
2602
|
+
returnsNullWhenInvalid,
|
|
2603
|
+
"Failed to time parse from minutes: " + value
|
|
2604
|
+
);
|
|
2605
|
+
return null;
|
|
2606
|
+
}
|
|
2607
|
+
if (value === 0) {
|
|
2608
|
+
return { h: 0, m: 0 };
|
|
2609
|
+
}
|
|
2610
|
+
value = value % 1440;
|
|
2611
|
+
if (value < 0) {
|
|
2612
|
+
value += 1440;
|
|
2613
|
+
}
|
|
2614
|
+
const h = Math.floor(value / 60);
|
|
2615
|
+
const m = value % 60;
|
|
2616
|
+
return { h, m };
|
|
2617
|
+
}
|
|
2618
|
+
|
|
2619
|
+
function timestamp(fromValue = Date.now()) {
|
|
2620
|
+
if (isDate(fromValue)) {
|
|
2621
|
+
fromValue = fromValue.getTime();
|
|
2622
|
+
}
|
|
2623
|
+
return Math.floor(fromValue / 1e3);
|
|
2624
|
+
}
|
|
2625
|
+
|
|
2626
|
+
function timestampToDate(value) {
|
|
2627
|
+
if (!isNumber(value)) return null;
|
|
2628
|
+
return new Date(value * 1e3);
|
|
2629
|
+
}
|
|
2630
|
+
|
|
2631
|
+
function timeStringify(value, returnsNullWhenInvalid = false) {
|
|
2632
|
+
const timeObject = createTimeObject(value, true);
|
|
2633
|
+
if (!timeObject) {
|
|
2634
|
+
ok(
|
|
2635
|
+
returnsNullWhenInvalid,
|
|
2636
|
+
"Failed to stringify time from: " + JSON.stringify(value)
|
|
2637
|
+
);
|
|
2638
|
+
return null;
|
|
2639
|
+
}
|
|
2640
|
+
let { h, m } = timeObject;
|
|
2641
|
+
const hStr = Math.ceil(h).toString().padStart(2, "0").slice(-2);
|
|
2642
|
+
const mStr = Math.ceil(m).toString().padStart(2, "0").slice(-2);
|
|
2643
|
+
return `${hStr}:${mStr}`;
|
|
2644
|
+
}
|
|
2645
|
+
|
|
2646
|
+
function timeToMinutes(value) {
|
|
2647
|
+
const time = createTimeObject(value);
|
|
2648
|
+
return time.h * 60 + time.m;
|
|
2649
|
+
}
|
|
2650
|
+
|
|
2651
|
+
function weeksInYear(year) {
|
|
2652
|
+
const target = new Date(Date.UTC(year + 1, 0, 1));
|
|
2653
|
+
const dayNumber = target.getDay();
|
|
2654
|
+
return dayNumber < 4 ? 52 : 53;
|
|
2655
|
+
}
|
|
2656
|
+
|
|
2657
|
+
const DateType = {
|
|
2658
|
+
placeholder: "$date",
|
|
2659
|
+
encode: (value) => {
|
|
2660
|
+
if (value instanceof Date) {
|
|
2661
|
+
return value.getTime();
|
|
2662
|
+
}
|
|
2663
|
+
},
|
|
2664
|
+
decode(value) {
|
|
2665
|
+
return new Date(value);
|
|
2666
|
+
}
|
|
2667
|
+
};
|
|
2668
|
+
const BinaryType = {
|
|
2669
|
+
placeholder: "$binary",
|
|
2670
|
+
encode: (value) => {
|
|
2671
|
+
if (value instanceof Uint8Array) {
|
|
2672
|
+
return base64.encode(value, { includePadding: true });
|
|
2673
|
+
} else if (value instanceof Uint16Array) {
|
|
2674
|
+
return {
|
|
2675
|
+
value: base64.encode(uint16ToUint8(value), { includePadding: true }),
|
|
2676
|
+
bit: 16
|
|
2677
|
+
};
|
|
2678
|
+
} else if (value instanceof Uint32Array) {
|
|
2679
|
+
return {
|
|
2680
|
+
value: base64.encode(uint32ToUint8(value), { includePadding: true }),
|
|
2681
|
+
bit: 32
|
|
2682
|
+
};
|
|
2683
|
+
}
|
|
2684
|
+
},
|
|
2685
|
+
decode(value) {
|
|
2686
|
+
if (typeof value === "string") {
|
|
2687
|
+
return base64.decode(value, { strict: true });
|
|
2688
|
+
} else if (value.bit === 16) {
|
|
2689
|
+
return uint8ToUint16(base64.decode(value.value, { strict: true }));
|
|
2690
|
+
} else if (value.bit === 32) {
|
|
2691
|
+
return uint8ToUint32(base64.decode(value.value, { strict: true }));
|
|
2692
|
+
}
|
|
2693
|
+
throw new Error("Unexpected $binary bit value: " + value.bit);
|
|
2694
|
+
}
|
|
2695
|
+
};
|
|
2696
|
+
const BigIntType = {
|
|
2697
|
+
placeholder: "$bigint",
|
|
2698
|
+
encode: (value) => {
|
|
2699
|
+
if (typeof value === "bigint") {
|
|
2700
|
+
return base64.encode(bigIntBytes(value), { includePadding: false });
|
|
2701
|
+
}
|
|
2702
|
+
},
|
|
2703
|
+
decode(value) {
|
|
2704
|
+
return bigIntFromBytes(base64.decode(value, { strict: false }));
|
|
2705
|
+
}
|
|
2706
|
+
};
|
|
2707
|
+
const MapType = {
|
|
2708
|
+
placeholder: "$map",
|
|
2709
|
+
encode: (value, encode) => {
|
|
2710
|
+
if (value instanceof Map) {
|
|
2711
|
+
return encode(Array.from(value.entries()));
|
|
2712
|
+
}
|
|
2713
|
+
},
|
|
2714
|
+
decode(value) {
|
|
2715
|
+
return new Map(value);
|
|
2716
|
+
}
|
|
2717
|
+
};
|
|
2718
|
+
const SetType = {
|
|
2719
|
+
placeholder: "$set",
|
|
2720
|
+
encode: (value, encode) => {
|
|
2721
|
+
if (value instanceof Set) {
|
|
2722
|
+
return encode(Array.from(value.values()));
|
|
2723
|
+
}
|
|
2724
|
+
},
|
|
2725
|
+
decode(value) {
|
|
2726
|
+
return new Set(value);
|
|
2727
|
+
}
|
|
2728
|
+
};
|
|
2729
|
+
const RegexType = {
|
|
2730
|
+
placeholder: "$regex",
|
|
2731
|
+
encode: (value, encode) => {
|
|
2732
|
+
if (value instanceof RegExp) {
|
|
2733
|
+
const regStr = value.toString();
|
|
2734
|
+
const patternStart = regStr.lastIndexOf("/");
|
|
2735
|
+
return {
|
|
2736
|
+
pattern: value.toString().slice(1, patternStart),
|
|
2737
|
+
flags: regStr.slice(patternStart + 1)
|
|
2738
|
+
};
|
|
2739
|
+
}
|
|
2740
|
+
},
|
|
2741
|
+
decode(value) {
|
|
2742
|
+
return new RegExp(value.pattern, value.flags);
|
|
2743
|
+
}
|
|
2744
|
+
};
|
|
2745
|
+
const InfinityType = {
|
|
2746
|
+
placeholder: "$inf",
|
|
2747
|
+
encode: (value, encode) => {
|
|
2748
|
+
if (value === Infinity) {
|
|
2749
|
+
return 1;
|
|
2750
|
+
} else if (value === -Infinity) {
|
|
2751
|
+
return -1;
|
|
2752
|
+
}
|
|
2753
|
+
},
|
|
2754
|
+
decode(value) {
|
|
2755
|
+
if (value === 1) return Infinity;
|
|
2756
|
+
if (value === -1) return -Infinity;
|
|
2757
|
+
throw new Error("Unexpected $inf value: " + value);
|
|
2758
|
+
}
|
|
2759
|
+
};
|
|
2760
|
+
|
|
2761
|
+
class EJSON {
|
|
2762
|
+
/** @internal */
|
|
2763
|
+
typeHandlers = /* @__PURE__ */ new Map();
|
|
2764
|
+
/** @internal */
|
|
2765
|
+
replacerReady;
|
|
2766
|
+
/** @internal */
|
|
2767
|
+
encode;
|
|
2768
|
+
/** @internal */
|
|
2769
|
+
reviewerReady;
|
|
2770
|
+
/** @internal */
|
|
2771
|
+
pure = true;
|
|
2772
|
+
_vendorName = null;
|
|
2773
|
+
/**
|
|
2774
|
+
* MIME type based on the provided vendor name or defaults to 'application/json'.
|
|
2775
|
+
*/
|
|
2776
|
+
mimetype = "application/json";
|
|
2777
|
+
Type = {
|
|
2778
|
+
Date: DateType,
|
|
2779
|
+
Map: MapType,
|
|
2780
|
+
Set: SetType,
|
|
2781
|
+
RegExp: RegexType,
|
|
2782
|
+
Infinity: InfinityType,
|
|
2783
|
+
BigInt: BigIntType,
|
|
2784
|
+
Binary: BinaryType
|
|
2785
|
+
};
|
|
2786
|
+
constructor() {
|
|
2787
|
+
this.replacerReady = this._replacer.bind(this);
|
|
2788
|
+
this.reviewerReady = this._reviewer.bind(this);
|
|
2789
|
+
this.encode = (value) => {
|
|
2790
|
+
return deepCloneWith(value, this.replacerReady);
|
|
2791
|
+
};
|
|
2792
|
+
}
|
|
2793
|
+
/**
|
|
2794
|
+
* The vendor name used for the custom MIME type definition.
|
|
2795
|
+
* If null, defaults to 'application/json'.
|
|
2796
|
+
*/
|
|
2797
|
+
get vendorName() {
|
|
2798
|
+
return this._vendorName;
|
|
2799
|
+
}
|
|
2800
|
+
set vendorName(value) {
|
|
2801
|
+
this._vendorName = value;
|
|
2802
|
+
if (!value) {
|
|
2803
|
+
this.mimetype = "application/json";
|
|
2804
|
+
} else {
|
|
2805
|
+
const vendorName = value.split(" ").map((v) => v.toLowerCase()).join(".").replace(/\.\.+/g, ".").replace(/\.$/, "");
|
|
2806
|
+
this.mimetype = `application/vnd.${vendorName}+json`;
|
|
2807
|
+
}
|
|
2808
|
+
}
|
|
2809
|
+
/**
|
|
2810
|
+
* Adds a custom type handler for encoding/decoding logic.
|
|
2811
|
+
* Ensures type placeholders are unique and adhere to conventions.
|
|
2812
|
+
*/
|
|
2813
|
+
addType(type) {
|
|
2814
|
+
ok(
|
|
2815
|
+
!this.typeHandlers.has(type.placeholder),
|
|
2816
|
+
`type with ${type.placeholder} already taken.`
|
|
2817
|
+
);
|
|
2818
|
+
ok(
|
|
2819
|
+
type.placeholder.startsWith("$"),
|
|
2820
|
+
"type placeholder must starts with $ symbol."
|
|
2821
|
+
);
|
|
2822
|
+
this.pure = false;
|
|
2823
|
+
this.typeHandlers.set(type.placeholder, type);
|
|
2824
|
+
return this;
|
|
2825
|
+
}
|
|
2826
|
+
/**
|
|
2827
|
+
* Stringifies a JavaScript value using custom encoding logic.
|
|
2828
|
+
* @param {any} value - The value to encode and stringify.
|
|
2829
|
+
* @param {string | number} [space] - Optional space for pretty-printing.
|
|
2830
|
+
* @returns {string} - The JSON stringified value.
|
|
2831
|
+
*/
|
|
2832
|
+
stringify(value, space) {
|
|
2833
|
+
if (this.pure) {
|
|
2834
|
+
return JSON.stringify(value, void 0, space);
|
|
2835
|
+
}
|
|
2836
|
+
return JSON.stringify(this.encode(value), void 0, space);
|
|
2837
|
+
}
|
|
2838
|
+
/**
|
|
2839
|
+
* Parses a JSON string using custom decoding logic.
|
|
2840
|
+
* @param {string} value - The JSON string to parse.
|
|
2841
|
+
* @returns {any} - The decoded JavaScript object.
|
|
2842
|
+
*/
|
|
2843
|
+
parse(value) {
|
|
2844
|
+
if (this.pure) {
|
|
2845
|
+
return JSON.parse(value);
|
|
2846
|
+
}
|
|
2847
|
+
return JSON.parse(value, this.reviewerReady);
|
|
2848
|
+
}
|
|
2849
|
+
/** @internal */
|
|
2850
|
+
_replacer(value, key) {
|
|
2851
|
+
if (isPlainObject(value)) return;
|
|
2852
|
+
if (Array.isArray(value)) return;
|
|
2853
|
+
if (!isInfinity(value) && !isBigInt(value)) {
|
|
2854
|
+
if (isPrimitive(value)) return;
|
|
2855
|
+
}
|
|
2856
|
+
for (const type of this.typeHandlers.values()) {
|
|
2857
|
+
const res = type.encode(value, this.encode);
|
|
2858
|
+
if (res !== void 0) {
|
|
2859
|
+
return type.encodeInline ? res : { [type.placeholder]: res };
|
|
2860
|
+
}
|
|
2861
|
+
}
|
|
2862
|
+
return value;
|
|
2863
|
+
}
|
|
2864
|
+
/** @internal */
|
|
2865
|
+
_reviewer(_, value) {
|
|
2866
|
+
const key = firstKey(value);
|
|
2867
|
+
if (!key || key[0] !== "$") return value;
|
|
2868
|
+
const type = this.typeHandlers.get(key);
|
|
2869
|
+
if (type) {
|
|
2870
|
+
return type.decode(value[key]);
|
|
2871
|
+
}
|
|
2872
|
+
return value;
|
|
2873
|
+
}
|
|
2874
|
+
}
|
|
2875
|
+
function firstKey(value) {
|
|
2876
|
+
if (!isObject(value)) return null;
|
|
2877
|
+
for (const key in value) {
|
|
2878
|
+
return key;
|
|
2879
|
+
}
|
|
2880
|
+
return null;
|
|
2881
|
+
}
|
|
2882
|
+
|
|
2883
|
+
function createEJSON(withBasicTypes = false) {
|
|
2884
|
+
const ejson = new EJSON();
|
|
2885
|
+
if (withBasicTypes) {
|
|
2886
|
+
ejson.addType(MapType);
|
|
2887
|
+
ejson.addType(SetType);
|
|
2888
|
+
ejson.addType(DateType);
|
|
2889
|
+
ejson.addType(InfinityType);
|
|
2890
|
+
ejson.addType(BigIntType);
|
|
2891
|
+
ejson.addType(BinaryType);
|
|
2892
|
+
ejson.addType(RegexType);
|
|
2893
|
+
}
|
|
2894
|
+
return ejson;
|
|
2895
|
+
}
|
|
2896
|
+
|
|
2897
|
+
class EJSONStream extends TransformStream {
|
|
2898
|
+
ejson;
|
|
2899
|
+
constructor({ ejson, cl, op, sep, onFlush, onStart }) {
|
|
2900
|
+
let firstChunk = true;
|
|
2901
|
+
super({
|
|
2902
|
+
async start(controller) {
|
|
2903
|
+
if (onStart) {
|
|
2904
|
+
await onStart(controller);
|
|
2905
|
+
}
|
|
2906
|
+
controller.enqueue(op);
|
|
2907
|
+
},
|
|
2908
|
+
transform(chunk, controller) {
|
|
2909
|
+
const jsonString = ejson.stringify(chunk);
|
|
2910
|
+
if (firstChunk) {
|
|
2911
|
+
firstChunk = false;
|
|
2912
|
+
} else {
|
|
2913
|
+
controller.enqueue(sep);
|
|
2914
|
+
}
|
|
2915
|
+
controller.enqueue(jsonString);
|
|
2916
|
+
},
|
|
2917
|
+
flush(controller) {
|
|
2918
|
+
controller.enqueue(cl);
|
|
2919
|
+
if (onFlush) {
|
|
2920
|
+
return onFlush(controller);
|
|
2921
|
+
}
|
|
2922
|
+
}
|
|
2923
|
+
});
|
|
2924
|
+
this.ejson = ejson;
|
|
2925
|
+
}
|
|
2926
|
+
/**
|
|
2927
|
+
* The vendor name used for the custom MIME type definition.
|
|
2928
|
+
* If null, defaults to 'application/json'.
|
|
2929
|
+
*/
|
|
2930
|
+
get vendorName() {
|
|
2931
|
+
return this.ejson.vendorName;
|
|
2932
|
+
}
|
|
2933
|
+
/**
|
|
2934
|
+
* MIME type based on the provided vendor name or defaults to 'application/json'.
|
|
2935
|
+
*/
|
|
2936
|
+
get mimetype() {
|
|
2937
|
+
return this.ejson.mimetype;
|
|
2938
|
+
}
|
|
2939
|
+
}
|
|
2940
|
+
|
|
2941
|
+
const instance = createEJSON(true);
|
|
2942
|
+
|
|
2943
|
+
function createEJSONStream(options = {}) {
|
|
2944
|
+
if (options.resultKey || options.append || options.prepend) {
|
|
2945
|
+
return createEJSONStreamPayload(options);
|
|
2946
|
+
}
|
|
2947
|
+
return new EJSONStream(getOptions(options));
|
|
2948
|
+
}
|
|
2949
|
+
function createEJSONStreamPayload(options) {
|
|
2950
|
+
let { cl, ejson, op, sep } = getOptions(options);
|
|
2951
|
+
const { append, prepend, resultKey } = options;
|
|
2952
|
+
notEmptyString(resultKey, "resultKey required.");
|
|
2953
|
+
const stream = new EJSONStream({
|
|
2954
|
+
ejson,
|
|
2955
|
+
cl,
|
|
2956
|
+
op,
|
|
2957
|
+
sep,
|
|
2958
|
+
async onStart(controller) {
|
|
2959
|
+
if (!prepend) {
|
|
2960
|
+
controller.enqueue(`{"${resultKey}":`);
|
|
2961
|
+
return;
|
|
2962
|
+
}
|
|
2963
|
+
const data = await prepend();
|
|
2964
|
+
if (data === null || data === void 0) {
|
|
2965
|
+
controller.enqueue(`{"${resultKey}":`);
|
|
2966
|
+
return;
|
|
2967
|
+
}
|
|
2968
|
+
ok(
|
|
2969
|
+
isPlainObject(data),
|
|
2970
|
+
"prepend result expected to be plain object"
|
|
2971
|
+
);
|
|
2972
|
+
const dataPart = instance.stringify(data).slice(0, -1);
|
|
2973
|
+
if (dataPart === "{") {
|
|
2974
|
+
controller.enqueue(`{"${resultKey}":`);
|
|
2975
|
+
return;
|
|
2976
|
+
}
|
|
2977
|
+
controller.enqueue(`${dataPart}${sep}"${resultKey}":`);
|
|
2978
|
+
},
|
|
2979
|
+
async onFlush(controller) {
|
|
2980
|
+
if (!append) {
|
|
2981
|
+
controller.enqueue("}");
|
|
2982
|
+
return;
|
|
2983
|
+
}
|
|
2984
|
+
const data = await append();
|
|
2985
|
+
if (data === null || data === void 0) {
|
|
2986
|
+
controller.enqueue("}");
|
|
2987
|
+
return;
|
|
2988
|
+
}
|
|
2989
|
+
ok(
|
|
2990
|
+
isPlainObject(data),
|
|
2991
|
+
"prepend result expected to be plain object"
|
|
2992
|
+
);
|
|
2993
|
+
const dataPart = instance.stringify(data).slice(1);
|
|
2994
|
+
if (dataPart === "}") {
|
|
2995
|
+
controller.enqueue(`}`);
|
|
2996
|
+
return;
|
|
2997
|
+
}
|
|
2998
|
+
controller.enqueue(`${sep}${dataPart}`);
|
|
2999
|
+
}
|
|
3000
|
+
});
|
|
3001
|
+
return stream;
|
|
3002
|
+
}
|
|
3003
|
+
function getOptions(options) {
|
|
3004
|
+
const { ejson = instance, cl = "]", op = "[", sep = "," } = options;
|
|
3005
|
+
return {
|
|
3006
|
+
cl,
|
|
3007
|
+
ejson,
|
|
3008
|
+
op,
|
|
3009
|
+
sep
|
|
3010
|
+
};
|
|
3011
|
+
}
|
|
3012
|
+
|
|
2057
3013
|
const env = (() => {
|
|
2058
3014
|
if (globalThis?.process) {
|
|
2059
3015
|
return createEnvParser(process.env);
|
|
@@ -2086,7 +3042,7 @@ function createEnvParser(targetObject) {
|
|
|
2086
3042
|
return parseDecimal(targetObject[key], dights) ?? defaultValue;
|
|
2087
3043
|
},
|
|
2088
3044
|
string(key, defaultValue = "") {
|
|
2089
|
-
return targetObject[key]
|
|
3045
|
+
return targetObject[key] ?? defaultValue;
|
|
2090
3046
|
},
|
|
2091
3047
|
list(key, type, defaultValue = []) {
|
|
2092
3048
|
if (!(key in targetObject)) {
|
|
@@ -2783,9 +3739,9 @@ function typeOf(value) {
|
|
|
2783
3739
|
if (value === null) return "null";
|
|
2784
3740
|
if (Array.isArray(value)) return "array";
|
|
2785
3741
|
if (isSet(value)) return "set";
|
|
2786
|
-
if (
|
|
3742
|
+
if (isWeakSet(value)) return "weakset";
|
|
2787
3743
|
if (isMap(value)) return "map";
|
|
2788
|
-
if (
|
|
3744
|
+
if (isWeakMap(value)) return "weakmap";
|
|
2789
3745
|
if (isDate(value)) return "date";
|
|
2790
3746
|
if (isObject(value)) return "object";
|
|
2791
3747
|
return "unknown";
|
|
@@ -2995,10 +3951,11 @@ function parseValue(value, asType) {
|
|
|
2995
3951
|
return void 0;
|
|
2996
3952
|
}
|
|
2997
3953
|
|
|
3954
|
+
const noopShouldRetryBasedOnError = () => true;
|
|
2998
3955
|
function retryOnError({
|
|
2999
3956
|
beforeRetryCallback,
|
|
3957
|
+
shouldRetryBasedOnError = noopShouldRetryBasedOnError,
|
|
3000
3958
|
maxRetriesNumber,
|
|
3001
|
-
shouldRetryBasedOnError,
|
|
3002
3959
|
delayFactor = 0,
|
|
3003
3960
|
delayMaxMs = 1e3,
|
|
3004
3961
|
delayMinMs = 100
|
|
@@ -3279,6 +4236,9 @@ exports.AsyncIterableQueue = AsyncIterableQueue;
|
|
|
3279
4236
|
exports.BrowserAssertionError = BrowserAssertionError;
|
|
3280
4237
|
exports.CancellablePromise = CancellablePromise;
|
|
3281
4238
|
exports.ColorParser = ColorParser;
|
|
4239
|
+
exports.EJSON = instance;
|
|
4240
|
+
exports.EJSONStream = EJSONStream;
|
|
4241
|
+
exports.FindMean = FindMean;
|
|
3282
4242
|
exports.FixedMap = FixedMap;
|
|
3283
4243
|
exports.FixedWeakMap = FixedWeakMap;
|
|
3284
4244
|
exports.LruCache = LruCache;
|
|
@@ -3286,6 +4246,7 @@ exports.Queue = Queue;
|
|
|
3286
4246
|
exports.SimpleEventEmitter = SimpleEventEmitter;
|
|
3287
4247
|
exports.TWEMOJI_REGEX = TWEMOJI_REGEX;
|
|
3288
4248
|
exports.TimeBucket = TimeBucket;
|
|
4249
|
+
exports.TimeSpan = TimeSpan;
|
|
3289
4250
|
exports.alpha = alpha;
|
|
3290
4251
|
exports.arrayable = arrayable;
|
|
3291
4252
|
exports.assert = assert;
|
|
@@ -3294,8 +4255,12 @@ exports.asyncFind = asyncFind;
|
|
|
3294
4255
|
exports.asyncForEach = asyncForEach;
|
|
3295
4256
|
exports.asyncMap = asyncMap;
|
|
3296
4257
|
exports.avg = avg;
|
|
4258
|
+
exports.base64ToBytes = base64ToBytes;
|
|
4259
|
+
exports.bigIntBytes = bigIntBytes;
|
|
4260
|
+
exports.bigIntFromBytes = bigIntFromBytes;
|
|
3297
4261
|
exports.blendColors = blendColors;
|
|
3298
4262
|
exports.buildCssColor = buildCssColor;
|
|
4263
|
+
exports.bytesToBase64 = bytesToBase64;
|
|
3299
4264
|
exports.cache = cache;
|
|
3300
4265
|
exports.cacheBucket = cacheBucket;
|
|
3301
4266
|
exports.cacheFixed = cacheFixed;
|
|
@@ -3314,17 +4279,26 @@ exports.clamp = clamp;
|
|
|
3314
4279
|
exports.cleanEmpty = cleanEmpty;
|
|
3315
4280
|
exports.cleanObject = cleanObject;
|
|
3316
4281
|
exports.colorToChannels = colorToChannels;
|
|
4282
|
+
exports.compareBytes = compareBytes;
|
|
4283
|
+
exports.concatenateBytes = concatenateBytes;
|
|
3317
4284
|
exports.contrastRatio = contrastRatio;
|
|
3318
4285
|
exports.convertToUnit = convertToUnit;
|
|
3319
4286
|
exports.crc32 = crc32;
|
|
3320
4287
|
exports.createCustomizer = createCustomizer;
|
|
3321
4288
|
exports.createCustomizerFactory = createCustomizerFactory;
|
|
4289
|
+
exports.createDateObject = createDateObject;
|
|
3322
4290
|
exports.createDeepCloneWith = createDeepCloneWith;
|
|
4291
|
+
exports.createEJSON = createEJSON;
|
|
4292
|
+
exports.createEJSONStream = createEJSONStream;
|
|
3323
4293
|
exports.createEnvParser = createEnvParser;
|
|
3324
4294
|
exports.createRandomizer = createRandomizer;
|
|
3325
4295
|
exports.createSecureCustomizer = createSecureCustomizer;
|
|
4296
|
+
exports.createTimeObject = createTimeObject;
|
|
4297
|
+
exports.createTimeSpan = createTimeSpan;
|
|
3326
4298
|
exports.createWithCache = createWithCache;
|
|
3327
4299
|
exports.cssVariable = cssVariable;
|
|
4300
|
+
exports.dateInDays = dateInDays;
|
|
4301
|
+
exports.dateInSeconds = dateInSeconds;
|
|
3328
4302
|
exports.deepAssign = deepAssign;
|
|
3329
4303
|
exports.deepClone = deepClone;
|
|
3330
4304
|
exports.deepCloneWith = deepCloneWith;
|
|
@@ -3333,6 +4307,7 @@ exports.deepFreeze = deepFreeze;
|
|
|
3333
4307
|
exports.def = def;
|
|
3334
4308
|
exports.defer = defer;
|
|
3335
4309
|
exports.delay = delay;
|
|
4310
|
+
exports.difference = difference;
|
|
3336
4311
|
exports.dropCache = dropCache;
|
|
3337
4312
|
exports.env = env;
|
|
3338
4313
|
exports.escapeHtml = escapeHtml;
|
|
@@ -3351,16 +4326,19 @@ exports.getFileExtension = getFileExtension;
|
|
|
3351
4326
|
exports.getFileName = getFileName;
|
|
3352
4327
|
exports.getInitials = getInitials;
|
|
3353
4328
|
exports.getRandomInt = getRandomInt;
|
|
4329
|
+
exports.getRandomTime = getRandomTime;
|
|
3354
4330
|
exports.getWords = getWords;
|
|
3355
4331
|
exports.has = has;
|
|
3356
4332
|
exports.hasOwn = hasOwn;
|
|
3357
4333
|
exports.hasProtocol = hasProtocol;
|
|
3358
4334
|
exports.hex = hex;
|
|
3359
4335
|
exports.hexToChannels = hexToChannels;
|
|
4336
|
+
exports.hmToSeconds = hmToSeconds;
|
|
3360
4337
|
exports.hslToChannels = hslToChannels;
|
|
3361
4338
|
exports.humanFileSize = humanFileSize;
|
|
3362
4339
|
exports.humanize = humanize;
|
|
3363
4340
|
exports.interpolateColor = interpolateColor;
|
|
4341
|
+
exports.intersection = intersection;
|
|
3364
4342
|
exports.isBigInt = isBigInt;
|
|
3365
4343
|
exports.isBoolean = isBoolean;
|
|
3366
4344
|
exports.isCached = isCached;
|
|
@@ -3368,16 +4346,19 @@ exports.isClient = isClient;
|
|
|
3368
4346
|
exports.isColorChannels = isColorChannels;
|
|
3369
4347
|
exports.isCustomizerFactory = isCustomizerFactory;
|
|
3370
4348
|
exports.isDate = isDate;
|
|
4349
|
+
exports.isDateObject = isDateObject;
|
|
3371
4350
|
exports.isDef = isDef;
|
|
3372
4351
|
exports.isEmpty = isEmpty;
|
|
3373
4352
|
exports.isEqual = isEqual;
|
|
3374
4353
|
exports.isError = isError;
|
|
3375
4354
|
exports.isFunction = isFunction;
|
|
4355
|
+
exports.isInfinity = isInfinity;
|
|
3376
4356
|
exports.isMap = isMap;
|
|
3377
4357
|
exports.isNullOrUndefined = isNullOrUndefined;
|
|
3378
4358
|
exports.isNumber = isNumber;
|
|
3379
4359
|
exports.isObject = isObject;
|
|
3380
4360
|
exports.isOneEmoji = isOneEmoji;
|
|
4361
|
+
exports.isPlainObject = isPlainObject;
|
|
3381
4362
|
exports.isPrimitive = isPrimitive;
|
|
3382
4363
|
exports.isPromise = isPromise;
|
|
3383
4364
|
exports.isSet = isSet;
|
|
@@ -3385,6 +4366,10 @@ exports.isSkip = isSkip;
|
|
|
3385
4366
|
exports.isString = isString;
|
|
3386
4367
|
exports.isSuccess = isSuccess;
|
|
3387
4368
|
exports.isSymbol = isSymbol;
|
|
4369
|
+
exports.isTimeObject = isTimeObject;
|
|
4370
|
+
exports.isTimeString = isTimeString;
|
|
4371
|
+
exports.isTimeValue = isTimeValue;
|
|
4372
|
+
exports.isValidWeekDay = isValidWeekDay;
|
|
3388
4373
|
exports.isWeakMap = isWeakMap;
|
|
3389
4374
|
exports.isWeakSet = isWeakSet;
|
|
3390
4375
|
exports.isWithCache = isWithCache;
|
|
@@ -3416,25 +4401,36 @@ exports.removeVS16s = removeVS16s;
|
|
|
3416
4401
|
exports.retryOnError = retryOnError;
|
|
3417
4402
|
exports.rgbToChannels = rgbToChannels;
|
|
3418
4403
|
exports.round2digits = round2digits;
|
|
4404
|
+
exports.secondsToHm = secondsToHm;
|
|
3419
4405
|
exports.set = set;
|
|
4406
|
+
exports.shuffle = shuffle;
|
|
3420
4407
|
exports.snakeCase = snakeCase;
|
|
3421
4408
|
exports.sprintf = sprintf;
|
|
3422
4409
|
exports.startCase = startCase;
|
|
3423
4410
|
exports.strAssign = strAssign;
|
|
3424
4411
|
exports.sum = sum;
|
|
4412
|
+
exports.timeFromMinutes = timeFromMinutes;
|
|
4413
|
+
exports.timeStringify = timeStringify;
|
|
4414
|
+
exports.timeToMinutes = timeToMinutes;
|
|
3425
4415
|
exports.timeout = timeout;
|
|
3426
4416
|
exports.timestamp = timestamp;
|
|
4417
|
+
exports.timestampMs = timestampMs;
|
|
3427
4418
|
exports.timestampToDate = timestampToDate;
|
|
3428
4419
|
exports.tintedTextColor = tintedTextColor;
|
|
3429
4420
|
exports.toError = toError;
|
|
3430
4421
|
exports.toMap = toMap;
|
|
3431
4422
|
exports.truncate = truncate;
|
|
3432
4423
|
exports.typeOf = typeOf;
|
|
4424
|
+
exports.uint16ToUint8 = uint16ToUint8;
|
|
4425
|
+
exports.uint32ToUint8 = uint32ToUint8;
|
|
4426
|
+
exports.uint8ToUint16 = uint8ToUint16;
|
|
4427
|
+
exports.uint8ToUint32 = uint8ToUint32;
|
|
3433
4428
|
exports.unflatten = unflatten;
|
|
3434
4429
|
exports.union = union;
|
|
3435
4430
|
exports.uniq = uniq;
|
|
3436
4431
|
exports.uniqBy = uniqBy;
|
|
3437
4432
|
exports.unset = unset;
|
|
4433
|
+
exports.weeksInYear = weeksInYear;
|
|
3438
4434
|
exports.withCache = withCache;
|
|
3439
4435
|
exports.withCacheBucket = withCacheBucket;
|
|
3440
4436
|
exports.withCacheBucketBatch = withCacheBucketBatch;
|