@naturalcycles/js-lib 15.8.0 → 15.9.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/array/array.util.d.ts +14 -6
- package/dist/array/array.util.js +57 -36
- package/dist/array/range.d.ts +1 -1
- package/dist/array/range.js +1 -1
- package/dist/datetime/dateInterval.d.ts +4 -5
- package/dist/datetime/dateInterval.js +8 -11
- package/dist/datetime/localDate.d.ts +3 -3
- package/dist/datetime/localDate.js +5 -7
- package/dist/datetime/localTime.d.ts +1 -1
- package/dist/datetime/localTime.js +2 -3
- package/dist/datetime/timeInterval.d.ts +2 -2
- package/dist/datetime/timeInterval.js +3 -4
- package/dist/http/fetcher.js +1 -1
- package/dist/json-schema/jsonSchema.util.js +1 -1
- package/dist/math/math.util.js +0 -1
- package/dist/number/number.util.d.ts +1 -1
- package/dist/number/number.util.js +6 -11
- package/dist/object/object.util.d.ts +14 -13
- package/dist/object/object.util.js +26 -26
- package/dist/types.d.ts +7 -5
- package/dist/types.js +1 -1
- package/package.json +1 -1
- package/src/array/array.util.ts +73 -45
- package/src/array/range.ts +1 -1
- package/src/datetime/dateInterval.ts +9 -12
- package/src/datetime/localDate.ts +6 -7
- package/src/datetime/localTime.ts +2 -3
- package/src/datetime/timeInterval.ts +4 -5
- package/src/http/fetcher.ts +1 -1
- package/src/json-schema/jsonSchema.util.ts +1 -1
- package/src/math/math.util.ts +0 -1
- package/src/number/number.util.ts +4 -11
- package/src/object/object.util.ts +30 -26
- package/src/types.ts +11 -6
|
@@ -4,8 +4,8 @@ import { _objectEntries, SKIP } from '../types.js';
|
|
|
4
4
|
* Returns clone of `obj` with only `props` preserved.
|
|
5
5
|
* Opposite of Omit.
|
|
6
6
|
*/
|
|
7
|
-
export function _pick(obj, props,
|
|
8
|
-
if (mutate) {
|
|
7
|
+
export function _pick(obj, props, opt = {}) {
|
|
8
|
+
if (opt.mutate) {
|
|
9
9
|
// Start as original object (mutable), DELETE properties that are not whitelisted
|
|
10
10
|
for (const k of Object.keys(obj)) {
|
|
11
11
|
if (!props.includes(k))
|
|
@@ -25,8 +25,8 @@ export function _pick(obj, props, mutate = false) {
|
|
|
25
25
|
* Sets all properties of an object except passed ones to `undefined`.
|
|
26
26
|
* This is a more performant alternative to `_pick` that does picking/deleting.
|
|
27
27
|
*/
|
|
28
|
-
export function _pickWithUndefined(obj, props,
|
|
29
|
-
const r = mutate ? obj : { ...obj };
|
|
28
|
+
export function _pickWithUndefined(obj, props, opt = {}) {
|
|
29
|
+
const r = opt.mutate ? obj : { ...obj };
|
|
30
30
|
for (const k of Object.keys(r)) {
|
|
31
31
|
if (!props.includes(k)) {
|
|
32
32
|
r[k] = undefined;
|
|
@@ -38,8 +38,8 @@ export function _pickWithUndefined(obj, props, mutate = false) {
|
|
|
38
38
|
* Returns clone of `obj` with `props` omitted.
|
|
39
39
|
* Opposite of Pick.
|
|
40
40
|
*/
|
|
41
|
-
export function _omit(obj, props,
|
|
42
|
-
if (mutate) {
|
|
41
|
+
export function _omit(obj, props, opt = {}) {
|
|
42
|
+
if (opt.mutate) {
|
|
43
43
|
for (const k of props) {
|
|
44
44
|
delete obj[k];
|
|
45
45
|
}
|
|
@@ -56,8 +56,8 @@ export function _omit(obj, props, mutate = false) {
|
|
|
56
56
|
* Sets all passed properties of an object to `undefined`.
|
|
57
57
|
* This is a more performant alternative to `_omit` that does picking/deleting.
|
|
58
58
|
*/
|
|
59
|
-
export function _omitWithUndefined(obj, props,
|
|
60
|
-
const r = mutate ? obj : { ...obj };
|
|
59
|
+
export function _omitWithUndefined(obj, props, opt = {}) {
|
|
60
|
+
const r = opt.mutate ? obj : { ...obj };
|
|
61
61
|
for (const k of props) {
|
|
62
62
|
r[k] = undefined;
|
|
63
63
|
}
|
|
@@ -71,8 +71,8 @@ export function _omitWithUndefined(obj, props, mutate = false) {
|
|
|
71
71
|
* 'account.updated',
|
|
72
72
|
* ])
|
|
73
73
|
*/
|
|
74
|
-
export function _mask(obj, props,
|
|
75
|
-
const r = mutate ? obj : _deepCopy(obj);
|
|
74
|
+
export function _mask(obj, props, opt = {}) {
|
|
75
|
+
const r = opt.mutate ? obj : _deepCopy(obj);
|
|
76
76
|
for (const k of props) {
|
|
77
77
|
_unset(r, k);
|
|
78
78
|
}
|
|
@@ -81,31 +81,31 @@ export function _mask(obj, props, mutate = false) {
|
|
|
81
81
|
/**
|
|
82
82
|
* Removes "falsy" values from the object.
|
|
83
83
|
*/
|
|
84
|
-
export function _filterFalsyValues(obj,
|
|
85
|
-
return _filterObject(obj, (_k, v) => !!v,
|
|
84
|
+
export function _filterFalsyValues(obj, opt = {}) {
|
|
85
|
+
return _filterObject(obj, (_k, v) => !!v, opt);
|
|
86
86
|
}
|
|
87
87
|
/**
|
|
88
88
|
* Removes values from the object that are `null` or `undefined`.
|
|
89
89
|
*/
|
|
90
|
-
export function _filterNullishValues(obj,
|
|
91
|
-
return _filterObject(obj, (_k, v) => v !== undefined && v !== null,
|
|
90
|
+
export function _filterNullishValues(obj, opt = {}) {
|
|
91
|
+
return _filterObject(obj, (_k, v) => v !== undefined && v !== null, opt);
|
|
92
92
|
}
|
|
93
93
|
/**
|
|
94
94
|
* Removes values from the object that are `undefined`.
|
|
95
95
|
* Only `undefined` values are removed. `null` values are kept!
|
|
96
96
|
*/
|
|
97
|
-
export function _filterUndefinedValues(obj,
|
|
98
|
-
return _filterObject(obj, (_k, v) => v !== undefined,
|
|
97
|
+
export function _filterUndefinedValues(obj, opt = {}) {
|
|
98
|
+
return _filterObject(obj, (_k, v) => v !== undefined, opt);
|
|
99
99
|
}
|
|
100
|
-
export function _filterEmptyArrays(obj,
|
|
101
|
-
return _filterObject(obj, (_k, v) => !Array.isArray(v) || v.length > 0,
|
|
100
|
+
export function _filterEmptyArrays(obj, opt = {}) {
|
|
101
|
+
return _filterObject(obj, (_k, v) => !Array.isArray(v) || v.length > 0, opt);
|
|
102
102
|
}
|
|
103
103
|
/**
|
|
104
104
|
* Returns clone of `obj` without properties that does not pass `predicate`.
|
|
105
105
|
* Allows filtering by both key and value.
|
|
106
106
|
*/
|
|
107
|
-
export function _filterObject(obj, predicate,
|
|
108
|
-
if (mutate) {
|
|
107
|
+
export function _filterObject(obj, predicate, opt = {}) {
|
|
108
|
+
if (opt.mutate) {
|
|
109
109
|
for (const [k, v] of _objectEntries(obj)) {
|
|
110
110
|
if (!predicate(k, v, obj)) {
|
|
111
111
|
delete obj[k];
|
|
@@ -132,8 +132,8 @@ export function _filterObject(obj, predicate, mutate = false) {
|
|
|
132
132
|
*
|
|
133
133
|
* To skip some key-value pairs - use _mapObject instead.
|
|
134
134
|
*/
|
|
135
|
-
export function _mapValues(obj, mapper,
|
|
136
|
-
const map = mutate ? obj : {};
|
|
135
|
+
export function _mapValues(obj, mapper, opt = {}) {
|
|
136
|
+
const map = opt.mutate ? obj : {};
|
|
137
137
|
for (const [k, v] of Object.entries(obj)) {
|
|
138
138
|
map[k] = mapper(k, v, obj);
|
|
139
139
|
}
|
|
@@ -183,8 +183,8 @@ export function _mapObject(obj, mapper) {
|
|
|
183
183
|
export function _findKeyByValue(obj, v) {
|
|
184
184
|
return Object.entries(obj).find(([_, value]) => value === v)?.[0];
|
|
185
185
|
}
|
|
186
|
-
export function _objectNullValuesToUndefined(obj,
|
|
187
|
-
return _mapValues(obj, (_k, v) => (v === null ? undefined : v),
|
|
186
|
+
export function _objectNullValuesToUndefined(obj, opt = {}) {
|
|
187
|
+
return _mapValues(obj, (_k, v) => (v === null ? undefined : v), opt);
|
|
188
188
|
}
|
|
189
189
|
/**
|
|
190
190
|
* Deep copy object (by json parse/stringify, since it has unbeatable performance+simplicity combo).
|
|
@@ -202,8 +202,8 @@ export function _undefinedIfEmpty(obj) {
|
|
|
202
202
|
/**
|
|
203
203
|
* Filters the object by removing all key-value pairs where Value is Empty (according to _isEmpty() specification).
|
|
204
204
|
*/
|
|
205
|
-
export function _filterEmptyValues(obj,
|
|
206
|
-
return _filterObject(obj, (_k, v) => !_isEmpty(v),
|
|
205
|
+
export function _filterEmptyValues(obj, opt = {}) {
|
|
206
|
+
return _filterObject(obj, (_k, v) => !_isEmpty(v), opt);
|
|
207
207
|
}
|
|
208
208
|
/**
|
|
209
209
|
* Recursively merges own and inherited enumerable properties of source
|
package/dist/types.d.ts
CHANGED
|
@@ -117,10 +117,12 @@ export declare const MISS: unique symbol;
|
|
|
117
117
|
/**
|
|
118
118
|
* Function which is called for every item in `input`. Expected to return a `Promise` or value.
|
|
119
119
|
*/
|
|
120
|
-
export type AsyncMapper<IN = any, OUT = any> = (input: IN
|
|
121
|
-
export type
|
|
122
|
-
export
|
|
123
|
-
export
|
|
120
|
+
export type AsyncMapper<IN = any, OUT = any> = (input: IN) => OUT | PromiseLike<OUT>;
|
|
121
|
+
export type AsyncIndexedMapper<IN = any, OUT = any> = (input: IN, index: number) => OUT | PromiseLike<OUT>;
|
|
122
|
+
export type Mapper<IN = any, OUT = any> = (input: IN) => OUT;
|
|
123
|
+
export type IndexedMapper<IN = any, OUT = any> = (input: IN, index: number) => OUT;
|
|
124
|
+
export declare const _passthroughMapper: IndexedMapper;
|
|
125
|
+
export declare const _passUndefinedMapper: IndexedMapper<any, void>;
|
|
124
126
|
/**
|
|
125
127
|
* Function that does nothings and returns `undefined`.
|
|
126
128
|
*/
|
|
@@ -326,7 +328,7 @@ export declare const _objectAssign: <T extends AnyObject>(target: T, part: Parti
|
|
|
326
328
|
*/
|
|
327
329
|
export type ErrorDataTuple<T = unknown, ERR = Error> = [err: null, data: T] | [err: ERR, data: null];
|
|
328
330
|
export type SortDirection = 'asc' | 'desc';
|
|
329
|
-
export type Inclusiveness = '
|
|
331
|
+
export type Inclusiveness = '[]' | '[)';
|
|
330
332
|
/**
|
|
331
333
|
* @experimental
|
|
332
334
|
*/
|
package/dist/types.js
CHANGED
|
@@ -24,7 +24,7 @@ export const _passNothingPredicate = () => false;
|
|
|
24
24
|
* Like _stringMapValues, but values are sorted.
|
|
25
25
|
*/
|
|
26
26
|
export function _stringMapValuesSorted(map, mapper, dir = 'asc') {
|
|
27
|
-
return _sortBy(_stringMapValues(map), mapper,
|
|
27
|
+
return _sortBy(_stringMapValues(map), mapper, { dir });
|
|
28
28
|
}
|
|
29
29
|
/**
|
|
30
30
|
* Needed due to https://github.com/microsoft/TypeScript/issues/13778
|
package/package.json
CHANGED
package/src/array/array.util.ts
CHANGED
|
@@ -61,9 +61,9 @@ export function _pushUniq<T>(a: T[], ...items: T[]): T[] {
|
|
|
61
61
|
* Mutates the array (same as normal `push`).
|
|
62
62
|
*/
|
|
63
63
|
export function _pushUniqBy<T>(a: T[], mapper: Mapper<T, any>, ...items: T[]): T[] {
|
|
64
|
-
const mappedSet = new Set(a.map(
|
|
65
|
-
items.forEach(
|
|
66
|
-
const mapped = mapper(item
|
|
64
|
+
const mappedSet = new Set(a.map(mapper))
|
|
65
|
+
items.forEach(item => {
|
|
66
|
+
const mapped = mapper(item)
|
|
67
67
|
if (!mappedSet.has(mapped)) {
|
|
68
68
|
a.push(item)
|
|
69
69
|
mappedSet.add(mapped)
|
|
@@ -91,8 +91,9 @@ export function _pushUniqBy<T>(a: T[], mapper: Mapper<T, any>, ...items: T[]): T
|
|
|
91
91
|
*/
|
|
92
92
|
export function _uniqBy<T>(arr: readonly T[], mapper: Mapper<T, any>): T[] {
|
|
93
93
|
const map = new Map<any, T>()
|
|
94
|
-
for (
|
|
95
|
-
const
|
|
94
|
+
for (let i = 0; i < arr.length; i++) {
|
|
95
|
+
const item = arr[i]!
|
|
96
|
+
const key = item === undefined || item === null ? item : mapper(item)
|
|
96
97
|
if (!map.has(key)) map.set(key, item)
|
|
97
98
|
}
|
|
98
99
|
return [...map.values()]
|
|
@@ -119,9 +120,16 @@ export function _uniqBy<T>(arr: readonly T[], mapper: Mapper<T, any>): T[] {
|
|
|
119
120
|
* Returning `undefined` from the Mapper will EXCLUDE the item.
|
|
120
121
|
*/
|
|
121
122
|
export function _by<T>(items: readonly T[], mapper: Mapper<T, any>): StringMap<T> {
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
123
|
+
const map: StringMap<T> = {}
|
|
124
|
+
for (let i = 0; i < items.length; i++) {
|
|
125
|
+
const v = items[i]!
|
|
126
|
+
const k = mapper(v)
|
|
127
|
+
if (k !== undefined) {
|
|
128
|
+
map[k] = v
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
return map
|
|
125
133
|
}
|
|
126
134
|
|
|
127
135
|
/**
|
|
@@ -131,12 +139,15 @@ export function _mapBy<ITEM, KEY>(
|
|
|
131
139
|
items: readonly ITEM[],
|
|
132
140
|
mapper: Mapper<ITEM, KEY>,
|
|
133
141
|
): Map<KEY, ITEM> {
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
142
|
+
const map = new Map<KEY, ITEM>()
|
|
143
|
+
for (let i = 0; i < items.length; i++) {
|
|
144
|
+
const item = items[i]!
|
|
145
|
+
const key = mapper(item)
|
|
146
|
+
if (key !== undefined) {
|
|
147
|
+
map.set(key, item)
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
return map
|
|
140
151
|
}
|
|
141
152
|
|
|
142
153
|
/**
|
|
@@ -152,14 +163,31 @@ export function _mapBy<ITEM, KEY>(
|
|
|
152
163
|
*/
|
|
153
164
|
export function _groupBy<T>(items: readonly T[], mapper: Mapper<T, any>): StringMap<T[]> {
|
|
154
165
|
const map: StringMap<T[]> = {}
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
166
|
+
|
|
167
|
+
for (let i = 0; i < items.length; i++) {
|
|
168
|
+
const item = items[i]!
|
|
169
|
+
const key = mapper(item)
|
|
170
|
+
if (key !== undefined) {
|
|
171
|
+
;(map[key] ||= []).push(item)
|
|
172
|
+
}
|
|
159
173
|
}
|
|
160
174
|
return map
|
|
161
175
|
}
|
|
162
176
|
|
|
177
|
+
export interface MutateOptions {
|
|
178
|
+
/**
|
|
179
|
+
* Defaults to false.
|
|
180
|
+
*/
|
|
181
|
+
mutate?: boolean
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
export interface SortByOptions extends MutateOptions {
|
|
185
|
+
/**
|
|
186
|
+
* Defaults to 'asc'.
|
|
187
|
+
*/
|
|
188
|
+
dir?: SortDirection
|
|
189
|
+
}
|
|
190
|
+
|
|
163
191
|
/**
|
|
164
192
|
* _sortBy([{age: 20}, {age: 10}], 'age')
|
|
165
193
|
* // => [{age: 10}, {age: 20}]
|
|
@@ -167,34 +195,34 @@ export function _groupBy<T>(items: readonly T[], mapper: Mapper<T, any>): String
|
|
|
167
195
|
* Same:
|
|
168
196
|
* _sortBy([{age: 20}, {age: 10}], o => o.age)
|
|
169
197
|
*/
|
|
170
|
-
export function _sortBy<T>(
|
|
198
|
+
export function _sortBy<T, COMPARE_TYPE extends string | number>(
|
|
171
199
|
items: T[],
|
|
172
|
-
mapper: Mapper<T,
|
|
173
|
-
|
|
174
|
-
dir: SortDirection = 'asc',
|
|
200
|
+
mapper: Mapper<T, COMPARE_TYPE>,
|
|
201
|
+
opt: SortByOptions = {},
|
|
175
202
|
): T[] {
|
|
176
|
-
const mod = dir === 'desc' ? -1 : 1
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
203
|
+
const mod = opt.dir === 'desc' ? -1 : 1
|
|
204
|
+
|
|
205
|
+
return (opt.mutate ? items : [...items]).sort((_a, _b) => {
|
|
206
|
+
// This implementation may call mapper more than once per item,
|
|
207
|
+
// but the benchmarks show no significant difference in performance.
|
|
208
|
+
const a = mapper(_a)
|
|
209
|
+
const b = mapper(_b)
|
|
210
|
+
// if (typeof a === 'number' && typeof b === 'number') return (a - b) * mod
|
|
211
|
+
// return String(a).localeCompare(String(b)) * mod
|
|
212
|
+
if (a > b) return mod
|
|
213
|
+
if (a < b) return -mod
|
|
214
|
+
return 0
|
|
181
215
|
})
|
|
182
216
|
}
|
|
183
217
|
|
|
184
|
-
/**
|
|
185
|
-
* Alias for _sortBy with descending order.
|
|
186
|
-
*/
|
|
187
|
-
export function _sortDescBy<T>(items: T[], mapper: Mapper<T, any>, mutate = false): T[] {
|
|
188
|
-
return _sortBy(items, mapper, mutate, 'desc')
|
|
189
|
-
}
|
|
190
|
-
|
|
191
218
|
/**
|
|
192
219
|
* Similar to `Array.find`, but the `predicate` may return `END` to stop the iteration early.
|
|
193
220
|
*
|
|
194
221
|
* Use `Array.find` if you don't need to stop the iteration early.
|
|
195
222
|
*/
|
|
196
223
|
export function _find<T>(items: readonly T[], predicate: AbortablePredicate<T>): T | undefined {
|
|
197
|
-
for (
|
|
224
|
+
for (let i = 0; i < items.length; i++) {
|
|
225
|
+
const item = items[i]!
|
|
198
226
|
const result = predicate(item, i)
|
|
199
227
|
if (result === END) return
|
|
200
228
|
if (result) return item
|
|
@@ -290,9 +318,8 @@ export function _count<T>(
|
|
|
290
318
|
export function _countBy<T>(items: Iterable<T>, mapper: Mapper<T, any>): StringMap<number> {
|
|
291
319
|
const map: StringMap<number> = {}
|
|
292
320
|
|
|
293
|
-
let i = 0
|
|
294
321
|
for (const item of items) {
|
|
295
|
-
const key = mapper(item
|
|
322
|
+
const key = mapper(item)
|
|
296
323
|
map[key] = (map[key] || 0) + 1
|
|
297
324
|
}
|
|
298
325
|
|
|
@@ -360,10 +387,9 @@ export function _sumBy<T, N extends number>(
|
|
|
360
387
|
mapper: Mapper<T, N | undefined>,
|
|
361
388
|
): N {
|
|
362
389
|
let sum = 0 as N
|
|
363
|
-
let i = 0
|
|
364
390
|
|
|
365
391
|
for (const n of items) {
|
|
366
|
-
const v = mapper(n
|
|
392
|
+
const v = mapper(n)
|
|
367
393
|
if (typeof v === 'number') {
|
|
368
394
|
// count only numbers, nothing else
|
|
369
395
|
sum = (sum + v) as N
|
|
@@ -407,8 +433,8 @@ export function _mapToObject<T, V>(
|
|
|
407
433
|
* Fisher–Yates algorithm.
|
|
408
434
|
* Based on: https://stackoverflow.com/a/12646864/4919972
|
|
409
435
|
*/
|
|
410
|
-
export function _shuffle<T>(array: T[],
|
|
411
|
-
const a = mutate ? array : [...array]
|
|
436
|
+
export function _shuffle<T>(array: T[], opt: MutateOptions = {}): T[] {
|
|
437
|
+
const a = opt.mutate ? array : [...array]
|
|
412
438
|
|
|
413
439
|
for (let i = a.length - 1; i > 0; i--) {
|
|
414
440
|
const j = Math.floor(Math.random() * (i + 1))
|
|
@@ -505,8 +531,9 @@ export function _maxByOrUndefined<T>(
|
|
|
505
531
|
let maxItem: T | undefined
|
|
506
532
|
let max: number | string | undefined
|
|
507
533
|
|
|
508
|
-
for (
|
|
509
|
-
const
|
|
534
|
+
for (let i = 0; i < array.length; i++) {
|
|
535
|
+
const item = array[i]!
|
|
536
|
+
const v = mapper(item)
|
|
510
537
|
if (v !== undefined && (max === undefined || v > max)) {
|
|
511
538
|
maxItem = item
|
|
512
539
|
max = v
|
|
@@ -524,8 +551,9 @@ export function _minByOrUndefined<T>(
|
|
|
524
551
|
let minItem: T | undefined
|
|
525
552
|
let min: number | string | undefined
|
|
526
553
|
|
|
527
|
-
for (
|
|
528
|
-
const
|
|
554
|
+
for (let i = 0; i < array.length; i++) {
|
|
555
|
+
const item = array[i]!
|
|
556
|
+
const v = mapper(item)
|
|
529
557
|
if (v !== undefined && (min === undefined || v < min)) {
|
|
530
558
|
minItem = item
|
|
531
559
|
min = v
|
package/src/array/range.ts
CHANGED
|
@@ -36,7 +36,7 @@ export function _range(fromIncl: Integer, toExcl?: Integer, step = 1): number[]
|
|
|
36
36
|
* Fill is Primitive, because it's safe to shallow-copy.
|
|
37
37
|
* If it was an object - it'll paste the same object reference, which can create bugs.
|
|
38
38
|
*/
|
|
39
|
-
export function
|
|
39
|
+
export function _arrayFilled<T extends Primitive>(length: Integer, fill: T): T[] {
|
|
40
40
|
// biome-ignore lint/style/useConsistentBuiltinInstantiation: ok
|
|
41
41
|
return Array(length).fill(fill)
|
|
42
42
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { IsoDate } from '../types.js'
|
|
2
2
|
import type { LocalDate, LocalDateInput, LocalDateUnit } from './localDate.js'
|
|
3
3
|
import { localDate } from './localDate.js'
|
|
4
4
|
|
|
@@ -60,16 +60,13 @@ export class DateInterval {
|
|
|
60
60
|
/**
|
|
61
61
|
* Ranges of DateInterval (start, end) are INCLUSIVE.
|
|
62
62
|
*/
|
|
63
|
-
includes(d: LocalDateInput
|
|
64
|
-
|
|
65
|
-
// eslint-disable-next-line @typescript-eslint/prefer-string-starts-ends-with
|
|
66
|
-
return d.isAfter(this.start, incl[0] === '[') && d.isBefore(this.end, incl[1] === ']')
|
|
63
|
+
includes(d: LocalDateInput): boolean {
|
|
64
|
+
return localDate(d).isBetween(this.start, this.end, '[]')
|
|
67
65
|
}
|
|
68
66
|
|
|
69
|
-
intersects(int: DateIntervalConfig
|
|
67
|
+
intersects(int: DateIntervalConfig): boolean {
|
|
70
68
|
const $int = DateInterval.parse(int)
|
|
71
|
-
|
|
72
|
-
return this.includes($int.start, incl) || this.includes($int.end, incl)
|
|
69
|
+
return this.includes($int.start) || this.includes($int.end)
|
|
73
70
|
}
|
|
74
71
|
|
|
75
72
|
/**
|
|
@@ -81,15 +78,15 @@ export class DateInterval {
|
|
|
81
78
|
return this.start.compare(d.start) || this.end.compare(d.end)
|
|
82
79
|
}
|
|
83
80
|
|
|
84
|
-
getDays(
|
|
85
|
-
return localDate.range(this.start, this.end,
|
|
81
|
+
getDays(): LocalDate[] {
|
|
82
|
+
return localDate.range(this.start, this.end, '[]', 1, 'day')
|
|
86
83
|
}
|
|
87
84
|
|
|
88
85
|
/**
|
|
89
86
|
* Returns an array of LocalDates that are included in the interval.
|
|
90
87
|
*/
|
|
91
|
-
range(
|
|
92
|
-
return localDate.range(this.start, this.end,
|
|
88
|
+
range(step = 1, stepUnit: LocalDateUnit = 'day'): LocalDate[] {
|
|
89
|
+
return localDate.range(this.start, this.end, '[]', step, stepUnit)
|
|
93
90
|
}
|
|
94
91
|
|
|
95
92
|
toString(): DateIntervalString {
|
|
@@ -117,10 +117,9 @@ export class LocalDate {
|
|
|
117
117
|
return this.compare(d) >= 0
|
|
118
118
|
}
|
|
119
119
|
|
|
120
|
-
isBetween(min: LocalDateInput, max: LocalDateInput, incl: Inclusiveness
|
|
120
|
+
isBetween(min: LocalDateInput, max: LocalDateInput, incl: Inclusiveness): boolean {
|
|
121
121
|
let r = this.compare(min)
|
|
122
|
-
|
|
123
|
-
if (r < 0 || (r === 0 && incl[0] === '(')) return false
|
|
122
|
+
if (r < 0) return false
|
|
124
123
|
r = this.compare(max)
|
|
125
124
|
if (r > 0 || (r === 0 && incl[1] === ')')) return false
|
|
126
125
|
return true
|
|
@@ -779,7 +778,7 @@ class LocalDateFactory {
|
|
|
779
778
|
range(
|
|
780
779
|
min: LocalDateInput,
|
|
781
780
|
max: LocalDateInput,
|
|
782
|
-
incl: Inclusiveness
|
|
781
|
+
incl: Inclusiveness,
|
|
783
782
|
step = 1,
|
|
784
783
|
stepUnit: LocalDateUnit = 'day',
|
|
785
784
|
): LocalDate[] {
|
|
@@ -793,7 +792,7 @@ class LocalDateFactory {
|
|
|
793
792
|
rangeIterable(
|
|
794
793
|
min: LocalDateInput,
|
|
795
794
|
max: LocalDateInput,
|
|
796
|
-
incl: Inclusiveness
|
|
795
|
+
incl: Inclusiveness,
|
|
797
796
|
step = 1,
|
|
798
797
|
stepUnit: LocalDateUnit = 'day',
|
|
799
798
|
): Iterable2<LocalDate> {
|
|
@@ -806,8 +805,8 @@ class LocalDateFactory {
|
|
|
806
805
|
const $max = this.fromInput(max).startOf(stepUnit)
|
|
807
806
|
|
|
808
807
|
let value = $min
|
|
809
|
-
|
|
810
|
-
if (value.
|
|
808
|
+
|
|
809
|
+
if (value.isSameOrAfter($min)) {
|
|
811
810
|
// ok
|
|
812
811
|
} else {
|
|
813
812
|
value.plus(1, stepUnit, true)
|
|
@@ -517,10 +517,9 @@ export class LocalTime {
|
|
|
517
517
|
return this.compare(d) >= 0
|
|
518
518
|
}
|
|
519
519
|
|
|
520
|
-
isBetween(min: LocalTimeInput, max: LocalTimeInput, incl: Inclusiveness
|
|
520
|
+
isBetween(min: LocalTimeInput, max: LocalTimeInput, incl: Inclusiveness): boolean {
|
|
521
521
|
let r = this.compare(min)
|
|
522
|
-
|
|
523
|
-
if (r < 0 || (r === 0 && incl[0] === '(')) return false
|
|
522
|
+
if (r < 0) return false
|
|
524
523
|
r = this.compare(max)
|
|
525
524
|
if (r > 0 || (r === 0 && incl[1] === ')')) return false
|
|
526
525
|
return true
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { UnixTimestamp } from '../types.js'
|
|
2
2
|
import type { LocalTime, LocalTimeInput } from './localTime.js'
|
|
3
3
|
import { localTime } from './localTime.js'
|
|
4
4
|
|
|
@@ -74,11 +74,10 @@ export class TimeInterval {
|
|
|
74
74
|
return this.cmp(d) >= 0
|
|
75
75
|
}
|
|
76
76
|
|
|
77
|
-
includes(d: LocalTimeInput
|
|
77
|
+
includes(d: LocalTimeInput): boolean {
|
|
78
78
|
d = localTime.fromInput(d).unix
|
|
79
|
-
|
|
80
|
-
if (d
|
|
81
|
-
if (d > this.$end || (d === this.$end && incl[1] === ')')) return false
|
|
79
|
+
if (d < this.$start) return false
|
|
80
|
+
if (d > this.$end) return false
|
|
82
81
|
return true
|
|
83
82
|
}
|
|
84
83
|
|
package/src/http/fetcher.ts
CHANGED
|
@@ -803,7 +803,7 @@ export class Fetcher {
|
|
|
803
803
|
}
|
|
804
804
|
|
|
805
805
|
// Because all header values are stringified, so `a: undefined` becomes `undefined` as a string
|
|
806
|
-
_filterNullishValues(req.init.headers, true)
|
|
806
|
+
_filterNullishValues(req.init.headers, { mutate: true })
|
|
807
807
|
|
|
808
808
|
// setup url
|
|
809
809
|
const baseUrl = opt.baseUrl || this.cfg.baseUrl
|
package/src/math/math.util.ts
CHANGED
|
@@ -29,7 +29,6 @@ export function _averageOrNull(values: number[] | undefined | null): number | nu
|
|
|
29
29
|
export function _averageWeighted(values: number[], weights: number[]): number {
|
|
30
30
|
let numerator = 0
|
|
31
31
|
let denominator = 0
|
|
32
|
-
// eslint-disable-next-line unicorn/no-for-loop
|
|
33
32
|
for (let i = 0; i < values.length; i++) {
|
|
34
33
|
numerator += values[i]! * weights[i]!
|
|
35
34
|
denominator += weights[i]!
|
|
@@ -42,18 +42,11 @@ export function _isBetween<T extends number | string>(
|
|
|
42
42
|
x: T,
|
|
43
43
|
min: T,
|
|
44
44
|
max: T,
|
|
45
|
-
incl: Inclusiveness
|
|
45
|
+
incl: Inclusiveness,
|
|
46
46
|
): boolean {
|
|
47
|
-
if (
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
if (incl === '[]') {
|
|
51
|
-
return x >= min && x <= max
|
|
52
|
-
}
|
|
53
|
-
if (incl === '(]') {
|
|
54
|
-
return x > min && x <= max
|
|
55
|
-
}
|
|
56
|
-
return x > min && x < max
|
|
47
|
+
if (x < min || x > max) return false
|
|
48
|
+
if (x === max && incl === '[)') return false
|
|
49
|
+
return true
|
|
57
50
|
}
|
|
58
51
|
|
|
59
52
|
export function _clamp(x: number, minIncl: number, maxIncl: number): number {
|