@simplysm/core-common 14.0.4 → 14.0.6
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 +123 -59
- package/docs/array-extensions.md +171 -164
- package/docs/env.md +8 -27
- package/docs/errors.md +15 -51
- package/docs/features.md +52 -68
- package/docs/map-extensions.md +41 -0
- package/docs/set-extensions.md +38 -0
- package/docs/template-strings-and-zip.md +87 -0
- package/docs/type-utilities.md +19 -35
- package/docs/types.md +111 -111
- package/docs/utilities.md +723 -0
- package/package.json +1 -1
- package/docs/utils.md +0 -641
package/docs/array-extensions.md
CHANGED
|
@@ -1,96 +1,98 @@
|
|
|
1
|
-
# Array
|
|
1
|
+
# Array Extensions
|
|
2
2
|
|
|
3
|
-
Prototype extensions added to `Array
|
|
3
|
+
Prototype extensions added to both `Array` and `ReadonlyArray`. Available after importing `@simplysm/core-common`.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
Also exports helper functions and result types.
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
## ReadonlyArray Extensions
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
These methods do not mutate the original array.
|
|
10
10
|
|
|
11
|
-
|
|
11
|
+
### `single`
|
|
12
|
+
|
|
13
|
+
Return the single element matching the predicate. Returns `undefined` if no match. Throws `ArgumentError` if more than one element matches.
|
|
12
14
|
|
|
13
15
|
```typescript
|
|
14
16
|
single(predicate?: (item: T, index: number) => boolean): T | undefined;
|
|
15
17
|
```
|
|
16
18
|
|
|
17
|
-
### `first
|
|
19
|
+
### `first`
|
|
18
20
|
|
|
19
|
-
|
|
21
|
+
Return the first element, or the first element matching the predicate.
|
|
20
22
|
|
|
21
23
|
```typescript
|
|
22
24
|
first(predicate?: (item: T, index: number) => boolean): T | undefined;
|
|
23
25
|
```
|
|
24
26
|
|
|
25
|
-
### `last
|
|
27
|
+
### `last`
|
|
26
28
|
|
|
27
|
-
|
|
29
|
+
Return the last element, or the last element matching the predicate.
|
|
28
30
|
|
|
29
31
|
```typescript
|
|
30
32
|
last(predicate?: (item: T, index: number) => boolean): T | undefined;
|
|
31
33
|
```
|
|
32
34
|
|
|
33
|
-
### `
|
|
35
|
+
### `filterExists`
|
|
34
36
|
|
|
35
|
-
|
|
37
|
+
Remove all `null` and `undefined` elements.
|
|
36
38
|
|
|
37
39
|
```typescript
|
|
38
|
-
|
|
40
|
+
filterExists(): NonNullable<T>[];
|
|
39
41
|
```
|
|
40
42
|
|
|
41
|
-
### `
|
|
43
|
+
### `ofType`
|
|
42
44
|
|
|
43
|
-
|
|
45
|
+
Filter elements by type. Accepts a `PrimitiveTypeStr` (e.g., `"string"`, `"DateTime"`) or a constructor function.
|
|
44
46
|
|
|
45
47
|
```typescript
|
|
46
|
-
|
|
48
|
+
ofType<TKey extends PrimitiveTypeStr>(type: TKey): Extract<T, PrimitiveTypeMap[TKey]>[];
|
|
49
|
+
ofType<TNarrow extends T>(type: Type<TNarrow>): TNarrow[];
|
|
47
50
|
```
|
|
48
51
|
|
|
49
|
-
### `
|
|
52
|
+
### `filterAsync`
|
|
50
53
|
|
|
51
|
-
|
|
54
|
+
Async sequential filter. Evaluates the predicate for each element in order.
|
|
52
55
|
|
|
53
56
|
```typescript
|
|
54
|
-
|
|
55
|
-
ofType<N extends T>(type: Type<N>): N[];
|
|
57
|
+
filterAsync(predicate: (item: T, index: number) => Promise<boolean>): Promise<T[]>;
|
|
56
58
|
```
|
|
57
59
|
|
|
58
|
-
### `mapAsync
|
|
60
|
+
### `mapAsync`
|
|
59
61
|
|
|
60
|
-
Async sequential map.
|
|
62
|
+
Async sequential map. Evaluates the selector for each element in order.
|
|
61
63
|
|
|
62
64
|
```typescript
|
|
63
65
|
mapAsync<R>(selector: (item: T, index: number) => Promise<R>): Promise<R[]>;
|
|
64
66
|
```
|
|
65
67
|
|
|
66
|
-
### `mapMany
|
|
68
|
+
### `mapMany`
|
|
67
69
|
|
|
68
|
-
|
|
70
|
+
Flatten a nested array, or map then flatten. Filters out null/undefined from the result.
|
|
69
71
|
|
|
70
72
|
```typescript
|
|
71
73
|
mapMany(): T extends readonly (infer U)[] ? U[] : T;
|
|
72
74
|
mapMany<R>(selector: (item: T, index: number) => R[]): R[];
|
|
73
75
|
```
|
|
74
76
|
|
|
75
|
-
### `mapManyAsync
|
|
77
|
+
### `mapManyAsync`
|
|
76
78
|
|
|
77
|
-
Async
|
|
79
|
+
Async map then flatten.
|
|
78
80
|
|
|
79
81
|
```typescript
|
|
80
82
|
mapManyAsync<R>(selector: (item: T, index: number) => Promise<R[]>): Promise<R[]>;
|
|
81
83
|
```
|
|
82
84
|
|
|
83
|
-
### `parallelAsync
|
|
85
|
+
### `parallelAsync`
|
|
84
86
|
|
|
85
|
-
|
|
87
|
+
Parallel async map using `Promise.all`. All promises run concurrently.
|
|
86
88
|
|
|
87
89
|
```typescript
|
|
88
90
|
parallelAsync<R>(fn: (item: T, index: number) => Promise<R>): Promise<R[]>;
|
|
89
91
|
```
|
|
90
92
|
|
|
91
|
-
### `groupBy
|
|
93
|
+
### `groupBy`
|
|
92
94
|
|
|
93
|
-
|
|
95
|
+
Group elements by a key selector. Supports object keys via deep comparison (O(n^2)). Primitive keys use Map-based O(n) lookup.
|
|
94
96
|
|
|
95
97
|
```typescript
|
|
96
98
|
groupBy<K>(keySelector: (item: T, index: number) => K): { key: K; values: T[] }[];
|
|
@@ -100,9 +102,9 @@ groupBy<K, V>(
|
|
|
100
102
|
): { key: K; values: V[] }[];
|
|
101
103
|
```
|
|
102
104
|
|
|
103
|
-
### `toMap
|
|
105
|
+
### `toMap`
|
|
104
106
|
|
|
105
|
-
|
|
107
|
+
Convert to a `Map`. Throws `ArgumentError` on duplicate keys.
|
|
106
108
|
|
|
107
109
|
```typescript
|
|
108
110
|
toMap<K>(keySelector: (item: T, index: number) => K): Map<K, T>;
|
|
@@ -112,7 +114,7 @@ toMap<K, V>(
|
|
|
112
114
|
): Map<K, V>;
|
|
113
115
|
```
|
|
114
116
|
|
|
115
|
-
### `toMapAsync
|
|
117
|
+
### `toMapAsync`
|
|
116
118
|
|
|
117
119
|
Async version of `toMap`.
|
|
118
120
|
|
|
@@ -124,9 +126,9 @@ toMapAsync<K, V>(
|
|
|
124
126
|
): Promise<Map<K, V>>;
|
|
125
127
|
```
|
|
126
128
|
|
|
127
|
-
### `toArrayMap
|
|
129
|
+
### `toArrayMap`
|
|
128
130
|
|
|
129
|
-
|
|
131
|
+
Convert to a `Map<K, V[]>`. Multiple items with the same key are grouped into an array.
|
|
130
132
|
|
|
131
133
|
```typescript
|
|
132
134
|
toArrayMap<K>(keySelector: (item: T, index: number) => K): Map<K, T[]>;
|
|
@@ -136,9 +138,9 @@ toArrayMap<K, V>(
|
|
|
136
138
|
): Map<K, V[]>;
|
|
137
139
|
```
|
|
138
140
|
|
|
139
|
-
### `toSetMap
|
|
141
|
+
### `toSetMap`
|
|
140
142
|
|
|
141
|
-
|
|
143
|
+
Convert to a `Map<K, Set<V>>`.
|
|
142
144
|
|
|
143
145
|
```typescript
|
|
144
146
|
toSetMap<K>(keySelector: (item: T, index: number) => K): Map<K, Set<T>>;
|
|
@@ -148,9 +150,9 @@ toSetMap<K, V>(
|
|
|
148
150
|
): Map<K, Set<V>>;
|
|
149
151
|
```
|
|
150
152
|
|
|
151
|
-
### `toMapValues
|
|
153
|
+
### `toMapValues`
|
|
152
154
|
|
|
153
|
-
|
|
155
|
+
Group by key, then aggregate each group's items using a value selector.
|
|
154
156
|
|
|
155
157
|
```typescript
|
|
156
158
|
toMapValues<K, V>(
|
|
@@ -159,9 +161,9 @@ toMapValues<K, V>(
|
|
|
159
161
|
): Map<K, V>;
|
|
160
162
|
```
|
|
161
163
|
|
|
162
|
-
### `toObject
|
|
164
|
+
### `toObject`
|
|
163
165
|
|
|
164
|
-
|
|
166
|
+
Convert to a plain object `Record<string, V>`. Throws `ArgumentError` on duplicate keys.
|
|
165
167
|
|
|
166
168
|
```typescript
|
|
167
169
|
toObject(keySelector: (item: T, index: number) => string): Record<string, T>;
|
|
@@ -171,68 +173,70 @@ toObject<V>(
|
|
|
171
173
|
): Record<string, V>;
|
|
172
174
|
```
|
|
173
175
|
|
|
174
|
-
### `toTree
|
|
176
|
+
### `toTree`
|
|
175
177
|
|
|
176
|
-
|
|
178
|
+
Convert a flat array to a tree structure. Items where `parentKey` is null/undefined become root nodes. Uses O(n) Map-based indexing internally.
|
|
177
179
|
|
|
178
180
|
```typescript
|
|
179
181
|
toTree<K extends keyof T, P extends keyof T>(keyProp: K, parentKey: P): TreeArray<T>[];
|
|
180
182
|
```
|
|
181
183
|
|
|
182
|
-
|
|
183
|
-
const items = [
|
|
184
|
-
{ id: 1, parentId: undefined, name: "root" },
|
|
185
|
-
{ id: 2, parentId: 1, name: "child" },
|
|
186
|
-
];
|
|
187
|
-
const tree = items.toTree("id", "parentId");
|
|
188
|
-
// [{ id: 1, name: "root", children: [{ id: 2, name: "child", children: [] }] }]
|
|
189
|
-
```
|
|
190
|
-
|
|
191
|
-
### `distinct(options?)`
|
|
184
|
+
### `distinct`
|
|
192
185
|
|
|
193
|
-
|
|
186
|
+
Remove duplicates (returns a new array).
|
|
194
187
|
|
|
195
188
|
```typescript
|
|
196
|
-
distinct(
|
|
197
|
-
matchAddress?: boolean;
|
|
198
|
-
|
|
199
|
-
}): T[];
|
|
189
|
+
distinct(
|
|
190
|
+
options?: boolean | { matchAddress?: boolean; keyFn?: (item: T) => string | number },
|
|
191
|
+
): T[];
|
|
200
192
|
```
|
|
201
193
|
|
|
202
194
|
| Option | Description |
|
|
203
195
|
|--------|-------------|
|
|
204
|
-
| `true` or `{ matchAddress: true }` |
|
|
205
|
-
| `{ keyFn }` |
|
|
206
|
-
|
|
|
196
|
+
| `true` or `{ matchAddress: true }` | Reference equality (Set-based, O(n)) |
|
|
197
|
+
| `{ keyFn }` | Custom key function (O(n)) |
|
|
198
|
+
| Default (no options) | Deep equality for objects (O(n^2)), type-based for primitives (O(n)) |
|
|
207
199
|
|
|
208
|
-
### `orderBy
|
|
200
|
+
### `orderBy`
|
|
209
201
|
|
|
210
|
-
|
|
202
|
+
Sort ascending (returns a new array). Supports `string`, `number`, `DateTime`, `DateOnly`, `Time`.
|
|
211
203
|
|
|
212
204
|
```typescript
|
|
213
205
|
orderBy(selector?: (item: T) => string | number | DateTime | DateOnly | Time | undefined): T[];
|
|
206
|
+
```
|
|
207
|
+
|
|
208
|
+
### `orderByDesc`
|
|
209
|
+
|
|
210
|
+
Sort descending (returns a new array).
|
|
211
|
+
|
|
212
|
+
```typescript
|
|
214
213
|
orderByDesc(selector?: (item: T) => string | number | DateTime | DateOnly | Time | undefined): T[];
|
|
215
214
|
```
|
|
216
215
|
|
|
217
|
-
### `diffs
|
|
216
|
+
### `diffs`
|
|
218
217
|
|
|
219
|
-
|
|
218
|
+
Compare this array (source) with a target array. Returns a list of insert/delete/update operations.
|
|
220
219
|
|
|
221
220
|
```typescript
|
|
222
|
-
diffs<P>(target: P[],
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
221
|
+
diffs<P>(target: P[]): ArrayDiffsResult<T, P>[];
|
|
222
|
+
diffs<P extends Record<string, unknown>>(
|
|
223
|
+
target: P[],
|
|
224
|
+
options: { keys: string[]; excludes?: string[] },
|
|
225
|
+
): ArrayDiffsResult<T, P>[];
|
|
226
|
+
diffs<P extends Record<string, unknown>>(
|
|
227
|
+
target: P[],
|
|
228
|
+
options: { excludes: string[] },
|
|
229
|
+
): ArrayDiffsResult<T, P>[];
|
|
226
230
|
```
|
|
227
231
|
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
+
| Option | Description |
|
|
233
|
+
|--------|-------------|
|
|
234
|
+
| `keys` | Properties to use for matching source to target items |
|
|
235
|
+
| `excludes` | Properties to ignore in equality comparison |
|
|
232
236
|
|
|
233
|
-
### `oneWayDiffs
|
|
237
|
+
### `oneWayDiffs`
|
|
234
238
|
|
|
235
|
-
One-way diff:
|
|
239
|
+
One-way diff: compare this array against original items. Returns create/update/same results.
|
|
236
240
|
|
|
237
241
|
```typescript
|
|
238
242
|
oneWayDiffs<K extends keyof T>(
|
|
@@ -242,160 +246,124 @@ oneWayDiffs<K extends keyof T>(
|
|
|
242
246
|
): ArrayOneWayDiffResult<T>[];
|
|
243
247
|
```
|
|
244
248
|
|
|
245
|
-
|
|
249
|
+
### `merge`
|
|
246
250
|
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
Merges two arrays using deep merge on matched items and appends unmatched target items.
|
|
251
|
+
Merge this array with a target array. Matched items are deep-merged; unmatched target items are appended.
|
|
250
252
|
|
|
251
253
|
```typescript
|
|
252
|
-
merge<P>(target: P[]
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
254
|
+
merge<P>(target: P[]): (T | P | (T & P))[];
|
|
255
|
+
merge<P extends Record<string, unknown>>(
|
|
256
|
+
target: P[],
|
|
257
|
+
options: { keys: string[]; excludes?: string[] },
|
|
258
|
+
): (T | P | (T & P))[];
|
|
259
|
+
merge<P extends Record<string, unknown>>(
|
|
260
|
+
target: P[],
|
|
261
|
+
options: { excludes: string[] },
|
|
262
|
+
): (T | P | (T & P))[];
|
|
256
263
|
```
|
|
257
264
|
|
|
258
|
-
### `sum
|
|
265
|
+
### `sum`
|
|
259
266
|
|
|
260
|
-
|
|
267
|
+
Sum of elements. If no selector is provided, elements must be numbers.
|
|
261
268
|
|
|
262
269
|
```typescript
|
|
263
270
|
sum(selector?: (item: T, index: number) => number): number;
|
|
264
271
|
```
|
|
265
272
|
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
Returns the minimum/maximum element. Returns `undefined` for empty arrays.
|
|
273
|
+
Returns `0` for empty arrays.
|
|
269
274
|
|
|
270
|
-
|
|
271
|
-
min(selector?: (item: T, index: number) => string | number): string | number | undefined;
|
|
272
|
-
max(selector?: (item: T, index: number) => string | number): string | number | undefined;
|
|
273
|
-
```
|
|
275
|
+
### `min`
|
|
274
276
|
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
Returns a new array with elements in random order (Fisher-Yates algorithm).
|
|
277
|
+
Minimum element or minimum selected value.
|
|
278
278
|
|
|
279
279
|
```typescript
|
|
280
|
-
|
|
280
|
+
min(): T extends number | string ? T | undefined : never;
|
|
281
|
+
min<P extends number | string>(selector?: (item: T, index: number) => P): P | undefined;
|
|
281
282
|
```
|
|
282
283
|
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
These methods mutate the original array in place.
|
|
284
|
+
### `max`
|
|
286
285
|
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
Removes duplicates from the original array in place. Same options as `distinct()`.
|
|
286
|
+
Maximum element or maximum selected value.
|
|
290
287
|
|
|
291
288
|
```typescript
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
keyFn?: (item: T) => string | number;
|
|
295
|
-
}): T[];
|
|
289
|
+
max(): T extends number | string ? T | undefined : never;
|
|
290
|
+
max<P extends number | string>(selector?: (item: T, index: number) => P): P | undefined;
|
|
296
291
|
```
|
|
297
292
|
|
|
298
|
-
### `
|
|
293
|
+
### `shuffle`
|
|
299
294
|
|
|
300
|
-
|
|
295
|
+
Return a new array with elements in random order (Fisher-Yates algorithm).
|
|
301
296
|
|
|
302
297
|
```typescript
|
|
303
|
-
|
|
304
|
-
orderByDescThis(selector?: (item: T) => string | number | DateTime | DateOnly | Time | undefined): T[];
|
|
298
|
+
shuffle(): T[];
|
|
305
299
|
```
|
|
306
300
|
|
|
307
|
-
|
|
301
|
+
---
|
|
308
302
|
|
|
309
|
-
|
|
303
|
+
## Mutable Array Extensions
|
|
310
304
|
|
|
311
|
-
|
|
312
|
-
insert(index: number, ...items: T[]): this;
|
|
313
|
-
```
|
|
305
|
+
These methods mutate the original array in-place.
|
|
314
306
|
|
|
315
|
-
### `
|
|
307
|
+
### `distinctThis`
|
|
316
308
|
|
|
317
|
-
|
|
309
|
+
Remove duplicates in-place. Same options as `distinct`.
|
|
318
310
|
|
|
319
311
|
```typescript
|
|
320
|
-
|
|
321
|
-
|
|
312
|
+
distinctThis(
|
|
313
|
+
options?: boolean | { matchAddress?: boolean; keyFn?: (item: T) => string | number },
|
|
314
|
+
): T[];
|
|
322
315
|
```
|
|
323
316
|
|
|
324
|
-
### `
|
|
317
|
+
### `orderByThis`
|
|
325
318
|
|
|
326
|
-
|
|
319
|
+
Sort ascending in-place.
|
|
327
320
|
|
|
328
321
|
```typescript
|
|
329
|
-
|
|
322
|
+
orderByThis(selector?: (item: T) => string | number | DateTime | DateOnly | Time | undefined): T[];
|
|
330
323
|
```
|
|
331
324
|
|
|
332
|
-
### `
|
|
325
|
+
### `orderByDescThis`
|
|
333
326
|
|
|
334
|
-
|
|
327
|
+
Sort descending in-place.
|
|
335
328
|
|
|
336
329
|
```typescript
|
|
337
|
-
|
|
330
|
+
orderByDescThis(selector?: (item: T) => string | number | DateTime | DateOnly | Time | undefined): T[];
|
|
338
331
|
```
|
|
339
332
|
|
|
340
|
-
|
|
333
|
+
### `insert`
|
|
341
334
|
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
Adds multiple values at once. Returns `this` for chaining.
|
|
335
|
+
Insert items at a given index. Mutates the array.
|
|
345
336
|
|
|
346
337
|
```typescript
|
|
347
|
-
|
|
338
|
+
insert(index: number, ...items: T[]): this;
|
|
348
339
|
```
|
|
349
340
|
|
|
350
|
-
### `
|
|
341
|
+
### `remove`
|
|
351
342
|
|
|
352
|
-
|
|
343
|
+
Remove items by value or predicate. Mutates the array.
|
|
353
344
|
|
|
354
345
|
```typescript
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
| Parameter | Type | Description |
|
|
359
|
-
|-----------|------|-------------|
|
|
360
|
-
| `value` | `T` | Value to toggle |
|
|
361
|
-
| `addOrDel` | `"add" \| "del" \| undefined` | Force add or delete. Omit for auto-toggle |
|
|
362
|
-
|
|
363
|
-
```typescript
|
|
364
|
-
const set = new Set([1, 2, 3]);
|
|
365
|
-
set.toggle(2); // removes 2 -> {1, 3}
|
|
366
|
-
set.toggle(4); // adds 4 -> {1, 3, 4}
|
|
367
|
-
set.toggle(5, "add"); // force add -> {1, 3, 4, 5}
|
|
368
|
-
set.toggle(5, "del"); // force del -> {1, 3, 4}
|
|
346
|
+
remove(item: T): this;
|
|
347
|
+
remove(selector: (item: T, index: number) => boolean): this;
|
|
369
348
|
```
|
|
370
349
|
|
|
371
|
-
|
|
350
|
+
### `toggle`
|
|
372
351
|
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
Returns the value for `key`. If the key does not exist, creates it with `newValue` (or calls `newValue` as a factory function if it is a function).
|
|
352
|
+
Toggle an item: remove if present, add (push) if absent.
|
|
376
353
|
|
|
377
354
|
```typescript
|
|
378
|
-
|
|
379
|
-
getOrCreate(key: K, newValueFn: () => V): V;
|
|
380
|
-
```
|
|
381
|
-
|
|
382
|
-
**Note:** If `V` is a function type, wrap it in a factory to avoid it being called:
|
|
383
|
-
```typescript
|
|
384
|
-
fnMap.getOrCreate("key", () => myFunction);
|
|
355
|
+
toggle(item: T): this;
|
|
385
356
|
```
|
|
386
357
|
|
|
387
|
-
### `
|
|
358
|
+
### `clear`
|
|
388
359
|
|
|
389
|
-
|
|
360
|
+
Remove all items from the array.
|
|
390
361
|
|
|
391
362
|
```typescript
|
|
392
|
-
|
|
363
|
+
clear(): this;
|
|
393
364
|
```
|
|
394
365
|
|
|
395
|
-
|
|
396
|
-
const counts = new Map<string, number>();
|
|
397
|
-
counts.update("hits", (v) => (v ?? 0) + 1);
|
|
398
|
-
```
|
|
366
|
+
---
|
|
399
367
|
|
|
400
368
|
## Exported Types
|
|
401
369
|
|
|
@@ -428,3 +396,42 @@ type TreeArray<TNode> = TNode & { children: TreeArray<TNode>[] };
|
|
|
428
396
|
```typescript
|
|
429
397
|
type ComparableType = string | number | boolean | DateTime | DateOnly | Time | undefined;
|
|
430
398
|
```
|
|
399
|
+
|
|
400
|
+
---
|
|
401
|
+
|
|
402
|
+
## Exported Helper Functions
|
|
403
|
+
|
|
404
|
+
### `toComparable`
|
|
405
|
+
|
|
406
|
+
Convert DateTime, DateOnly, or Time to their tick value for comparison. Primitives pass through unchanged.
|
|
407
|
+
|
|
408
|
+
```typescript
|
|
409
|
+
function toComparable(value: ComparableType): string | number | boolean | undefined;
|
|
410
|
+
```
|
|
411
|
+
|
|
412
|
+
### `compareForOrder`
|
|
413
|
+
|
|
414
|
+
Comparison function for sorting. Handles null/undefined (sorted first in ascending, last in descending). Supports string (locale-aware), number, and boolean.
|
|
415
|
+
|
|
416
|
+
```typescript
|
|
417
|
+
function compareForOrder(pp: ComparableType, pn: ComparableType, desc: boolean): number;
|
|
418
|
+
```
|
|
419
|
+
|
|
420
|
+
| Parameter | Type | Description |
|
|
421
|
+
|-----------|------|-------------|
|
|
422
|
+
| `pp` | `ComparableType` | First value |
|
|
423
|
+
| `pn` | `ComparableType` | Second value |
|
|
424
|
+
| `desc` | `boolean` | `true` for descending order |
|
|
425
|
+
|
|
426
|
+
**Returns:** Negative if `pp` should come first, positive if `pn` should come first, `0` if equal.
|
|
427
|
+
|
|
428
|
+
### `getDistinctIndices`
|
|
429
|
+
|
|
430
|
+
Get the set of indices to keep for deduplication. Handles all strategies: address comparison, custom key function, and deep equality.
|
|
431
|
+
|
|
432
|
+
```typescript
|
|
433
|
+
function getDistinctIndices<T>(
|
|
434
|
+
items: readonly T[],
|
|
435
|
+
options?: boolean | { matchAddress?: boolean; keyFn?: (item: T) => string | number },
|
|
436
|
+
): Set<number>;
|
|
437
|
+
```
|
package/docs/env.md
CHANGED
|
@@ -1,10 +1,8 @@
|
|
|
1
1
|
# Environment
|
|
2
2
|
|
|
3
|
-
Unified access to environment variables from both `import.meta.env` (Vite/browser) and `process.env` (Node.js). `process.env` takes precedence when both are available.
|
|
4
|
-
|
|
5
3
|
## `parseBoolEnv`
|
|
6
4
|
|
|
7
|
-
|
|
5
|
+
Parse a value to boolean. Recognizes `"true"`, `"1"`, `"yes"`, `"on"` (case-insensitive) as `true`; everything else is `false`.
|
|
8
6
|
|
|
9
7
|
```typescript
|
|
10
8
|
function parseBoolEnv(value: unknown): boolean;
|
|
@@ -12,22 +10,13 @@ function parseBoolEnv(value: unknown): boolean;
|
|
|
12
10
|
|
|
13
11
|
| Parameter | Type | Description |
|
|
14
12
|
|-----------|------|-------------|
|
|
15
|
-
| `value` | `unknown` | The value to parse |
|
|
13
|
+
| `value` | `unknown` | The value to parse. Converted to string internally. |
|
|
16
14
|
|
|
17
15
|
**Returns:** `boolean`
|
|
18
16
|
|
|
19
|
-
```typescript
|
|
20
|
-
parseBoolEnv("true"); // true
|
|
21
|
-
parseBoolEnv("1"); // true
|
|
22
|
-
parseBoolEnv("yes"); // true
|
|
23
|
-
parseBoolEnv("on"); // true
|
|
24
|
-
parseBoolEnv("false"); // false
|
|
25
|
-
parseBoolEnv(undefined); // false
|
|
26
|
-
```
|
|
27
|
-
|
|
28
17
|
## `env`
|
|
29
18
|
|
|
30
|
-
|
|
19
|
+
Unified environment variable object. Merges `import.meta.env` and `process.env` (process.env takes precedence). `DEV` is auto-parsed as boolean, `VER` is typed as optional string.
|
|
31
20
|
|
|
32
21
|
```typescript
|
|
33
22
|
const env: {
|
|
@@ -37,16 +26,8 @@ const env: {
|
|
|
37
26
|
};
|
|
38
27
|
```
|
|
39
28
|
|
|
40
|
-
|
|
|
41
|
-
|
|
42
|
-
| `DEV` | `boolean` | Whether in development mode
|
|
43
|
-
| `VER` | `string \| undefined` |
|
|
44
|
-
| `[key]` | `unknown` | Any other environment variable |
|
|
45
|
-
|
|
46
|
-
```typescript
|
|
47
|
-
import { env } from "@simplysm/core-common";
|
|
48
|
-
|
|
49
|
-
if (env.DEV) {
|
|
50
|
-
// development-only logic
|
|
51
|
-
}
|
|
52
|
-
```
|
|
29
|
+
| Field | Type | Description |
|
|
30
|
+
|-------|------|-------------|
|
|
31
|
+
| `DEV` | `boolean` | Whether the app is running in development mode. Parsed from raw `DEV` env var via `parseBoolEnv`. |
|
|
32
|
+
| `VER` | `string \| undefined` | Application version string, if set. |
|
|
33
|
+
| `[key: string]` | `unknown` | Any other environment variable. |
|