happy-rusty 1.5.0 → 1.6.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/CHANGELOG.md +206 -0
- package/README.cn.md +265 -19
- package/README.md +261 -21
- package/dist/main.cjs +382 -32
- package/dist/main.cjs.map +1 -1
- package/dist/main.mjs +374 -33
- package/dist/main.mjs.map +1 -1
- package/dist/types.d.ts +2002 -52
- package/package.json +37 -24
- package/dist/types.d.ts.map +0 -1
- package/docs/README.md +0 -47
- package/docs/functions/Err.md +0 -46
- package/docs/functions/Ok.md +0 -70
- package/docs/functions/Some.md +0 -45
- package/docs/functions/isOption.md +0 -35
- package/docs/functions/isResult.md +0 -36
- package/docs/functions/promiseToAsyncResult.md +0 -50
- package/docs/interfaces/None.md +0 -979
- package/docs/interfaces/Option.md +0 -857
- package/docs/interfaces/Result.md +0 -903
- package/docs/type-aliases/AsyncIOResult.md +0 -24
- package/docs/type-aliases/AsyncOption.md +0 -24
- package/docs/type-aliases/AsyncResult.md +0 -25
- package/docs/type-aliases/AsyncVoidIOResult.md +0 -17
- package/docs/type-aliases/AsyncVoidResult.md +0 -23
- package/docs/type-aliases/IOResult.md +0 -24
- package/docs/type-aliases/VoidIOResult.md +0 -17
- package/docs/type-aliases/VoidResult.md +0 -23
- package/docs/variables/None.md +0 -18
- package/docs/variables/RESULT_FALSE.md +0 -18
- package/docs/variables/RESULT_TRUE.md +0 -18
- package/docs/variables/RESULT_VOID.md +0 -17
- package/docs/variables/RESULT_ZERO.md +0 -18
- package/src/enum/constants.ts +0 -30
- package/src/enum/core.ts +0 -635
- package/src/enum/defines.ts +0 -45
- package/src/enum/extensions.ts +0 -31
- package/src/enum/mod.ts +0 -6
- package/src/enum/prelude.ts +0 -619
- package/src/enum/symbols.ts +0 -9
- package/src/enum/utils.ts +0 -27
- package/src/mod.ts +0 -1
package/dist/types.d.ts
CHANGED
|
@@ -1,9 +1,36 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* @fileoverview
|
|
3
|
+
* Internal symbols used to identify `Option` and `Result` type variants.
|
|
4
|
+
*
|
|
5
|
+
* These symbols are used as property keys to distinguish between `Some`/`None` and `Ok`/`Err` variants.
|
|
6
|
+
* They provide a reliable way to identify the variant of an `Option` or `Result` instance without
|
|
7
|
+
* relying on method calls or duck typing.
|
|
8
|
+
*
|
|
9
|
+
* Note: These symbols are internal implementation details and are not exported as part of the public API.
|
|
10
|
+
* Use the `isOption` and `isResult` utility functions for type checking instead.
|
|
11
|
+
*/
|
|
12
|
+
/**
|
|
13
|
+
* A unique symbol used as a property key to identify the variant of an `Option` instance.
|
|
14
|
+
*
|
|
15
|
+
* When accessed on an `Option`, returns `'Some'` if the Option contains a value,
|
|
16
|
+
* or `'None'` if it represents the absence of a value.
|
|
17
|
+
*
|
|
18
|
+
* This symbol is used internally by the `isOption` utility function to verify
|
|
19
|
+
* that an object is a valid `Option` instance.
|
|
20
|
+
*
|
|
21
|
+
* @internal
|
|
3
22
|
*/
|
|
4
23
|
declare const OptionKindSymbol: unique symbol;
|
|
5
24
|
/**
|
|
6
|
-
*
|
|
25
|
+
* A unique symbol used as a property key to identify the variant of a `Result` instance.
|
|
26
|
+
*
|
|
27
|
+
* When accessed on a `Result`, returns `'Ok'` if the Result represents success,
|
|
28
|
+
* or `'Err'` if it represents failure.
|
|
29
|
+
*
|
|
30
|
+
* This symbol is used internally by the `isResult` utility function to verify
|
|
31
|
+
* that an object is a valid `Result` instance.
|
|
32
|
+
*
|
|
33
|
+
* @internal
|
|
7
34
|
*/
|
|
8
35
|
declare const ResultKindSymbol: unique symbol;
|
|
9
36
|
|
|
@@ -30,15 +57,31 @@ pub enum Option<T> {
|
|
|
30
57
|
*/
|
|
31
58
|
interface Option<T> {
|
|
32
59
|
/**
|
|
33
|
-
*
|
|
60
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
61
|
+
* Returns `'Option'` so that `Object.prototype.toString.call(option)` produces `'[object Option]'`.
|
|
62
|
+
*
|
|
63
|
+
* This enables reliable type identification even across different execution contexts (e.g., iframes, different module instances).
|
|
34
64
|
*
|
|
35
|
-
* @
|
|
65
|
+
* @example
|
|
66
|
+
* ```ts
|
|
67
|
+
* const x = Some(5);
|
|
68
|
+
* console.log(Object.prototype.toString.call(x)); // '[object Option]'
|
|
69
|
+
* ```
|
|
70
|
+
*
|
|
71
|
+
* @internal
|
|
36
72
|
*/
|
|
37
73
|
readonly [Symbol.toStringTag]: 'Option';
|
|
38
74
|
/**
|
|
39
|
-
*
|
|
75
|
+
* A unique symbol property used to identify the variant of this `Option`.
|
|
76
|
+
* Returns `'Some'` if the Option contains a value, or `'None'` if it represents absence.
|
|
77
|
+
*
|
|
78
|
+
* This is used internally by the `isOption` utility function to verify that an object is a valid `Option` instance,
|
|
79
|
+
* and to distinguish between `Some` and `None` variants without calling methods.
|
|
40
80
|
*
|
|
41
|
-
*
|
|
81
|
+
* Note: The symbol itself is not exported as part of the public API.
|
|
82
|
+
* Use the `isOption` utility function or the `isSome()`/`isNone()` methods for type checking.
|
|
83
|
+
*
|
|
84
|
+
* @internal
|
|
42
85
|
*/
|
|
43
86
|
readonly [OptionKindSymbol]: 'Some' | 'None';
|
|
44
87
|
/**
|
|
@@ -46,21 +89,81 @@ interface Option<T> {
|
|
|
46
89
|
*/
|
|
47
90
|
/**
|
|
48
91
|
* Returns `true` if the Option is a `Some` value.
|
|
92
|
+
* @example
|
|
93
|
+
* ```ts
|
|
94
|
+
* const x = Some(2);
|
|
95
|
+
* console.log(x.isSome()); // true
|
|
96
|
+
*
|
|
97
|
+
* const y = None;
|
|
98
|
+
* console.log(y.isSome()); // false
|
|
99
|
+
* ```
|
|
49
100
|
*/
|
|
50
101
|
isSome(): boolean;
|
|
51
102
|
/**
|
|
52
103
|
* Returns `true` if the Option is a `None` value.
|
|
104
|
+
* @example
|
|
105
|
+
* ```ts
|
|
106
|
+
* const x = Some(2);
|
|
107
|
+
* console.log(x.isNone()); // false
|
|
108
|
+
*
|
|
109
|
+
* const y = None;
|
|
110
|
+
* console.log(y.isNone()); // true
|
|
111
|
+
* ```
|
|
53
112
|
*/
|
|
54
113
|
isNone(): boolean;
|
|
55
114
|
/**
|
|
56
115
|
* Returns `true` if the Option is a `Some` value and the predicate returns `true` for the contained value.
|
|
57
116
|
* @param predicate - A function that takes the contained value and returns a boolean.
|
|
117
|
+
* @example
|
|
118
|
+
* ```ts
|
|
119
|
+
* const x = Some(2);
|
|
120
|
+
* console.log(x.isSomeAnd(v => v > 1)); // true
|
|
121
|
+
* console.log(x.isSomeAnd(v => v > 5)); // false
|
|
122
|
+
* ```
|
|
58
123
|
*/
|
|
59
124
|
isSomeAnd(predicate: (value: T) => boolean): boolean;
|
|
60
125
|
/**
|
|
61
126
|
* Asynchronous version of `isSomeAnd`.
|
|
127
|
+
* @param predicate - An async function that takes the contained value and returns a `Promise<boolean>`.
|
|
128
|
+
* @returns A promise that resolves to `true` if the Option is `Some` and the predicate resolves to `true`.
|
|
129
|
+
* @see isSomeAnd
|
|
130
|
+
* @example
|
|
131
|
+
* ```ts
|
|
132
|
+
* const x = Some(2);
|
|
133
|
+
* await x.isSomeAndAsync(async v => v > 1); // true
|
|
134
|
+
* ```
|
|
62
135
|
*/
|
|
63
136
|
isSomeAndAsync(predicate: (value: T) => Promise<boolean>): Promise<boolean>;
|
|
137
|
+
/**
|
|
138
|
+
* Returns `true` if the Option is `None`, or the predicate returns `true` for the contained value.
|
|
139
|
+
* @param predicate - A function that takes the contained value and returns a boolean.
|
|
140
|
+
* @see isSomeAnd
|
|
141
|
+
* @example
|
|
142
|
+
* ```ts
|
|
143
|
+
* const x = Some(2);
|
|
144
|
+
* console.log(x.isNoneOr(v => v > 1)); // true
|
|
145
|
+
* console.log(x.isNoneOr(v => v > 5)); // false
|
|
146
|
+
*
|
|
147
|
+
* const y = None;
|
|
148
|
+
* console.log(y.isNoneOr(v => v > 5)); // true (always true for None)
|
|
149
|
+
* ```
|
|
150
|
+
*/
|
|
151
|
+
isNoneOr(predicate: (value: T) => boolean): boolean;
|
|
152
|
+
/**
|
|
153
|
+
* Asynchronous version of `isNoneOr`.
|
|
154
|
+
* @param predicate - An async function that takes the contained value and returns a `Promise<boolean>`.
|
|
155
|
+
* @returns A promise that resolves to `true` if the Option is `None` or the predicate resolves to `true`.
|
|
156
|
+
* @see isNoneOr
|
|
157
|
+
* @example
|
|
158
|
+
* ```ts
|
|
159
|
+
* const x = Some(2);
|
|
160
|
+
* await x.isNoneOrAsync(async v => v > 1); // true
|
|
161
|
+
*
|
|
162
|
+
* const y = None;
|
|
163
|
+
* await y.isNoneOrAsync(async v => v > 5); // true
|
|
164
|
+
* ```
|
|
165
|
+
*/
|
|
166
|
+
isNoneOrAsync(predicate: (value: T) => Promise<boolean>): Promise<boolean>;
|
|
64
167
|
/**
|
|
65
168
|
* These methods extract the contained value in an `Option<T>` when it is the `Some` variant:
|
|
66
169
|
*/
|
|
@@ -68,25 +171,67 @@ interface Option<T> {
|
|
|
68
171
|
* Returns the contained `Some` value, with a provided error message if the value is a `None`.
|
|
69
172
|
* @param msg - The error message to provide if the value is a `None`.
|
|
70
173
|
* @throws {TypeError} Throws an error with the provided message if the Option is a `None`.
|
|
174
|
+
* @see unwrap
|
|
175
|
+
* @example
|
|
176
|
+
* ```ts
|
|
177
|
+
* const x = Some(5);
|
|
178
|
+
* console.log(x.expect('value should exist')); // 5
|
|
179
|
+
*
|
|
180
|
+
* const y = None;
|
|
181
|
+
* y.expect('value should exist'); // throws TypeError: value should exist
|
|
182
|
+
* ```
|
|
71
183
|
*/
|
|
72
184
|
expect(msg: string): T;
|
|
73
185
|
/**
|
|
74
186
|
* Returns the contained `Some` value.
|
|
75
187
|
* @throws {TypeError} Throws an error if the value is a `None`.
|
|
188
|
+
* @see expect
|
|
189
|
+
* @see unwrapOr
|
|
190
|
+
* @example
|
|
191
|
+
* ```ts
|
|
192
|
+
* const x = Some(5);
|
|
193
|
+
* console.log(x.unwrap()); // 5
|
|
194
|
+
*
|
|
195
|
+
* const y = None;
|
|
196
|
+
* y.unwrap(); // throws TypeError
|
|
197
|
+
* ```
|
|
76
198
|
*/
|
|
77
199
|
unwrap(): T;
|
|
78
200
|
/**
|
|
79
201
|
* Returns the contained `Some` value or a provided default.
|
|
80
202
|
* @param defaultValue - The value to return if the Option is a `None`.
|
|
203
|
+
* @see unwrapOrElse
|
|
204
|
+
* @example
|
|
205
|
+
* ```ts
|
|
206
|
+
* const x = Some(5);
|
|
207
|
+
* console.log(x.unwrapOr(10)); // 5
|
|
208
|
+
*
|
|
209
|
+
* const y = None;
|
|
210
|
+
* console.log(y.unwrapOr(10)); // 10
|
|
211
|
+
* ```
|
|
81
212
|
*/
|
|
82
213
|
unwrapOr(defaultValue: T): T;
|
|
83
214
|
/**
|
|
84
215
|
* Returns the contained `Some` value or computes it from a closure.
|
|
85
216
|
* @param fn - A function that returns the default value.
|
|
217
|
+
* @see unwrapOr
|
|
218
|
+
* @example
|
|
219
|
+
* ```ts
|
|
220
|
+
* const x = None;
|
|
221
|
+
* console.log(x.unwrapOrElse(() => 10)); // 10
|
|
222
|
+
* ```
|
|
86
223
|
*/
|
|
87
224
|
unwrapOrElse(fn: () => T): T;
|
|
88
225
|
/**
|
|
89
226
|
* Asynchronous version of `unwrapOrElse`.
|
|
227
|
+
* @param fn - An async function that returns a `Promise<T>` as the default value.
|
|
228
|
+
* @returns A promise that resolves to the contained value or the result of the async function.
|
|
229
|
+
* @see unwrapOrElse
|
|
230
|
+
* @example
|
|
231
|
+
* ```ts
|
|
232
|
+
* const x = None;
|
|
233
|
+
* await x.unwrapOrElseAsync(async () => 10); // 10
|
|
234
|
+
* ```
|
|
90
235
|
*/
|
|
91
236
|
unwrapOrElseAsync(fn: () => Promise<T>): Promise<T>;
|
|
92
237
|
/**
|
|
@@ -96,23 +241,49 @@ interface Option<T> {
|
|
|
96
241
|
* Transforms the `Option<T>` into a `Result<T, E>`, mapping `Some(v)` to `Ok(v)` and `None` to `Err(err)`.
|
|
97
242
|
* @typeParam E - The type of the error value in the `Err` variant of the resulting `Result`.
|
|
98
243
|
* @param error - The error value to use if the Option is a `None`.
|
|
244
|
+
* @see okOrElse
|
|
245
|
+
* @example
|
|
246
|
+
* ```ts
|
|
247
|
+
* const x = Some(5);
|
|
248
|
+
* console.log(x.okOr('error').isOk()); // true
|
|
249
|
+
*
|
|
250
|
+
* const y = None;
|
|
251
|
+
* console.log(y.okOr('error').unwrapErr()); // 'error'
|
|
252
|
+
* ```
|
|
99
253
|
*/
|
|
100
254
|
okOr<E>(error: E): Result<T, E>;
|
|
101
255
|
/**
|
|
102
256
|
* Transforms the `Option<T>` into a `Result<T, E>`, mapping `Some(v)` to `Ok(v)` and `None` to `Err(err())`.
|
|
103
257
|
* @typeParam E - The type of the error value in the `Err` variant of the resulting `Result`.
|
|
104
258
|
* @param err - A function that returns the error value.
|
|
259
|
+
* @see okOr
|
|
260
|
+
* @example
|
|
261
|
+
* ```ts
|
|
262
|
+
* const x = None;
|
|
263
|
+
* console.log(x.okOrElse(() => 'error').unwrapErr()); // 'error'
|
|
264
|
+
* ```
|
|
105
265
|
*/
|
|
106
266
|
okOrElse<E>(err: () => E): Result<T, E>;
|
|
107
267
|
/**
|
|
108
268
|
* Transposes an `Option` of a `Result` into a `Result` of an `Option`.
|
|
109
|
-
* @typeParam
|
|
269
|
+
* @typeParam U - The type of the success value in the `Ok` variant of the `Result`.
|
|
110
270
|
* @typeParam E - The type of the error value in the `Err` variant of the `Result`.
|
|
111
271
|
* @returns `Ok` containing `Some` if the Option is a `Some` containing `Ok`,
|
|
112
272
|
* `Err` containing the error if the Option is a `Some` containing `Err`,
|
|
113
273
|
* `Ok` containing `None` if the Option is `None`.
|
|
274
|
+
* @example
|
|
275
|
+
* ```ts
|
|
276
|
+
* const x = Some(Ok(5));
|
|
277
|
+
* console.log(x.transpose().unwrap().unwrap()); // 5
|
|
278
|
+
*
|
|
279
|
+
* const y = Some(Err('error'));
|
|
280
|
+
* console.log(y.transpose().unwrapErr()); // 'error'
|
|
281
|
+
*
|
|
282
|
+
* const z: Option<Result<number, string>> = None;
|
|
283
|
+
* console.log(z.transpose().unwrap().isNone()); // true
|
|
284
|
+
* ```
|
|
114
285
|
*/
|
|
115
|
-
transpose<
|
|
286
|
+
transpose<U, E>(this: Option<Result<U, E>>): Result<Option<U>, E>;
|
|
116
287
|
/**
|
|
117
288
|
* These methods transform the `Some` variant:
|
|
118
289
|
*/
|
|
@@ -121,17 +292,41 @@ interface Option<T> {
|
|
|
121
292
|
* - `Some(t)` if predicate returns `true` (where `t` is the wrapped value), and
|
|
122
293
|
* - `None` if predicate returns `false`.
|
|
123
294
|
* @param predicate - A function that takes the contained value and returns a boolean.
|
|
295
|
+
* @example
|
|
296
|
+
* ```ts
|
|
297
|
+
* const x = Some(4);
|
|
298
|
+
* console.log(x.filter(v => v > 2).isSome()); // true
|
|
299
|
+
* console.log(x.filter(v => v > 5).isNone()); // true
|
|
300
|
+
* ```
|
|
124
301
|
*/
|
|
125
302
|
filter(predicate: (value: T) => boolean): Option<T>;
|
|
126
303
|
/**
|
|
127
|
-
* Converts from `Option<Option<
|
|
304
|
+
* Converts from `Option<Option<U>>` to `Option<U>`.
|
|
305
|
+
* @typeParam U - The type of the value contained in the inner `Option`.
|
|
128
306
|
* @returns `None` if the Option is `None`, otherwise returns the contained `Option`.
|
|
307
|
+
* @example
|
|
308
|
+
* ```ts
|
|
309
|
+
* const x = Some(Some(5));
|
|
310
|
+
* console.log(x.flatten().unwrap()); // 5
|
|
311
|
+
*
|
|
312
|
+
* const y = Some(None);
|
|
313
|
+
* console.log(y.flatten().isNone()); // true
|
|
314
|
+
* ```
|
|
129
315
|
*/
|
|
130
|
-
flatten<
|
|
316
|
+
flatten<U>(this: Option<Option<U>>): Option<U>;
|
|
131
317
|
/**
|
|
132
318
|
* Maps an `Option<T>` to `Option<U>` by applying a function to a contained value.
|
|
133
319
|
* @typeParam U - The type of the value returned by the map function.
|
|
134
320
|
* @param fn - A function that takes the contained value and returns a new value.
|
|
321
|
+
* @see andThen
|
|
322
|
+
* @example
|
|
323
|
+
* ```ts
|
|
324
|
+
* const x = Some(5);
|
|
325
|
+
* console.log(x.map(v => v * 2).unwrap()); // 10
|
|
326
|
+
*
|
|
327
|
+
* const y = None;
|
|
328
|
+
* console.log(y.map(v => v * 2).isNone()); // true
|
|
329
|
+
* ```
|
|
135
330
|
*/
|
|
136
331
|
map<U>(fn: (value: T) => U): Option<U>;
|
|
137
332
|
/**
|
|
@@ -139,6 +334,15 @@ interface Option<T> {
|
|
|
139
334
|
* @typeParam U - The type of the value returned by the map function or the default value.
|
|
140
335
|
* @param defaultValue - The value to return if the Option is `None`.
|
|
141
336
|
* @param fn - A function that takes the contained value and returns a new value.
|
|
337
|
+
* @see mapOrElse
|
|
338
|
+
* @example
|
|
339
|
+
* ```ts
|
|
340
|
+
* const x = Some(5);
|
|
341
|
+
* console.log(x.mapOr(0, v => v * 2)); // 10
|
|
342
|
+
*
|
|
343
|
+
* const y = None;
|
|
344
|
+
* console.log(y.mapOr(0, v => v * 2)); // 0
|
|
345
|
+
* ```
|
|
142
346
|
*/
|
|
143
347
|
mapOr<U>(defaultValue: U, fn: (value: T) => U): U;
|
|
144
348
|
/**
|
|
@@ -146,6 +350,15 @@ interface Option<T> {
|
|
|
146
350
|
* @typeParam U - The type of the value returned by the map function or the default function.
|
|
147
351
|
* @param defaultFn - A function that returns the default value.
|
|
148
352
|
* @param fn - A function that takes the contained value and returns a new value.
|
|
353
|
+
* @see mapOr
|
|
354
|
+
* @example
|
|
355
|
+
* ```ts
|
|
356
|
+
* const x = Some(5);
|
|
357
|
+
* console.log(x.mapOrElse(() => 0, v => v * 2)); // 10
|
|
358
|
+
*
|
|
359
|
+
* const y = None;
|
|
360
|
+
* console.log(y.mapOrElse(() => 0, v => v * 2)); // 0
|
|
361
|
+
* ```
|
|
149
362
|
*/
|
|
150
363
|
mapOrElse<U>(defaultFn: () => U, fn: (value: T) => U): U;
|
|
151
364
|
/**
|
|
@@ -158,6 +371,17 @@ interface Option<T> {
|
|
|
158
371
|
* @typeParam U - The type of the value in the other `Option`.
|
|
159
372
|
* @param other - The other `Option` to zip with.
|
|
160
373
|
* @returns An `Option` containing a tuple of the values if both are `Some`, otherwise `None`.
|
|
374
|
+
* @see zipWith
|
|
375
|
+
* @see unzip
|
|
376
|
+
* @example
|
|
377
|
+
* ```ts
|
|
378
|
+
* const x = Some(1);
|
|
379
|
+
* const y = Some('hello');
|
|
380
|
+
* console.log(x.zip(y).unwrap()); // [1, 'hello']
|
|
381
|
+
*
|
|
382
|
+
* const z = None;
|
|
383
|
+
* console.log(x.zip(z).isNone()); // true
|
|
384
|
+
* ```
|
|
161
385
|
*/
|
|
162
386
|
zip<U>(other: Option<U>): Option<[T, U]>;
|
|
163
387
|
/**
|
|
@@ -169,17 +393,32 @@ interface Option<T> {
|
|
|
169
393
|
* @param other - The other `Option` to zip with.
|
|
170
394
|
* @param fn - The function to combine the values from both `Options`.
|
|
171
395
|
* @returns An `Option` containing the result of `fn` if both `Options` are `Some`, otherwise `None`.
|
|
396
|
+
* @see zip
|
|
397
|
+
* @example
|
|
398
|
+
* ```ts
|
|
399
|
+
* const x = Some(2);
|
|
400
|
+
* const y = Some(3);
|
|
401
|
+
* console.log(x.zipWith(y, (a, b) => a * b).unwrap()); // 6
|
|
402
|
+
* ```
|
|
172
403
|
*/
|
|
173
404
|
zipWith<U, R>(other: Option<U>, fn: (value: T, otherValue: U) => R): Option<R>;
|
|
174
405
|
/**
|
|
175
|
-
* Converts from `Option<[
|
|
406
|
+
* Converts from `Option<[U, R]>` to `[Option<U>, Option<R>]`.
|
|
176
407
|
* If `this` is `Some([a, b])`, returns `[Some(a), Some(b)]`.
|
|
177
408
|
* If `this` is `None`, returns `[None, None]`.
|
|
178
|
-
* @typeParam
|
|
179
|
-
* @typeParam
|
|
409
|
+
* @typeParam U - The type of the first value in the tuple.
|
|
410
|
+
* @typeParam R - The type of the second value in the tuple.
|
|
180
411
|
* @returns A tuple of `Options`, one for each element in the original `Option` of a tuple.
|
|
412
|
+
* @see zip
|
|
413
|
+
* @example
|
|
414
|
+
* ```ts
|
|
415
|
+
* const x = Some([1, 'hello'] as [number, string]);
|
|
416
|
+
* const [a, b] = x.unzip();
|
|
417
|
+
* console.log(a.unwrap()); // 1
|
|
418
|
+
* console.log(b.unwrap()); // 'hello'
|
|
419
|
+
* ```
|
|
181
420
|
*/
|
|
182
|
-
unzip<
|
|
421
|
+
unzip<U, R>(this: Option<[U, R]>): [Option<U>, Option<R>];
|
|
183
422
|
/**
|
|
184
423
|
* These methods treat the `Option` as a boolean value, where `Some` acts like `true` and `None` acts like `false`.
|
|
185
424
|
*/
|
|
@@ -189,6 +428,17 @@ interface Option<T> {
|
|
|
189
428
|
* @typeParam U - The type of the value in the other `Option`.
|
|
190
429
|
* @param other - The `Option` to return if `this` is `Some`.
|
|
191
430
|
* @returns `None` if `this` is `None`, otherwise returns `other`.
|
|
431
|
+
* @see or
|
|
432
|
+
* @see xor
|
|
433
|
+
* @example
|
|
434
|
+
* ```ts
|
|
435
|
+
* const x = Some(2);
|
|
436
|
+
* const y = Some('hello');
|
|
437
|
+
* console.log(x.and(y).unwrap()); // 'hello'
|
|
438
|
+
*
|
|
439
|
+
* const z = None;
|
|
440
|
+
* console.log(z.and(y).isNone()); // true
|
|
441
|
+
* ```
|
|
192
442
|
*/
|
|
193
443
|
and<U>(other: Option<U>): Option<U>;
|
|
194
444
|
/**
|
|
@@ -197,10 +447,32 @@ interface Option<T> {
|
|
|
197
447
|
* @typeParam U - The type of the value returned by the function.
|
|
198
448
|
* @param fn - A function that takes the contained value and returns an `Option`.
|
|
199
449
|
* @returns The result of `fn` if `this` is `Some`, otherwise `None`.
|
|
450
|
+
* @see map
|
|
451
|
+
* @see orElse
|
|
452
|
+
* @example
|
|
453
|
+
* ```ts
|
|
454
|
+
* const x = Some(2);
|
|
455
|
+
* const result = x.andThen(v => v > 0 ? Some(v * 2) : None);
|
|
456
|
+
* console.log(result.unwrap()); // 4
|
|
457
|
+
*
|
|
458
|
+
* const y = None;
|
|
459
|
+
* console.log(y.andThen(v => Some(v * 2)).isNone()); // true
|
|
460
|
+
* ```
|
|
200
461
|
*/
|
|
201
462
|
andThen<U>(fn: (value: T) => Option<U>): Option<U>;
|
|
202
463
|
/**
|
|
203
464
|
* Asynchronous version of `andThen`.
|
|
465
|
+
* @typeParam U - The type of the value returned by the async function.
|
|
466
|
+
* @param fn - An async function that takes the contained value and returns a `Promise<Option<U>>`.
|
|
467
|
+
* @returns A promise that resolves to `None` if `this` is `None`, otherwise the result of `fn`.
|
|
468
|
+
* @see andThen
|
|
469
|
+
* @see orElseAsync
|
|
470
|
+
* @example
|
|
471
|
+
* ```ts
|
|
472
|
+
* const x = Some(2);
|
|
473
|
+
* const result = await x.andThenAsync(async v => Some(v * 2));
|
|
474
|
+
* console.log(result.unwrap()); // 4
|
|
475
|
+
* ```
|
|
204
476
|
*/
|
|
205
477
|
andThenAsync<U>(fn: (value: T) => AsyncOption<U>): AsyncOption<U>;
|
|
206
478
|
/**
|
|
@@ -208,6 +480,17 @@ interface Option<T> {
|
|
|
208
480
|
* This can be used for providing a fallback `Option`.
|
|
209
481
|
* @param other - The fallback `Option` to use if `this` is `None`.
|
|
210
482
|
* @returns `this` if it is `Some`, otherwise `other`.
|
|
483
|
+
* @see and
|
|
484
|
+
* @see xor
|
|
485
|
+
* @example
|
|
486
|
+
* ```ts
|
|
487
|
+
* const x = None;
|
|
488
|
+
* const y = Some(5);
|
|
489
|
+
* console.log(x.or(y).unwrap()); // 5
|
|
490
|
+
*
|
|
491
|
+
* const z = Some(2);
|
|
492
|
+
* console.log(z.or(y).unwrap()); // 2
|
|
493
|
+
* ```
|
|
211
494
|
*/
|
|
212
495
|
or(other: Option<T>): Option<T>;
|
|
213
496
|
/**
|
|
@@ -215,10 +498,30 @@ interface Option<T> {
|
|
|
215
498
|
* This method can be used for lazy fallbacks, as `fn` is only evaluated if `this` is `None`.
|
|
216
499
|
* @param fn - A function that produces an `Option`.
|
|
217
500
|
* @returns `this` if it is `Some`, otherwise the result of `fn`.
|
|
501
|
+
* @see andThen
|
|
502
|
+
* @example
|
|
503
|
+
* ```ts
|
|
504
|
+
* const x = None;
|
|
505
|
+
* const result = x.orElse(() => Some(10));
|
|
506
|
+
* console.log(result.unwrap()); // 10
|
|
507
|
+
*
|
|
508
|
+
* const y = Some(5);
|
|
509
|
+
* console.log(y.orElse(() => Some(10)).unwrap()); // 5
|
|
510
|
+
* ```
|
|
218
511
|
*/
|
|
219
512
|
orElse(fn: () => Option<T>): Option<T>;
|
|
220
513
|
/**
|
|
221
514
|
* Asynchronous version of `orElse`.
|
|
515
|
+
* @param fn - An async function that produces a `Promise<Option<T>>`.
|
|
516
|
+
* @returns A promise that resolves to `this` if it is `Some`, otherwise the result of `fn`.
|
|
517
|
+
* @see orElse
|
|
518
|
+
* @see andThenAsync
|
|
519
|
+
* @example
|
|
520
|
+
* ```ts
|
|
521
|
+
* const x = None;
|
|
522
|
+
* const result = await x.orElseAsync(async () => Some(10));
|
|
523
|
+
* console.log(result.unwrap()); // 10
|
|
524
|
+
* ```
|
|
222
525
|
*/
|
|
223
526
|
orElseAsync(fn: () => AsyncOption<T>): AsyncOption<T>;
|
|
224
527
|
/**
|
|
@@ -226,6 +529,18 @@ interface Option<T> {
|
|
|
226
529
|
* This can be thought of as an exclusive or operation on `Option` values.
|
|
227
530
|
* @param other - The other `Option` to compare with.
|
|
228
531
|
* @returns `Some` if exactly one of `this` and `other` is `Some`, otherwise `None`.
|
|
532
|
+
* @see and
|
|
533
|
+
* @see or
|
|
534
|
+
* @example
|
|
535
|
+
* ```ts
|
|
536
|
+
* const x = Some(2);
|
|
537
|
+
* const y = None;
|
|
538
|
+
* console.log(x.xor(y).unwrap()); // 2
|
|
539
|
+
*
|
|
540
|
+
* const a = Some(2);
|
|
541
|
+
* const b = Some(3);
|
|
542
|
+
* console.log(a.xor(b).isNone()); // true
|
|
543
|
+
* ```
|
|
229
544
|
*/
|
|
230
545
|
xor(other: Option<T>): Option<T>;
|
|
231
546
|
/**
|
|
@@ -233,6 +548,16 @@ interface Option<T> {
|
|
|
233
548
|
* This is primarily for side effects and does not transform the `Option`.
|
|
234
549
|
* @param fn - A function to call with the contained value.
|
|
235
550
|
* @returns `this`, unmodified, for chaining additional methods.
|
|
551
|
+
* @example
|
|
552
|
+
* ```ts
|
|
553
|
+
* const x = Some(5);
|
|
554
|
+
* // Prints "value: 5" and returns Some(10)
|
|
555
|
+
* const doubled = x.inspect(v => console.log('value:', v)).map(v => v * 2);
|
|
556
|
+
*
|
|
557
|
+
* const y = None;
|
|
558
|
+
* // Does nothing and returns None
|
|
559
|
+
* y.inspect(v => console.log('value:', v));
|
|
560
|
+
* ```
|
|
236
561
|
*/
|
|
237
562
|
inspect(fn: (value: T) => void): this;
|
|
238
563
|
/**
|
|
@@ -240,10 +565,25 @@ interface Option<T> {
|
|
|
240
565
|
* This method can be used for comparing `Option` instances in a value-sensitive manner.
|
|
241
566
|
* @param other - The other `Option` to compare with.
|
|
242
567
|
* @returns `true` if `this` and `other` are both `Some` with equal values, or both are `None`, otherwise `false`.
|
|
568
|
+
* @example
|
|
569
|
+
* ```ts
|
|
570
|
+
* const a = Some(5);
|
|
571
|
+
* const b = Some(5);
|
|
572
|
+
* const c = Some(10);
|
|
573
|
+
* console.log(a.eq(b)); // true
|
|
574
|
+
* console.log(a.eq(c)); // false
|
|
575
|
+
* console.log(None.eq(None)); // true
|
|
576
|
+
* console.log(a.eq(None)); // false
|
|
577
|
+
* ```
|
|
243
578
|
*/
|
|
244
579
|
eq(other: Option<T>): boolean;
|
|
245
580
|
/**
|
|
246
581
|
* Custom `toString` implementation that uses the `Option`'s contained value.
|
|
582
|
+
* @example
|
|
583
|
+
* ```ts
|
|
584
|
+
* console.log(Some(5).toString()); // 'Some(5)'
|
|
585
|
+
* console.log(None.toString()); // 'None'
|
|
586
|
+
* ```
|
|
247
587
|
*/
|
|
248
588
|
toString(): string;
|
|
249
589
|
}
|
|
@@ -264,15 +604,31 @@ pub enum Result<T, E> {
|
|
|
264
604
|
*/
|
|
265
605
|
interface Result<T, E> {
|
|
266
606
|
/**
|
|
267
|
-
*
|
|
607
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
608
|
+
* Returns `'Result'` so that `Object.prototype.toString.call(result)` produces `'[object Result]'`.
|
|
609
|
+
*
|
|
610
|
+
* This enables reliable type identification even across different execution contexts (e.g., iframes, different module instances).
|
|
268
611
|
*
|
|
269
|
-
* @
|
|
612
|
+
* @example
|
|
613
|
+
* ```ts
|
|
614
|
+
* const x = Ok(5);
|
|
615
|
+
* console.log(Object.prototype.toString.call(x)); // '[object Result]'
|
|
616
|
+
* ```
|
|
617
|
+
*
|
|
618
|
+
* @internal
|
|
270
619
|
*/
|
|
271
620
|
readonly [Symbol.toStringTag]: 'Result';
|
|
272
621
|
/**
|
|
273
|
-
*
|
|
622
|
+
* A unique symbol property used to identify the variant of this `Result`.
|
|
623
|
+
* Returns `'Ok'` if the Result represents success, or `'Err'` if it represents failure.
|
|
624
|
+
*
|
|
625
|
+
* This is used internally by the `isResult` utility function to verify that an object is a valid `Result` instance,
|
|
626
|
+
* and to distinguish between `Ok` and `Err` variants without calling methods.
|
|
274
627
|
*
|
|
275
|
-
*
|
|
628
|
+
* Note: The symbol itself is not exported as part of the public API.
|
|
629
|
+
* Use the `isResult` utility function or the `isOk()`/`isErr()` methods for type checking.
|
|
630
|
+
*
|
|
631
|
+
* @internal
|
|
276
632
|
*/
|
|
277
633
|
readonly [ResultKindSymbol]: 'Ok' | 'Err';
|
|
278
634
|
/**
|
|
@@ -280,28 +636,75 @@ interface Result<T, E> {
|
|
|
280
636
|
*/
|
|
281
637
|
/**
|
|
282
638
|
* Returns `true` if the result is `Ok`.
|
|
639
|
+
* @example
|
|
640
|
+
* ```ts
|
|
641
|
+
* const x = Ok(5);
|
|
642
|
+
* console.log(x.isOk()); // true
|
|
643
|
+
*
|
|
644
|
+
* const y = Err('error');
|
|
645
|
+
* console.log(y.isOk()); // false
|
|
646
|
+
* ```
|
|
283
647
|
*/
|
|
284
648
|
isOk(): boolean;
|
|
285
649
|
/**
|
|
286
650
|
* Returns `true` if the result is `Err`.
|
|
651
|
+
* @example
|
|
652
|
+
* ```ts
|
|
653
|
+
* const x = Ok(5);
|
|
654
|
+
* console.log(x.isErr()); // false
|
|
655
|
+
*
|
|
656
|
+
* const y = Err('error');
|
|
657
|
+
* console.log(y.isErr()); // true
|
|
658
|
+
* ```
|
|
287
659
|
*/
|
|
288
660
|
isErr(): boolean;
|
|
289
661
|
/**
|
|
290
662
|
* Returns `true` if the result is `Ok` and the provided predicate returns `true` for the contained value.
|
|
291
663
|
* @param predicate - A function that takes the `Ok` value and returns a boolean.
|
|
664
|
+
* @see isErrAnd
|
|
665
|
+
* @example
|
|
666
|
+
* ```ts
|
|
667
|
+
* const x = Ok(2);
|
|
668
|
+
* console.log(x.isOkAnd(v => v > 1)); // true
|
|
669
|
+
* console.log(x.isOkAnd(v => v > 5)); // false
|
|
670
|
+
* ```
|
|
292
671
|
*/
|
|
293
672
|
isOkAnd(predicate: (value: T) => boolean): boolean;
|
|
294
673
|
/**
|
|
295
674
|
* Asynchronous version of `isOkAnd`.
|
|
675
|
+
* @param predicate - An async function that takes the `Ok` value and returns a `Promise<boolean>`.
|
|
676
|
+
* @returns A promise that resolves to `true` if the Result is `Ok` and the predicate resolves to `true`.
|
|
677
|
+
* @see isOkAnd
|
|
678
|
+
* @see isErrAndAsync
|
|
679
|
+
* @example
|
|
680
|
+
* ```ts
|
|
681
|
+
* const x = Ok(2);
|
|
682
|
+
* await x.isOkAndAsync(async v => v > 1); // true
|
|
683
|
+
* ```
|
|
296
684
|
*/
|
|
297
685
|
isOkAndAsync(predicate: (value: T) => Promise<boolean>): Promise<boolean>;
|
|
298
686
|
/**
|
|
299
687
|
* Returns `true` if the result is `Err` and the provided predicate returns `true` for the contained error.
|
|
300
688
|
* @param predicate - A function that takes the `Err` value and returns a boolean.
|
|
689
|
+
* @see isOkAnd
|
|
690
|
+
* @example
|
|
691
|
+
* ```ts
|
|
692
|
+
* const x = Err('error');
|
|
693
|
+
* console.log(x.isErrAnd(e => e === 'error')); // true
|
|
694
|
+
* ```
|
|
301
695
|
*/
|
|
302
696
|
isErrAnd(predicate: (error: E) => boolean): boolean;
|
|
303
697
|
/**
|
|
304
698
|
* Asynchronous version of `isErrAnd`.
|
|
699
|
+
* @param predicate - An async function that takes the `Err` value and returns a `Promise<boolean>`.
|
|
700
|
+
* @returns A promise that resolves to `true` if the Result is `Err` and the predicate resolves to `true`.
|
|
701
|
+
* @see isErrAnd
|
|
702
|
+
* @see isOkAndAsync
|
|
703
|
+
* @example
|
|
704
|
+
* ```ts
|
|
705
|
+
* const x = Err('error');
|
|
706
|
+
* await x.isErrAndAsync(async e => e.length > 0); // true
|
|
707
|
+
* ```
|
|
305
708
|
*/
|
|
306
709
|
isErrAndAsync(predicate: (error: E) => Promise<boolean>): Promise<boolean>;
|
|
307
710
|
/**
|
|
@@ -311,25 +714,69 @@ interface Result<T, E> {
|
|
|
311
714
|
* Returns the contained `Ok` value, with a provided error message if the result is `Err`.
|
|
312
715
|
* @param msg - The error message to provide if the result is an `Err`.
|
|
313
716
|
* @throws {TypeError} Throws an error with the provided message if the result is an `Err`.
|
|
717
|
+
* @see unwrap
|
|
718
|
+
* @see expectErr
|
|
719
|
+
* @example
|
|
720
|
+
* ```ts
|
|
721
|
+
* const x = Ok(5);
|
|
722
|
+
* console.log(x.expect('should have value')); // 5
|
|
723
|
+
*
|
|
724
|
+
* const y = Err('error');
|
|
725
|
+
* y.expect('should have value'); // throws TypeError: should have value: error
|
|
726
|
+
* ```
|
|
314
727
|
*/
|
|
315
728
|
expect(msg: string): T;
|
|
316
729
|
/**
|
|
317
730
|
* Returns the contained `Ok` value.
|
|
318
731
|
* @throws {TypeError} Throws an error if the result is an `Err`.
|
|
732
|
+
* @see expect
|
|
733
|
+
* @see unwrapOr
|
|
734
|
+
* @see unwrapErr
|
|
735
|
+
* @example
|
|
736
|
+
* ```ts
|
|
737
|
+
* const x = Ok(5);
|
|
738
|
+
* console.log(x.unwrap()); // 5
|
|
739
|
+
*
|
|
740
|
+
* const y = Err('error');
|
|
741
|
+
* y.unwrap(); // throws TypeError
|
|
742
|
+
* ```
|
|
319
743
|
*/
|
|
320
744
|
unwrap(): T;
|
|
321
745
|
/**
|
|
322
746
|
* Returns the contained `Ok` value or a provided default.
|
|
323
747
|
* @param defaultValue - The value to return if the result is an `Err`.
|
|
748
|
+
* @see unwrapOrElse
|
|
749
|
+
* @example
|
|
750
|
+
* ```ts
|
|
751
|
+
* const x = Ok(5);
|
|
752
|
+
* console.log(x.unwrapOr(10)); // 5
|
|
753
|
+
*
|
|
754
|
+
* const y = Err('error');
|
|
755
|
+
* console.log(y.unwrapOr(10)); // 10
|
|
756
|
+
* ```
|
|
324
757
|
*/
|
|
325
758
|
unwrapOr(defaultValue: T): T;
|
|
326
759
|
/**
|
|
327
760
|
* Returns the contained `Ok` value or computes it from a closure if the result is `Err`.
|
|
328
761
|
* @param fn - A function that takes the `Err` value and returns an `Ok` value.
|
|
762
|
+
* @see unwrapOr
|
|
763
|
+
* @example
|
|
764
|
+
* ```ts
|
|
765
|
+
* const x = Err('error');
|
|
766
|
+
* console.log(x.unwrapOrElse(e => e.length)); // 5
|
|
767
|
+
* ```
|
|
329
768
|
*/
|
|
330
769
|
unwrapOrElse(fn: (error: E) => T): T;
|
|
331
770
|
/**
|
|
332
771
|
* Asynchronous version of `unwrapOrElse`.
|
|
772
|
+
* @param fn - An async function that takes the `Err` value and returns a `Promise<T>`.
|
|
773
|
+
* @returns A promise that resolves to the contained `Ok` value or the result of the async function.
|
|
774
|
+
* @see unwrapOrElse
|
|
775
|
+
* @example
|
|
776
|
+
* ```ts
|
|
777
|
+
* const x = Err('error');
|
|
778
|
+
* await x.unwrapOrElseAsync(async e => e.length); // 5
|
|
779
|
+
* ```
|
|
333
780
|
*/
|
|
334
781
|
unwrapOrElseAsync(fn: (error: E) => Promise<T>): Promise<T>;
|
|
335
782
|
/**
|
|
@@ -339,11 +786,31 @@ interface Result<T, E> {
|
|
|
339
786
|
* Returns the contained `Err` value, with a provided error message if the result is `Ok`.
|
|
340
787
|
* @param msg - The error message to provide if the result is an `Ok`.
|
|
341
788
|
* @throws {TypeError} Throws an error with the provided message if the result is an `Ok`.
|
|
789
|
+
* @see unwrapErr
|
|
790
|
+
* @see expect
|
|
791
|
+
* @example
|
|
792
|
+
* ```ts
|
|
793
|
+
* const x = Err('error');
|
|
794
|
+
* console.log(x.expectErr('should have error')); // 'error'
|
|
795
|
+
*
|
|
796
|
+
* const y = Ok(5);
|
|
797
|
+
* y.expectErr('should have error'); // throws TypeError: should have error: 5
|
|
798
|
+
* ```
|
|
342
799
|
*/
|
|
343
800
|
expectErr(msg: string): E;
|
|
344
801
|
/**
|
|
345
802
|
* Returns the contained `Err` value.
|
|
346
803
|
* @throws {TypeError} Throws an error if the result is an `Ok`.
|
|
804
|
+
* @see expectErr
|
|
805
|
+
* @see unwrap
|
|
806
|
+
* @example
|
|
807
|
+
* ```ts
|
|
808
|
+
* const x = Err('error');
|
|
809
|
+
* console.log(x.unwrapErr()); // 'error'
|
|
810
|
+
*
|
|
811
|
+
* const y = Ok(5);
|
|
812
|
+
* y.unwrapErr(); // throws TypeError
|
|
813
|
+
* ```
|
|
347
814
|
*/
|
|
348
815
|
unwrapErr(): E;
|
|
349
816
|
/**
|
|
@@ -353,22 +820,51 @@ interface Result<T, E> {
|
|
|
353
820
|
* Converts from `Result<T, E>` to `Option<T>`.
|
|
354
821
|
* If the result is `Ok`, returns `Some(T)`.
|
|
355
822
|
* If the result is `Err`, returns `None`.
|
|
823
|
+
* @see err
|
|
824
|
+
* @example
|
|
825
|
+
* ```ts
|
|
826
|
+
* const x = Ok(5);
|
|
827
|
+
* console.log(x.ok().unwrap()); // 5
|
|
828
|
+
*
|
|
829
|
+
* const y = Err('error');
|
|
830
|
+
* console.log(y.ok().isNone()); // true
|
|
831
|
+
* ```
|
|
356
832
|
*/
|
|
357
833
|
ok(): Option<T>;
|
|
358
834
|
/**
|
|
359
835
|
* Converts from `Result<T, E>` to `Option<E>`.
|
|
360
836
|
* If the result is `Err`, returns `Some(E)`.
|
|
361
837
|
* If the result is `Ok`, returns `None`.
|
|
838
|
+
* @see ok
|
|
839
|
+
* @example
|
|
840
|
+
* ```ts
|
|
841
|
+
* const x = Err('error');
|
|
842
|
+
* console.log(x.err().unwrap()); // 'error'
|
|
843
|
+
*
|
|
844
|
+
* const y = Ok(5);
|
|
845
|
+
* console.log(y.err().isNone()); // true
|
|
846
|
+
* ```
|
|
362
847
|
*/
|
|
363
848
|
err(): Option<E>;
|
|
364
849
|
/**
|
|
365
850
|
* Transposes a `Result` of an `Option` into an `Option` of a `Result`.
|
|
366
|
-
* @typeParam
|
|
851
|
+
* @typeParam U - The type of the success value in the `Ok` variant of the `Option`.
|
|
367
852
|
* @returns `Some` containing `Ok` if the result is `Ok` containing `Some`,
|
|
368
853
|
* `Some` containing `Err` if the result is `Err`,
|
|
369
854
|
* `None` if the result is `Ok` containing `None`.
|
|
855
|
+
* @example
|
|
856
|
+
* ```ts
|
|
857
|
+
* const x = Ok(Some(5));
|
|
858
|
+
* console.log(x.transpose().unwrap().unwrap()); // 5
|
|
859
|
+
*
|
|
860
|
+
* const y: Result<Option<number>, string> = Err('error');
|
|
861
|
+
* console.log(y.transpose().unwrap().unwrapErr()); // 'error'
|
|
862
|
+
*
|
|
863
|
+
* const z = Ok(None);
|
|
864
|
+
* console.log(z.transpose().isNone()); // true
|
|
865
|
+
* ```
|
|
370
866
|
*/
|
|
371
|
-
transpose<
|
|
867
|
+
transpose<U>(this: Result<Option<U>, E>): Option<Result<U, E>>;
|
|
372
868
|
/**
|
|
373
869
|
* This method transforms the contained value of the `Ok` variant:
|
|
374
870
|
*/
|
|
@@ -377,6 +873,16 @@ interface Result<T, E> {
|
|
|
377
873
|
* leaving an `Err` value untouched.
|
|
378
874
|
* @typeParam U - The type of the value returned by the map function.
|
|
379
875
|
* @param fn - A function that takes the `Ok` value and returns a new value.
|
|
876
|
+
* @see mapErr
|
|
877
|
+
* @see andThen
|
|
878
|
+
* @example
|
|
879
|
+
* ```ts
|
|
880
|
+
* const x = Ok(5);
|
|
881
|
+
* console.log(x.map(v => v * 2).unwrap()); // 10
|
|
882
|
+
*
|
|
883
|
+
* const y = Err('error');
|
|
884
|
+
* console.log(y.map(v => v * 2).unwrapErr()); // 'error'
|
|
885
|
+
* ```
|
|
380
886
|
*/
|
|
381
887
|
map<U>(fn: (value: T) => U): Result<U, E>;
|
|
382
888
|
/**
|
|
@@ -387,6 +893,12 @@ interface Result<T, E> {
|
|
|
387
893
|
* leaving an `Ok` value untouched.
|
|
388
894
|
* @typeParam F - The type of the error returned by the map function.
|
|
389
895
|
* @param fn - A function that takes the `Err` value and returns a new error value.
|
|
896
|
+
* @see map
|
|
897
|
+
* @example
|
|
898
|
+
* ```ts
|
|
899
|
+
* const x = Err('error');
|
|
900
|
+
* console.log(x.mapErr(e => e.toUpperCase()).unwrapErr()); // 'ERROR'
|
|
901
|
+
* ```
|
|
390
902
|
*/
|
|
391
903
|
mapErr<F>(fn: (error: E) => F): Result<T, F>;
|
|
392
904
|
/**
|
|
@@ -397,6 +909,15 @@ interface Result<T, E> {
|
|
|
397
909
|
* @typeParam U - The type of the value returned by the map function or the default value.
|
|
398
910
|
* @param defaultValue - The value to return if the result is `Err`.
|
|
399
911
|
* @param fn - A function that takes the `Ok` value and returns a new value.
|
|
912
|
+
* @see mapOrElse
|
|
913
|
+
* @example
|
|
914
|
+
* ```ts
|
|
915
|
+
* const x = Ok(5);
|
|
916
|
+
* console.log(x.mapOr(0, v => v * 2)); // 10
|
|
917
|
+
*
|
|
918
|
+
* const y = Err('error');
|
|
919
|
+
* console.log(y.mapOr(0, v => v * 2)); // 0
|
|
920
|
+
* ```
|
|
400
921
|
*/
|
|
401
922
|
mapOr<U>(defaultValue: U, fn: (value: T) => U): U;
|
|
402
923
|
/**
|
|
@@ -404,14 +925,32 @@ interface Result<T, E> {
|
|
|
404
925
|
* @typeParam U - The type of the value returned by the map function or the default function.
|
|
405
926
|
* @param defaultFn - A function that returns the default value.
|
|
406
927
|
* @param fn - A function that takes the `Ok` value and returns a new value.
|
|
928
|
+
* @see mapOr
|
|
929
|
+
* @example
|
|
930
|
+
* ```ts
|
|
931
|
+
* const x = Ok(5);
|
|
932
|
+
* console.log(x.mapOrElse(e => 0, v => v * 2)); // 10
|
|
933
|
+
*
|
|
934
|
+
* const y = Err('error');
|
|
935
|
+
* console.log(y.mapOrElse(e => e.length, v => v * 2)); // 5
|
|
936
|
+
* ```
|
|
407
937
|
*/
|
|
408
938
|
mapOrElse<U>(defaultFn: (error: E) => U, fn: (value: T) => U): U;
|
|
409
939
|
/**
|
|
410
|
-
* Converts from `Result<Result<
|
|
411
|
-
* If the result is `Ok(Ok(
|
|
940
|
+
* Converts from `Result<Result<U, E>, E>` to `Result<U, E>`.
|
|
941
|
+
* If the result is `Ok(Ok(U))`, returns `Ok(U)`.
|
|
412
942
|
* If the result is `Ok(Err(E))` or `Err(E)`, returns `Err(E)`.
|
|
943
|
+
* @typeParam U - The type of the success value in the inner `Result`.
|
|
944
|
+
* @example
|
|
945
|
+
* ```ts
|
|
946
|
+
* const x = Ok(Ok(5));
|
|
947
|
+
* console.log(x.flatten().unwrap()); // 5
|
|
948
|
+
*
|
|
949
|
+
* const y = Ok(Err('error'));
|
|
950
|
+
* console.log(y.flatten().unwrapErr()); // 'error'
|
|
951
|
+
* ```
|
|
413
952
|
*/
|
|
414
|
-
flatten<
|
|
953
|
+
flatten<U>(this: Result<Result<U, E>, E>): Result<U, E>;
|
|
415
954
|
/**
|
|
416
955
|
* These methods treat the `Result` as a boolean value, where `Ok` acts like `true` and `Err` acts like `false`.
|
|
417
956
|
*/
|
|
@@ -420,6 +959,17 @@ interface Result<T, E> {
|
|
|
420
959
|
* @typeParam U - The type of the value in the other `Result`.
|
|
421
960
|
* @param other - The `Result` to return if `this` is `Ok`.
|
|
422
961
|
* @returns The passed `Result` if `this` is `Ok`, otherwise returns `this` (which is `Err`).
|
|
962
|
+
* @see or
|
|
963
|
+
* @example
|
|
964
|
+
* ```ts
|
|
965
|
+
* const x = Ok(2);
|
|
966
|
+
* const y = Err('late error');
|
|
967
|
+
* console.log(x.and(y).unwrapErr()); // 'late error'
|
|
968
|
+
*
|
|
969
|
+
* const a = Err('early error');
|
|
970
|
+
* const b = Ok(5);
|
|
971
|
+
* console.log(a.and(b).unwrapErr()); // 'early error'
|
|
972
|
+
* ```
|
|
423
973
|
*/
|
|
424
974
|
and<U>(other: Result<U, E>): Result<U, E>;
|
|
425
975
|
/**
|
|
@@ -427,6 +977,17 @@ interface Result<T, E> {
|
|
|
427
977
|
* @typeParam F - The type of the error in the other `Result`.
|
|
428
978
|
* @param other - The `Result` to return if `this` is `Err`.
|
|
429
979
|
* @returns `this` if it is `Ok`, otherwise returns `other`.
|
|
980
|
+
* @see and
|
|
981
|
+
* @example
|
|
982
|
+
* ```ts
|
|
983
|
+
* const x = Err('error');
|
|
984
|
+
* const y = Ok(5);
|
|
985
|
+
* console.log(x.or(y).unwrap()); // 5
|
|
986
|
+
*
|
|
987
|
+
* const a = Ok(2);
|
|
988
|
+
* const b = Ok(100);
|
|
989
|
+
* console.log(a.or(b).unwrap()); // 2
|
|
990
|
+
* ```
|
|
430
991
|
*/
|
|
431
992
|
or<F>(other: Result<T, F>): Result<T, F>;
|
|
432
993
|
/**
|
|
@@ -434,10 +995,32 @@ interface Result<T, E> {
|
|
|
434
995
|
* @typeParam U - The type of the value returned by the function.
|
|
435
996
|
* @param fn - A function that takes the `Ok` value and returns a `Result`.
|
|
436
997
|
* @returns The result of `fn` if `this` is `Ok`, otherwise `this` as `Err`.
|
|
998
|
+
* @see map
|
|
999
|
+
* @see orElse
|
|
1000
|
+
* @example
|
|
1001
|
+
* ```ts
|
|
1002
|
+
* const x = Ok(2);
|
|
1003
|
+
* const result = x.andThen(v => v > 0 ? Ok(v * 2) : Err('negative'));
|
|
1004
|
+
* console.log(result.unwrap()); // 4
|
|
1005
|
+
*
|
|
1006
|
+
* const y = Err('error');
|
|
1007
|
+
* console.log(y.andThen(v => Ok(v * 2)).unwrapErr()); // 'error'
|
|
1008
|
+
* ```
|
|
437
1009
|
*/
|
|
438
1010
|
andThen<U>(fn: (value: T) => Result<U, E>): Result<U, E>;
|
|
439
1011
|
/**
|
|
440
1012
|
* Asynchronous version of `andThen`.
|
|
1013
|
+
* @typeParam U - The type of the value returned by the async function.
|
|
1014
|
+
* @param fn - An async function that takes the `Ok` value and returns a `Promise<Result<U, E>>`.
|
|
1015
|
+
* @returns A promise that resolves to `this` as `Err` if `this` is `Err`, otherwise the result of `fn`.
|
|
1016
|
+
* @see andThen
|
|
1017
|
+
* @see orElseAsync
|
|
1018
|
+
* @example
|
|
1019
|
+
* ```ts
|
|
1020
|
+
* const x = Ok(2);
|
|
1021
|
+
* const result = await x.andThenAsync(async v => Ok(v * 2));
|
|
1022
|
+
* console.log(result.unwrap()); // 4
|
|
1023
|
+
* ```
|
|
441
1024
|
*/
|
|
442
1025
|
andThenAsync<U>(fn: (value: T) => AsyncResult<U, E>): AsyncResult<U, E>;
|
|
443
1026
|
/**
|
|
@@ -445,10 +1028,31 @@ interface Result<T, E> {
|
|
|
445
1028
|
* @typeParam F - The type of the error returned by the function.
|
|
446
1029
|
* @param fn - A function that takes the `Err` value and returns a `Result`.
|
|
447
1030
|
* @returns The result of `fn` if `this` is `Err`, otherwise `this` as `Ok`.
|
|
1031
|
+
* @see andThen
|
|
1032
|
+
* @example
|
|
1033
|
+
* ```ts
|
|
1034
|
+
* const x = Err('error');
|
|
1035
|
+
* const result = x.orElse(e => Ok(e.length));
|
|
1036
|
+
* console.log(result.unwrap()); // 5
|
|
1037
|
+
*
|
|
1038
|
+
* const y = Ok(2);
|
|
1039
|
+
* console.log(y.orElse(e => Ok(0)).unwrap()); // 2
|
|
1040
|
+
* ```
|
|
448
1041
|
*/
|
|
449
1042
|
orElse<F>(fn: (error: E) => Result<T, F>): Result<T, F>;
|
|
450
1043
|
/**
|
|
451
1044
|
* Asynchronous version of `orElse`.
|
|
1045
|
+
* @typeParam F - The type of the error returned by the async function.
|
|
1046
|
+
* @param fn - An async function that takes the `Err` value and returns a `Promise<Result<T, F>>`.
|
|
1047
|
+
* @returns A promise that resolves to `this` as `Ok` if `this` is `Ok`, otherwise the result of `fn`.
|
|
1048
|
+
* @see orElse
|
|
1049
|
+
* @see andThenAsync
|
|
1050
|
+
* @example
|
|
1051
|
+
* ```ts
|
|
1052
|
+
* const x = Err('error');
|
|
1053
|
+
* const result = await x.orElseAsync(async e => Ok(e.length));
|
|
1054
|
+
* console.log(result.unwrap()); // 5
|
|
1055
|
+
* ```
|
|
452
1056
|
*/
|
|
453
1057
|
orElseAsync<F>(fn: (error: E) => AsyncResult<T, F>): AsyncResult<T, F>;
|
|
454
1058
|
/**
|
|
@@ -456,6 +1060,12 @@ interface Result<T, E> {
|
|
|
456
1060
|
* Does not modify the `Result`.
|
|
457
1061
|
* @param fn - A function to call with the `Ok` value.
|
|
458
1062
|
* @returns `this`, unmodified.
|
|
1063
|
+
* @see inspectErr
|
|
1064
|
+
* @example
|
|
1065
|
+
* ```ts
|
|
1066
|
+
* const x = Ok(5);
|
|
1067
|
+
* x.inspect(v => console.log(v)); // prints 5
|
|
1068
|
+
* ```
|
|
459
1069
|
*/
|
|
460
1070
|
inspect(fn: (value: T) => void): this;
|
|
461
1071
|
/**
|
|
@@ -463,35 +1073,73 @@ interface Result<T, E> {
|
|
|
463
1073
|
* Does not modify the `Result`.
|
|
464
1074
|
* @param fn - A function to call with the `Err` value.
|
|
465
1075
|
* @returns `this`, unmodified.
|
|
1076
|
+
* @see inspect
|
|
1077
|
+
* @example
|
|
1078
|
+
* ```ts
|
|
1079
|
+
* const x = Err('error');
|
|
1080
|
+
* x.inspectErr(e => console.log(e)); // prints 'error'
|
|
1081
|
+
* ```
|
|
466
1082
|
*/
|
|
467
1083
|
inspectErr(fn: (error: E) => void): this;
|
|
468
1084
|
/**
|
|
469
1085
|
* Tests whether `this` and `other` are both `Ok` containing equal values, or both are `Err` containing equal errors.
|
|
470
1086
|
* @param other - The other `Result` to compare with.
|
|
471
1087
|
* @returns `true` if `this` and `other` are both `Ok` with equal values, or both are `Err` with equal errors, otherwise `false`.
|
|
1088
|
+
* @example
|
|
1089
|
+
* ```ts
|
|
1090
|
+
* const a = Ok(5);
|
|
1091
|
+
* const b = Ok(5);
|
|
1092
|
+
* const c = Ok(10);
|
|
1093
|
+
* console.log(a.eq(b)); // true
|
|
1094
|
+
* console.log(a.eq(c)); // false
|
|
1095
|
+
*
|
|
1096
|
+
* const d = Err('error');
|
|
1097
|
+
* const e = Err('error');
|
|
1098
|
+
* console.log(d.eq(e)); // true
|
|
1099
|
+
* console.log(a.eq(d)); // false
|
|
1100
|
+
* ```
|
|
472
1101
|
*/
|
|
473
1102
|
eq(other: Result<T, E>): boolean;
|
|
474
1103
|
/**
|
|
475
|
-
* Transforms the current Result into a new Result where the type of the error
|
|
476
|
-
* The type of the success
|
|
477
|
-
*
|
|
1104
|
+
* Transforms the current Result into a new Result where the type of the error is replaced with a new type `F`.
|
|
1105
|
+
* The type of the success value remains unchanged.
|
|
1106
|
+
* This is a type-level only operation, equivalent to `result as unknown as Result<T, F>`.
|
|
478
1107
|
*
|
|
479
|
-
* @typeParam F - The new type for the error
|
|
480
|
-
* @returns `this`
|
|
1108
|
+
* @typeParam F - The new type for the error.
|
|
1109
|
+
* @returns `this` with the error type cast to `F`.
|
|
1110
|
+
* @see asErr
|
|
1111
|
+
* @example
|
|
1112
|
+
* ```ts
|
|
1113
|
+
* const x: Result<number, string> = Ok(5);
|
|
1114
|
+
* const y: Result<number, Error> = x.asOk<Error>();
|
|
1115
|
+
* console.log(y.unwrap()); // 5
|
|
1116
|
+
* ```
|
|
481
1117
|
*/
|
|
482
1118
|
asOk<F>(): Result<T, F>;
|
|
483
1119
|
/**
|
|
484
|
-
* Transforms the current Result into a new Result where the type of the success
|
|
485
|
-
* The type of the error
|
|
486
|
-
*
|
|
487
|
-
*
|
|
1120
|
+
* Transforms the current Result into a new Result where the type of the success value is replaced with a new type `U`.
|
|
1121
|
+
* The type of the error remains unchanged.
|
|
1122
|
+
* This is a type-level only operation, equivalent to `result as unknown as Result<U, E>`.
|
|
1123
|
+
* Useful when you need to propagate an error to a different success type context.
|
|
488
1124
|
*
|
|
489
|
-
* @typeParam U - The new type for the success
|
|
490
|
-
* @returns `this`
|
|
1125
|
+
* @typeParam U - The new type for the success value.
|
|
1126
|
+
* @returns `this` with the success type cast to `U`.
|
|
1127
|
+
* @see asOk
|
|
1128
|
+
* @example
|
|
1129
|
+
* ```ts
|
|
1130
|
+
* const x: Result<number, string> = Err('error');
|
|
1131
|
+
* const y: Result<string, string> = x.asErr<string>();
|
|
1132
|
+
* console.log(y.unwrapErr()); // 'error'
|
|
1133
|
+
* ```
|
|
491
1134
|
*/
|
|
492
1135
|
asErr<U>(): Result<U, E>;
|
|
493
1136
|
/**
|
|
494
1137
|
* Custom `toString` implementation that uses the `Result`'s contained value.
|
|
1138
|
+
* @example
|
|
1139
|
+
* ```ts
|
|
1140
|
+
* console.log(Ok(5).toString()); // 'Ok(5)'
|
|
1141
|
+
* console.log(Err('error').toString()); // 'Err(error)'
|
|
1142
|
+
* ```
|
|
495
1143
|
*/
|
|
496
1144
|
toString(): string;
|
|
497
1145
|
}
|
|
@@ -512,30 +1160,66 @@ type AsyncOption<T> = Promise<Option<T>>;
|
|
|
512
1160
|
type AsyncResult<T, E> = Promise<Result<T, E>>;
|
|
513
1161
|
|
|
514
1162
|
/**
|
|
515
|
-
*
|
|
1163
|
+
* @fileoverview
|
|
1164
|
+
* Pre-defined Result constants for common return values.
|
|
1165
|
+
*
|
|
1166
|
+
* These immutable constants can be reused throughout the application to avoid
|
|
1167
|
+
* creating new Result instances for common values like `true`, `false`, `0`, and `void`.
|
|
516
1168
|
*/
|
|
1169
|
+
|
|
517
1170
|
/**
|
|
518
1171
|
* Result constant for `true`.
|
|
519
1172
|
* Can be used anywhere due to immutability.
|
|
1173
|
+
* @example
|
|
1174
|
+
* ```ts
|
|
1175
|
+
* function validate(): Result<boolean, Error> {
|
|
1176
|
+
* return RESULT_TRUE;
|
|
1177
|
+
* }
|
|
1178
|
+
* ```
|
|
520
1179
|
*/
|
|
521
1180
|
declare const RESULT_TRUE: Result<boolean, any>;
|
|
522
1181
|
/**
|
|
523
1182
|
* Result constant for `false`.
|
|
524
1183
|
* Can be used anywhere due to immutability.
|
|
1184
|
+
* @example
|
|
1185
|
+
* ```ts
|
|
1186
|
+
* function validate(): Result<boolean, Error> {
|
|
1187
|
+
* return RESULT_FALSE;
|
|
1188
|
+
* }
|
|
1189
|
+
* ```
|
|
525
1190
|
*/
|
|
526
1191
|
declare const RESULT_FALSE: Result<boolean, any>;
|
|
527
1192
|
/**
|
|
528
1193
|
* Result constant for `0`.
|
|
529
1194
|
* Can be used anywhere due to immutability.
|
|
1195
|
+
* @example
|
|
1196
|
+
* ```ts
|
|
1197
|
+
* function count(): Result<number, Error> {
|
|
1198
|
+
* return RESULT_ZERO;
|
|
1199
|
+
* }
|
|
1200
|
+
* ```
|
|
530
1201
|
*/
|
|
531
1202
|
declare const RESULT_ZERO: Result<number, any>;
|
|
532
1203
|
/**
|
|
533
1204
|
* Result constant for `void` or `()`.
|
|
1205
|
+
* Can be used anywhere due to immutability.
|
|
1206
|
+
* @example
|
|
1207
|
+
* ```ts
|
|
1208
|
+
* function doSomething(): Result<void, Error> {
|
|
1209
|
+
* return RESULT_VOID;
|
|
1210
|
+
* }
|
|
1211
|
+
* ```
|
|
534
1212
|
*/
|
|
535
1213
|
declare const RESULT_VOID: Result<void, any>;
|
|
536
1214
|
|
|
537
1215
|
/**
|
|
538
|
-
*
|
|
1216
|
+
* @fileoverview
|
|
1217
|
+
* Type aliases for commonly used `Result` type combinations.
|
|
1218
|
+
*
|
|
1219
|
+
* These types provide convenient shortcuts for common patterns like:
|
|
1220
|
+
* - Operations that return nothing on success (`VoidResult`)
|
|
1221
|
+
* - I/O operations that may fail with an Error (`IOResult`)
|
|
1222
|
+
* - Async versions of the above
|
|
539
1223
|
*/
|
|
540
1224
|
|
|
541
1225
|
/**
|
|
@@ -573,10 +1257,20 @@ type VoidIOResult = IOResult<void>;
|
|
|
573
1257
|
*/
|
|
574
1258
|
type AsyncVoidIOResult = AsyncIOResult<void>;
|
|
575
1259
|
|
|
1260
|
+
/**
|
|
1261
|
+
* @fileoverview
|
|
1262
|
+
* Extension functions for bridging Promise-based APIs with the Result type.
|
|
1263
|
+
*
|
|
1264
|
+
* This module provides utilities for integrating async/await patterns with Result-based error handling.
|
|
1265
|
+
*/
|
|
1266
|
+
|
|
576
1267
|
/**
|
|
577
1268
|
* Converts a Promise to a Result type, capturing the resolved value in an `Ok`, or the error in an `Err`.
|
|
578
1269
|
* This allows for promise-based asynchronous operations to be handled in a way that is more in line with the Result pattern.
|
|
579
1270
|
*
|
|
1271
|
+
* Note: JavaScript promises can reject with any value, not just `Error` objects.
|
|
1272
|
+
* The error is cast to type `E`, so ensure your error handling accounts for this.
|
|
1273
|
+
*
|
|
580
1274
|
* @typeParam T - The type of the value that the promise resolves to.
|
|
581
1275
|
* @typeParam E - The type of the error that the promise may reject with, defaults to `Error`.
|
|
582
1276
|
* @param p - The promise to convert into a `Result` type.
|
|
@@ -593,9 +1287,27 @@ type AsyncVoidIOResult = AsyncIOResult<void>;
|
|
|
593
1287
|
* });
|
|
594
1288
|
* }
|
|
595
1289
|
* ```
|
|
1290
|
+
*
|
|
1291
|
+
* @example
|
|
1292
|
+
* ```ts
|
|
1293
|
+
* // With custom error type
|
|
1294
|
+
* const result = await promiseToAsyncResult<User, ApiError>(fetchUser(id));
|
|
1295
|
+
* ```
|
|
596
1296
|
*/
|
|
597
1297
|
declare function promiseToAsyncResult<T, E = Error>(p: Promise<T>): Promise<Result<T, E>>;
|
|
598
1298
|
|
|
1299
|
+
/**
|
|
1300
|
+
* @fileoverview
|
|
1301
|
+
* Constructors and factory functions for creating `Option` and `Result` types.
|
|
1302
|
+
*
|
|
1303
|
+
* This module exports:
|
|
1304
|
+
* - `Some<T>(value)` - Creates an Option containing a value
|
|
1305
|
+
* - `None` - Constant representing absence of value
|
|
1306
|
+
* - `Ok<T, E>(value)` - Creates a successful Result
|
|
1307
|
+
* - `Err<T, E>(error)` - Creates a failed Result
|
|
1308
|
+
* - `None` interface - Type overrides for better type inference
|
|
1309
|
+
*/
|
|
1310
|
+
|
|
599
1311
|
/**
|
|
600
1312
|
* Creates an `Option<T>` representing the presence of a value.
|
|
601
1313
|
* This function is typically used to construct an `Option` that contains a value, indicating that the operation yielding the value was successful.
|
|
@@ -626,6 +1338,8 @@ interface None extends Option<never> {
|
|
|
626
1338
|
isNone(): true;
|
|
627
1339
|
isSomeAnd(predicate: (value: never) => boolean): false;
|
|
628
1340
|
isSomeAndAsync(predicate: (value: never) => Promise<boolean>): Promise<false>;
|
|
1341
|
+
isNoneOr(predicate: (value: never) => boolean): true;
|
|
1342
|
+
isNoneOrAsync(predicate: (value: never) => Promise<boolean>): Promise<true>;
|
|
629
1343
|
expect(msg: string): never;
|
|
630
1344
|
unwrap(): never;
|
|
631
1345
|
unwrapOr<T>(defaultValue: T): T;
|
|
@@ -633,18 +1347,18 @@ interface None extends Option<never> {
|
|
|
633
1347
|
unwrapOrElseAsync<T>(fn: () => Promise<T>): Promise<T>;
|
|
634
1348
|
okOr<E>(error: E): Result<never, E>;
|
|
635
1349
|
okOrElse<E>(err: () => E): Result<never, E>;
|
|
636
|
-
transpose(): Result<
|
|
637
|
-
filter(predicate: (value: never) => boolean):
|
|
638
|
-
flatten():
|
|
639
|
-
map<U>(fn: (value: never) => U):
|
|
1350
|
+
transpose(): Result<this, never>;
|
|
1351
|
+
filter(predicate: (value: never) => boolean): this;
|
|
1352
|
+
flatten(): this;
|
|
1353
|
+
map<U>(fn: (value: never) => U): this;
|
|
640
1354
|
mapOr<U>(defaultValue: U, fn: (value: never) => U): U;
|
|
641
1355
|
mapOrElse<U>(defaultFn: () => U, fn: (value: never) => U): U;
|
|
642
|
-
zip<U>(other: Option<U>):
|
|
643
|
-
zipWith<U, R>(other: Option<U>, fn: (value: never, otherValue: U) => R):
|
|
644
|
-
unzip(): [
|
|
645
|
-
and<U>(other: Option<U>):
|
|
646
|
-
andThen<U>(fn: (value: never) => Option<U>):
|
|
647
|
-
andThenAsync<U>(fn: (value: never) => AsyncOption<U>): Promise<
|
|
1356
|
+
zip<U>(other: Option<U>): this;
|
|
1357
|
+
zipWith<U, R>(other: Option<U>, fn: (value: never, otherValue: U) => R): this;
|
|
1358
|
+
unzip(): [this, this];
|
|
1359
|
+
and<U>(other: Option<U>): this;
|
|
1360
|
+
andThen<U>(fn: (value: never) => Option<U>): this;
|
|
1361
|
+
andThenAsync<U>(fn: (value: never) => AsyncOption<U>): Promise<this>;
|
|
648
1362
|
or<T>(other: Option<T>): Option<T>;
|
|
649
1363
|
orElse<T>(fn: () => Option<T>): Option<T>;
|
|
650
1364
|
orElseAsync<T>(fn: () => AsyncOption<T>): AsyncOption<T>;
|
|
@@ -655,6 +1369,24 @@ interface None extends Option<never> {
|
|
|
655
1369
|
/**
|
|
656
1370
|
* A constant representing the `None` case of an `Option`, indicating the absence of a value.
|
|
657
1371
|
* This constant is frozen to ensure it is immutable and cannot be altered, preserving the integrity of `None` throughout the application.
|
|
1372
|
+
*
|
|
1373
|
+
* @example
|
|
1374
|
+
* ```ts
|
|
1375
|
+
* // Use None to represent absence of a value
|
|
1376
|
+
* function findUser(id: number): Option<User> {
|
|
1377
|
+
* const user = users.find(u => u.id === id);
|
|
1378
|
+
* return user ? Some(user) : None;
|
|
1379
|
+
* }
|
|
1380
|
+
*
|
|
1381
|
+
* // None is a singleton, so you can compare by reference
|
|
1382
|
+
* const result = findUser(999);
|
|
1383
|
+
* if (result === None) {
|
|
1384
|
+
* console.log('User not found');
|
|
1385
|
+
* }
|
|
1386
|
+
*
|
|
1387
|
+
* // Use with Option methods
|
|
1388
|
+
* const name = None.unwrapOr('Anonymous'); // 'Anonymous'
|
|
1389
|
+
* ```
|
|
658
1390
|
*/
|
|
659
1391
|
declare const None: None;
|
|
660
1392
|
/**
|
|
@@ -674,11 +1406,35 @@ declare const None: None;
|
|
|
674
1406
|
* }
|
|
675
1407
|
* ```
|
|
676
1408
|
*/
|
|
677
|
-
declare function Ok<T, E>(value: T): Result<T, E>;
|
|
1409
|
+
declare function Ok<T, E = never>(value: T): Result<T, E>;
|
|
678
1410
|
/**
|
|
679
|
-
*
|
|
1411
|
+
* Creates a `Result<void, E>` representing a successful outcome with no value.
|
|
1412
|
+
* This overload is used when the operation succeeds but doesn't produce a meaningful value.
|
|
1413
|
+
*
|
|
1414
|
+
* In Rust, this would be `Ok(())` using the unit type `()`.
|
|
1415
|
+
* Since JavaScript doesn't have a unit type, we use `void` instead.
|
|
1416
|
+
*
|
|
1417
|
+
* @typeParam E - The type of the error that the result could potentially contain.
|
|
1418
|
+
* @returns A `Result<void, E>` representing a successful operation with no value.
|
|
1419
|
+
*
|
|
1420
|
+
* @example
|
|
1421
|
+
* ```ts
|
|
1422
|
+
* function saveToFile(path: string): Result<void, Error> {
|
|
1423
|
+
* try {
|
|
1424
|
+
* fs.writeFileSync(path, data);
|
|
1425
|
+
* return Ok(); // Success with no return value
|
|
1426
|
+
* } catch (e) {
|
|
1427
|
+
* return Err(e as Error);
|
|
1428
|
+
* }
|
|
1429
|
+
* }
|
|
1430
|
+
*
|
|
1431
|
+
* const result = saveToFile('/tmp/data.txt');
|
|
1432
|
+
* if (result.isOk()) {
|
|
1433
|
+
* console.log('File saved successfully');
|
|
1434
|
+
* }
|
|
1435
|
+
* ```
|
|
680
1436
|
*/
|
|
681
|
-
declare function Ok<E>(): Result<void, E>;
|
|
1437
|
+
declare function Ok<E = never>(): Result<void, E>;
|
|
682
1438
|
/**
|
|
683
1439
|
* Creates a `Result<T, E>` representing a failed outcome containing an error.
|
|
684
1440
|
* This function is used to construct a `Result` that signifies the operation failed by containing the error `E`.
|
|
@@ -696,7 +1452,14 @@ declare function Ok<E>(): Result<void, E>;
|
|
|
696
1452
|
* }
|
|
697
1453
|
* ```
|
|
698
1454
|
*/
|
|
699
|
-
declare function Err<T, E>(error: E): Result<T, E>;
|
|
1455
|
+
declare function Err<T = never, E = unknown>(error: E): Result<T, E>;
|
|
1456
|
+
|
|
1457
|
+
/**
|
|
1458
|
+
* @fileoverview
|
|
1459
|
+
* Type guard utilities for checking if values are `Option` or `Result` types.
|
|
1460
|
+
*
|
|
1461
|
+
* These functions provide runtime type checking capabilities for the Option and Result types.
|
|
1462
|
+
*/
|
|
700
1463
|
|
|
701
1464
|
/**
|
|
702
1465
|
* Checks if a value is an `Option`.
|
|
@@ -704,6 +1467,13 @@ declare function Err<T, E>(error: E): Result<T, E>;
|
|
|
704
1467
|
* @typeParam T - The expected type of the value contained within the `Option`.
|
|
705
1468
|
* @param o - The value to be checked as an `Option`.
|
|
706
1469
|
* @returns `true` if the value is an `Option`, otherwise `false`.
|
|
1470
|
+
* @example
|
|
1471
|
+
* ```ts
|
|
1472
|
+
* const x = Some(5);
|
|
1473
|
+
* console.log(isOption(x)); // true
|
|
1474
|
+
* console.log(isOption(null)); // false
|
|
1475
|
+
* console.log(isOption({ value: 5 })); // false
|
|
1476
|
+
* ```
|
|
707
1477
|
*/
|
|
708
1478
|
declare function isOption<T>(o: unknown): o is Option<T>;
|
|
709
1479
|
/**
|
|
@@ -713,8 +1483,1188 @@ declare function isOption<T>(o: unknown): o is Option<T>;
|
|
|
713
1483
|
* @typeParam E - The expected type of the error value contained within the `Result`.
|
|
714
1484
|
* @param r - The value to be checked as a `Result`.
|
|
715
1485
|
* @returns `true` if the value is a `Result`, otherwise `false`.
|
|
1486
|
+
* @example
|
|
1487
|
+
* ```ts
|
|
1488
|
+
* const x = Ok(5);
|
|
1489
|
+
* console.log(isResult(x)); // true
|
|
1490
|
+
* console.log(isResult(null)); // false
|
|
1491
|
+
* console.log(isResult({ value: 5 })); // false
|
|
1492
|
+
* ```
|
|
716
1493
|
*/
|
|
717
1494
|
declare function isResult<T, E>(r: unknown): r is Result<T, E>;
|
|
718
1495
|
|
|
719
|
-
|
|
720
|
-
|
|
1496
|
+
/**
|
|
1497
|
+
* @fileoverview
|
|
1498
|
+
* Internal symbols used to identify `ControlFlow` type variants.
|
|
1499
|
+
*
|
|
1500
|
+
* These symbols are used as property keys to distinguish between `Break` and `Continue` variants.
|
|
1501
|
+
* They provide a reliable way to identify the variant of a `ControlFlow` instance without
|
|
1502
|
+
* relying on method calls or duck typing.
|
|
1503
|
+
*
|
|
1504
|
+
* Note: These symbols are internal implementation details and are not exported as part of the public API.
|
|
1505
|
+
* Use the `isControlFlow` utility function for type checking instead.
|
|
1506
|
+
*/
|
|
1507
|
+
/**
|
|
1508
|
+
* A unique symbol used as a property key to identify the variant of a `ControlFlow` instance.
|
|
1509
|
+
*
|
|
1510
|
+
* When accessed on a `ControlFlow`, returns `'Break'` if the ControlFlow signals early exit,
|
|
1511
|
+
* or `'Continue'` if it signals to proceed as normal.
|
|
1512
|
+
*
|
|
1513
|
+
* This symbol is used internally by the `isControlFlow` utility function to verify
|
|
1514
|
+
* that an object is a valid `ControlFlow` instance.
|
|
1515
|
+
*
|
|
1516
|
+
* @internal
|
|
1517
|
+
*/
|
|
1518
|
+
declare const ControlFlowKindSymbol: unique symbol;
|
|
1519
|
+
|
|
1520
|
+
/**
|
|
1521
|
+
* @fileoverview
|
|
1522
|
+
* Rust-inspired [ControlFlow](https://doc.rust-lang.org/std/ops/enum.ControlFlow.html) for control flow handling.
|
|
1523
|
+
*
|
|
1524
|
+
* `ControlFlow` is used to tell an operation whether it should exit early or go on as usual.
|
|
1525
|
+
* This is useful for:
|
|
1526
|
+
* - Short-circuiting iterators
|
|
1527
|
+
* - Signaling early termination in fold-like operations
|
|
1528
|
+
* - Implementing custom control flow patterns
|
|
1529
|
+
*/
|
|
1530
|
+
|
|
1531
|
+
/**
|
|
1532
|
+
* Used to tell an operation whether it should exit early or go on as usual.
|
|
1533
|
+
*
|
|
1534
|
+
* This is the return type of `try_fold` and similar iterator methods that support
|
|
1535
|
+
* short-circuiting. It can also be used in custom control flow scenarios.
|
|
1536
|
+
*
|
|
1537
|
+
* @typeParam B - The type of the value returned on `Break` (early exit).
|
|
1538
|
+
* @typeParam C - The type of the value returned on `Continue` (default: `void`).
|
|
1539
|
+
*
|
|
1540
|
+
* @example
|
|
1541
|
+
* ```ts
|
|
1542
|
+
* // Using ControlFlow to short-circuit a search
|
|
1543
|
+
* function findFirstNegative(numbers: number[]): Option<number> {
|
|
1544
|
+
* let result: Option<number> = None;
|
|
1545
|
+
*
|
|
1546
|
+
* for (const n of numbers) {
|
|
1547
|
+
* const flow = n < 0 ? Break(n) : Continue();
|
|
1548
|
+
* if (flow.isBreak()) {
|
|
1549
|
+
* result = Some(flow.breakValue().unwrap());
|
|
1550
|
+
* break;
|
|
1551
|
+
* }
|
|
1552
|
+
* }
|
|
1553
|
+
*
|
|
1554
|
+
* return result;
|
|
1555
|
+
* }
|
|
1556
|
+
* ```
|
|
1557
|
+
*
|
|
1558
|
+
* @example
|
|
1559
|
+
* ```ts
|
|
1560
|
+
* // Using ControlFlow in a custom fold operation
|
|
1561
|
+
* function tryFold<T, Acc>(
|
|
1562
|
+
* arr: T[],
|
|
1563
|
+
* init: Acc,
|
|
1564
|
+
* f: (acc: Acc, item: T) => ControlFlow<Acc, Acc>
|
|
1565
|
+
* ): ControlFlow<Acc, Acc> {
|
|
1566
|
+
* let acc = init;
|
|
1567
|
+
* for (const item of arr) {
|
|
1568
|
+
* const flow = f(acc, item);
|
|
1569
|
+
* if (flow.isBreak()) {
|
|
1570
|
+
* return flow;
|
|
1571
|
+
* }
|
|
1572
|
+
* acc = flow.continueValue().unwrap();
|
|
1573
|
+
* }
|
|
1574
|
+
* return Continue(acc);
|
|
1575
|
+
* }
|
|
1576
|
+
* ```
|
|
1577
|
+
*/
|
|
1578
|
+
interface ControlFlow<B, C = void> {
|
|
1579
|
+
/**
|
|
1580
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
1581
|
+
* Returns `'ControlFlow'` so that `Object.prototype.toString.call(flow)` produces `'[object ControlFlow]'`.
|
|
1582
|
+
*
|
|
1583
|
+
* This enables reliable type identification even across different execution contexts (e.g., iframes, different module instances).
|
|
1584
|
+
*
|
|
1585
|
+
* @example
|
|
1586
|
+
* ```ts
|
|
1587
|
+
* const x = Break(5);
|
|
1588
|
+
* console.log(Object.prototype.toString.call(x)); // '[object ControlFlow]'
|
|
1589
|
+
* ```
|
|
1590
|
+
*
|
|
1591
|
+
* @internal
|
|
1592
|
+
*/
|
|
1593
|
+
readonly [Symbol.toStringTag]: 'ControlFlow';
|
|
1594
|
+
/**
|
|
1595
|
+
* A unique symbol property used to identify the variant of this `ControlFlow`.
|
|
1596
|
+
* Returns `'Break'` if the ControlFlow signals early exit, or `'Continue'` if it signals to proceed as normal.
|
|
1597
|
+
*
|
|
1598
|
+
* This is used internally by the `isControlFlow` utility function to verify that an object is a valid `ControlFlow` instance,
|
|
1599
|
+
* and to distinguish between `Break` and `Continue` variants without calling methods.
|
|
1600
|
+
*
|
|
1601
|
+
* Note: The symbol itself is not exported as part of the public API.
|
|
1602
|
+
* Use the `isControlFlow` utility function or the `isBreak()`/`isContinue()` methods for type checking.
|
|
1603
|
+
*
|
|
1604
|
+
* @internal
|
|
1605
|
+
*/
|
|
1606
|
+
readonly [ControlFlowKindSymbol]: 'Break' | 'Continue';
|
|
1607
|
+
/**
|
|
1608
|
+
* Returns `true` if this is a `Break` variant.
|
|
1609
|
+
*
|
|
1610
|
+
* @example
|
|
1611
|
+
* ```ts
|
|
1612
|
+
* console.log(Break(3).isBreak()); // true
|
|
1613
|
+
* console.log(Continue().isBreak()); // false
|
|
1614
|
+
* ```
|
|
1615
|
+
*/
|
|
1616
|
+
isBreak(): boolean;
|
|
1617
|
+
/**
|
|
1618
|
+
* Returns `true` if this is a `Continue` variant.
|
|
1619
|
+
*
|
|
1620
|
+
* @example
|
|
1621
|
+
* ```ts
|
|
1622
|
+
* console.log(Continue().isContinue()); // true
|
|
1623
|
+
* console.log(Break(3).isContinue()); // false
|
|
1624
|
+
* ```
|
|
1625
|
+
*/
|
|
1626
|
+
isContinue(): boolean;
|
|
1627
|
+
/**
|
|
1628
|
+
* Converts the `ControlFlow` into an `Option` which is `Some` if the
|
|
1629
|
+
* `ControlFlow` was `Break` and `None` otherwise.
|
|
1630
|
+
*
|
|
1631
|
+
* @returns `Some(value)` if `Break`, `None` if `Continue`.
|
|
1632
|
+
*
|
|
1633
|
+
* @example
|
|
1634
|
+
* ```ts
|
|
1635
|
+
* console.log(Break(3).breakValue()); // Some(3)
|
|
1636
|
+
* console.log(Continue().breakValue()); // None
|
|
1637
|
+
* ```
|
|
1638
|
+
*/
|
|
1639
|
+
breakValue(): Option<B>;
|
|
1640
|
+
/**
|
|
1641
|
+
* Converts the `ControlFlow` into an `Option` which is `Some` if the
|
|
1642
|
+
* `ControlFlow` was `Continue` and `None` otherwise.
|
|
1643
|
+
*
|
|
1644
|
+
* @returns `Some(value)` if `Continue`, `None` if `Break`.
|
|
1645
|
+
*
|
|
1646
|
+
* @example
|
|
1647
|
+
* ```ts
|
|
1648
|
+
* console.log(Continue(5).continueValue()); // Some(5)
|
|
1649
|
+
* console.log(Break(3).continueValue()); // None
|
|
1650
|
+
* ```
|
|
1651
|
+
*/
|
|
1652
|
+
continueValue(): Option<C>;
|
|
1653
|
+
/**
|
|
1654
|
+
* Maps `ControlFlow<B, C>` to `ControlFlow<T, C>` by applying a function
|
|
1655
|
+
* to the break value in case it exists.
|
|
1656
|
+
*
|
|
1657
|
+
* @typeParam T - The type of the new break value.
|
|
1658
|
+
* @param fn - A function to apply to the break value.
|
|
1659
|
+
* @returns A new `ControlFlow` with the mapped break value.
|
|
1660
|
+
*
|
|
1661
|
+
* @example
|
|
1662
|
+
* ```ts
|
|
1663
|
+
* const flow = Break(3);
|
|
1664
|
+
* console.log(flow.mapBreak(v => v * 2).breakValue()); // Some(6)
|
|
1665
|
+
* ```
|
|
1666
|
+
*/
|
|
1667
|
+
mapBreak<T>(fn: (value: B) => T): ControlFlow<T, C>;
|
|
1668
|
+
/**
|
|
1669
|
+
* Maps `ControlFlow<B, C>` to `ControlFlow<B, T>` by applying a function
|
|
1670
|
+
* to the continue value in case it exists.
|
|
1671
|
+
*
|
|
1672
|
+
* @typeParam T - The type of the new continue value.
|
|
1673
|
+
* @param fn - A function to apply to the continue value.
|
|
1674
|
+
* @returns A new `ControlFlow` with the mapped continue value.
|
|
1675
|
+
*
|
|
1676
|
+
* @example
|
|
1677
|
+
* ```ts
|
|
1678
|
+
* const flow = Continue(5);
|
|
1679
|
+
* console.log(flow.mapContinue(v => v * 2).continueValue()); // Some(10)
|
|
1680
|
+
* ```
|
|
1681
|
+
*/
|
|
1682
|
+
mapContinue<T>(fn: (value: C) => T): ControlFlow<B, T>;
|
|
1683
|
+
/**
|
|
1684
|
+
* Converts the `ControlFlow` into a `Result` which is `Ok` if the
|
|
1685
|
+
* `ControlFlow` was `Break` and `Err` otherwise.
|
|
1686
|
+
*
|
|
1687
|
+
* @returns `Ok(breakValue)` if `Break`, `Err(continueValue)` if `Continue`.
|
|
1688
|
+
*
|
|
1689
|
+
* @example
|
|
1690
|
+
* ```ts
|
|
1691
|
+
* console.log(Break(3).breakOk()); // Ok(3)
|
|
1692
|
+
* console.log(Continue('still going').breakOk()); // Err('still going')
|
|
1693
|
+
* ```
|
|
1694
|
+
*/
|
|
1695
|
+
breakOk(): Result<B, C>;
|
|
1696
|
+
/**
|
|
1697
|
+
* Converts the `ControlFlow` into a `Result` which is `Ok` if the
|
|
1698
|
+
* `ControlFlow` was `Continue` and `Err` otherwise.
|
|
1699
|
+
*
|
|
1700
|
+
* @returns `Ok(continueValue)` if `Continue`, `Err(breakValue)` if `Break`.
|
|
1701
|
+
*
|
|
1702
|
+
* @example
|
|
1703
|
+
* ```ts
|
|
1704
|
+
* console.log(Continue(5).continueOk()); // Ok(5)
|
|
1705
|
+
* console.log(Break('stopped').continueOk()); // Err('stopped')
|
|
1706
|
+
* ```
|
|
1707
|
+
*/
|
|
1708
|
+
continueOk(): Result<C, B>;
|
|
1709
|
+
/**
|
|
1710
|
+
* Custom `toString` implementation that uses the `ControlFlow`'s contained value.
|
|
1711
|
+
* @example
|
|
1712
|
+
* ```ts
|
|
1713
|
+
* console.log(Break(5).toString()); // 'Break(5)'
|
|
1714
|
+
* console.log(Continue('ok').toString()); // 'Continue(ok)'
|
|
1715
|
+
* ```
|
|
1716
|
+
*/
|
|
1717
|
+
toString(): string;
|
|
1718
|
+
}
|
|
1719
|
+
/**
|
|
1720
|
+
* Creates a `Break` variant of `ControlFlow`.
|
|
1721
|
+
*
|
|
1722
|
+
* Use this to signal that an operation should exit early with the given value.
|
|
1723
|
+
*
|
|
1724
|
+
* @typeParam B - The type of the break value.
|
|
1725
|
+
* @typeParam C - The type of the continue value (defaults to `void` when a value is provided).
|
|
1726
|
+
* @param value - The value to return on break.
|
|
1727
|
+
* @returns A `ControlFlow` in the `Break` state.
|
|
1728
|
+
*
|
|
1729
|
+
* @example
|
|
1730
|
+
* ```ts
|
|
1731
|
+
* const flow = Break('found it');
|
|
1732
|
+
* console.log(flow.isBreak()); // true
|
|
1733
|
+
* console.log(flow.breakValue().unwrap()); // 'found it'
|
|
1734
|
+
*
|
|
1735
|
+
* const voidFlow = Break();
|
|
1736
|
+
* console.log(voidFlow.isBreak()); // true
|
|
1737
|
+
* ```
|
|
1738
|
+
*/
|
|
1739
|
+
declare function Break<B, C = never>(value: B): ControlFlow<B, C>;
|
|
1740
|
+
/**
|
|
1741
|
+
* Creates a `Break` variant of `ControlFlow` with no value.
|
|
1742
|
+
* This overload is used when the operation exits early but doesn't produce a meaningful value.
|
|
1743
|
+
*
|
|
1744
|
+
* @typeParam C - The type of the continue value (allows type specification when chaining with Continue).
|
|
1745
|
+
* @returns A `ControlFlow<void, C>` in the `Break` state.
|
|
1746
|
+
*
|
|
1747
|
+
* @example
|
|
1748
|
+
* ```ts
|
|
1749
|
+
* const voidFlow = Break();
|
|
1750
|
+
* console.log(voidFlow.isBreak()); // true
|
|
1751
|
+
* console.log(voidFlow.breakValue()); // Some(undefined)
|
|
1752
|
+
*
|
|
1753
|
+
* // With explicit type parameter
|
|
1754
|
+
* const typedFlow = Break<number>(); // ControlFlow<void, number>
|
|
1755
|
+
* ```
|
|
1756
|
+
*/
|
|
1757
|
+
declare function Break<C = never>(): ControlFlow<void, C>;
|
|
1758
|
+
/**
|
|
1759
|
+
* Creates a `Continue` variant of `ControlFlow`.
|
|
1760
|
+
*
|
|
1761
|
+
* Use this to signal that an operation should continue as normal.
|
|
1762
|
+
*
|
|
1763
|
+
* @typeParam B - The type of the break value (defaults to `void` when a value is provided).
|
|
1764
|
+
* @typeParam C - The type of the continue value.
|
|
1765
|
+
* @param value - The value to carry forward (optional, defaults to `undefined`).
|
|
1766
|
+
* @returns A `ControlFlow` in the `Continue` state.
|
|
1767
|
+
*
|
|
1768
|
+
* @example
|
|
1769
|
+
* ```ts
|
|
1770
|
+
* const flow = Continue();
|
|
1771
|
+
* console.log(flow.isContinue()); // true
|
|
1772
|
+
*
|
|
1773
|
+
* const flowWithValue = Continue(42);
|
|
1774
|
+
* console.log(flowWithValue.continueValue().unwrap()); // 42
|
|
1775
|
+
* ```
|
|
1776
|
+
*/
|
|
1777
|
+
declare function Continue<B = never, C = void>(value: C): ControlFlow<B, C>;
|
|
1778
|
+
/**
|
|
1779
|
+
* Creates a `Continue` variant of `ControlFlow` with no value.
|
|
1780
|
+
* This overload is used when the operation continues but doesn't carry a meaningful value.
|
|
1781
|
+
*
|
|
1782
|
+
* @typeParam B - The type of the break value (allows type specification when chaining with Break).
|
|
1783
|
+
* @returns A `ControlFlow<B, void>` in the `Continue` state.
|
|
1784
|
+
*
|
|
1785
|
+
* @example
|
|
1786
|
+
* ```ts
|
|
1787
|
+
* const voidFlow = Continue();
|
|
1788
|
+
* console.log(voidFlow.isContinue()); // true
|
|
1789
|
+
* console.log(voidFlow.continueValue()); // Some(undefined)
|
|
1790
|
+
*
|
|
1791
|
+
* // With explicit type parameter
|
|
1792
|
+
* const typedFlow = Continue<string>(); // ControlFlow<string, void>
|
|
1793
|
+
* ```
|
|
1794
|
+
*/
|
|
1795
|
+
declare function Continue<B = never>(): ControlFlow<B, void>;
|
|
1796
|
+
|
|
1797
|
+
/**
|
|
1798
|
+
* @fileoverview
|
|
1799
|
+
* Type guard utilities for checking if values are `ControlFlow` types.
|
|
1800
|
+
*
|
|
1801
|
+
* These functions provide runtime type checking capabilities for the ControlFlow type.
|
|
1802
|
+
*/
|
|
1803
|
+
|
|
1804
|
+
/**
|
|
1805
|
+
* Checks if a value is a `ControlFlow`.
|
|
1806
|
+
*
|
|
1807
|
+
* @typeParam B - The expected type of the break value contained within the `ControlFlow`.
|
|
1808
|
+
* @typeParam C - The expected type of the continue value contained within the `ControlFlow`.
|
|
1809
|
+
* @param cf - The value to be checked as a `ControlFlow`.
|
|
1810
|
+
* @returns `true` if the value is a `ControlFlow`, otherwise `false`.
|
|
1811
|
+
* @example
|
|
1812
|
+
* ```ts
|
|
1813
|
+
* const x = Break(5);
|
|
1814
|
+
* console.log(isControlFlow(x)); // true
|
|
1815
|
+
* console.log(isControlFlow(null)); // false
|
|
1816
|
+
* console.log(isControlFlow({ isBreak: () => true })); // false
|
|
1817
|
+
* ```
|
|
1818
|
+
*/
|
|
1819
|
+
declare function isControlFlow<B, C>(cf: unknown): cf is ControlFlow<B, C>;
|
|
1820
|
+
|
|
1821
|
+
/**
|
|
1822
|
+
* @fileoverview
|
|
1823
|
+
* Rust-inspired [LazyLock](https://doc.rust-lang.org/std/sync/struct.LazyLock.html) for lazy initialization.
|
|
1824
|
+
*
|
|
1825
|
+
* `Lazy<T>` is a value which is initialized on the first access. Unlike `Once<T>`,
|
|
1826
|
+
* the initialization function is provided at construction time.
|
|
1827
|
+
*/
|
|
1828
|
+
|
|
1829
|
+
/**
|
|
1830
|
+
* A value which is initialized on the first access.
|
|
1831
|
+
*
|
|
1832
|
+
* This is a lazily evaluated value. The initialization function is provided
|
|
1833
|
+
* at construction time and executed on first access. Subsequent accesses
|
|
1834
|
+
* return the cached value.
|
|
1835
|
+
*
|
|
1836
|
+
* Unlike `Once<T>`, which allows setting values manually or with different
|
|
1837
|
+
* initializers, `Lazy<T>` binds the initializer at creation time.
|
|
1838
|
+
*
|
|
1839
|
+
* @typeParam T - The type of the value stored.
|
|
1840
|
+
*
|
|
1841
|
+
* @example
|
|
1842
|
+
* ```ts
|
|
1843
|
+
* const expensive = Lazy(() => {
|
|
1844
|
+
* console.log('Computing...');
|
|
1845
|
+
* return heavyComputation();
|
|
1846
|
+
* });
|
|
1847
|
+
*
|
|
1848
|
+
* // Nothing computed yet
|
|
1849
|
+
* console.log(expensive.isInitialized()); // false
|
|
1850
|
+
*
|
|
1851
|
+
* // First access triggers computation
|
|
1852
|
+
* const value = expensive.force(); // logs "Computing..."
|
|
1853
|
+
*
|
|
1854
|
+
* // Subsequent access returns cached value
|
|
1855
|
+
* const same = expensive.force(); // no log, returns cached value
|
|
1856
|
+
* ```
|
|
1857
|
+
*/
|
|
1858
|
+
interface Lazy<T> {
|
|
1859
|
+
/**
|
|
1860
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
1861
|
+
* Returns `'Lazy'` so that `Object.prototype.toString.call(lazy)` produces `'[object Lazy]'`.
|
|
1862
|
+
*
|
|
1863
|
+
* @internal
|
|
1864
|
+
*/
|
|
1865
|
+
readonly [Symbol.toStringTag]: 'Lazy';
|
|
1866
|
+
/**
|
|
1867
|
+
* Forces the evaluation of this lazy value and returns the result.
|
|
1868
|
+
*
|
|
1869
|
+
* If the value has already been initialized, returns the cached value.
|
|
1870
|
+
* Otherwise, executes the initialization function, caches the result,
|
|
1871
|
+
* and returns it.
|
|
1872
|
+
*
|
|
1873
|
+
* @returns The initialized value.
|
|
1874
|
+
*
|
|
1875
|
+
* @example
|
|
1876
|
+
* ```ts
|
|
1877
|
+
* const lazy = Lazy(() => 42);
|
|
1878
|
+
* console.log(lazy.force()); // 42
|
|
1879
|
+
* console.log(lazy.force()); // 42 (cached)
|
|
1880
|
+
* ```
|
|
1881
|
+
*/
|
|
1882
|
+
force(): T;
|
|
1883
|
+
/**
|
|
1884
|
+
* Gets the value if it has been initialized.
|
|
1885
|
+
*
|
|
1886
|
+
* Unlike `force()`, this does not trigger initialization.
|
|
1887
|
+
*
|
|
1888
|
+
* @returns `Some(value)` if initialized, `None` otherwise.
|
|
1889
|
+
*
|
|
1890
|
+
* @example
|
|
1891
|
+
* ```ts
|
|
1892
|
+
* const lazy = Lazy(() => 42);
|
|
1893
|
+
* console.log(lazy.get()); // None
|
|
1894
|
+
*
|
|
1895
|
+
* lazy.force();
|
|
1896
|
+
* console.log(lazy.get()); // Some(42)
|
|
1897
|
+
* ```
|
|
1898
|
+
*/
|
|
1899
|
+
get(): Option<T>;
|
|
1900
|
+
/**
|
|
1901
|
+
* Returns `true` if the value has been initialized.
|
|
1902
|
+
*
|
|
1903
|
+
* @example
|
|
1904
|
+
* ```ts
|
|
1905
|
+
* const lazy = Lazy(() => 42);
|
|
1906
|
+
* console.log(lazy.isInitialized()); // false
|
|
1907
|
+
*
|
|
1908
|
+
* lazy.force();
|
|
1909
|
+
* console.log(lazy.isInitialized()); // true
|
|
1910
|
+
* ```
|
|
1911
|
+
*/
|
|
1912
|
+
isInitialized(): boolean;
|
|
1913
|
+
/**
|
|
1914
|
+
* Custom `toString` implementation.
|
|
1915
|
+
* @example
|
|
1916
|
+
* ```ts
|
|
1917
|
+
* const lazy = Lazy(() => 42);
|
|
1918
|
+
* console.log(lazy.toString()); // 'Lazy(<uninitialized>)'
|
|
1919
|
+
*
|
|
1920
|
+
* lazy.force();
|
|
1921
|
+
* console.log(lazy.toString()); // 'Lazy(42)'
|
|
1922
|
+
* ```
|
|
1923
|
+
*/
|
|
1924
|
+
toString(): string;
|
|
1925
|
+
}
|
|
1926
|
+
/**
|
|
1927
|
+
* Creates a new `Lazy<T>` with the given synchronous initialization function.
|
|
1928
|
+
*
|
|
1929
|
+
* The function is called at most once, on first access via `force()`.
|
|
1930
|
+
*
|
|
1931
|
+
* @typeParam T - The type of value to store.
|
|
1932
|
+
* @param fn - The initialization function that produces the value.
|
|
1933
|
+
* @returns A new `Lazy<T>` instance.
|
|
1934
|
+
*
|
|
1935
|
+
* @example
|
|
1936
|
+
* ```ts
|
|
1937
|
+
* // Basic usage
|
|
1938
|
+
* const lazy = Lazy(() => {
|
|
1939
|
+
* console.log('Initializing');
|
|
1940
|
+
* return 42;
|
|
1941
|
+
* });
|
|
1942
|
+
*
|
|
1943
|
+
* console.log(lazy.isInitialized()); // false
|
|
1944
|
+
* console.log(lazy.force()); // logs "Initializing", returns 42
|
|
1945
|
+
* console.log(lazy.isInitialized()); // true
|
|
1946
|
+
* console.log(lazy.force()); // returns 42 (no log)
|
|
1947
|
+
* ```
|
|
1948
|
+
*
|
|
1949
|
+
* @example
|
|
1950
|
+
* ```ts
|
|
1951
|
+
* // Lazy singleton pattern
|
|
1952
|
+
* const logger = Lazy(() => new Logger('app'));
|
|
1953
|
+
*
|
|
1954
|
+
* function getLogger(): Logger {
|
|
1955
|
+
* return logger.force();
|
|
1956
|
+
* }
|
|
1957
|
+
* ```
|
|
1958
|
+
*
|
|
1959
|
+
* @example
|
|
1960
|
+
* ```ts
|
|
1961
|
+
* // Expensive computation
|
|
1962
|
+
* const fibonacci = Lazy(() => {
|
|
1963
|
+
* function fib(n: number): number {
|
|
1964
|
+
* if (n <= 1) return n;
|
|
1965
|
+
* return fib(n - 1) + fib(n - 2);
|
|
1966
|
+
* }
|
|
1967
|
+
* return fib(40); // Only computed once
|
|
1968
|
+
* });
|
|
1969
|
+
* ```
|
|
1970
|
+
*/
|
|
1971
|
+
declare function Lazy<T>(fn: () => T): Lazy<T>;
|
|
1972
|
+
/**
|
|
1973
|
+
* A value which is initialized asynchronously on the first access.
|
|
1974
|
+
*
|
|
1975
|
+
* Similar to `Lazy<T>`, but the initialization function is async.
|
|
1976
|
+
* If multiple calls to `force()` occur concurrently before initialization
|
|
1977
|
+
* completes, only one initialization will run.
|
|
1978
|
+
*
|
|
1979
|
+
* @typeParam T - The type of the value stored.
|
|
1980
|
+
*
|
|
1981
|
+
* @example
|
|
1982
|
+
* ```ts
|
|
1983
|
+
* const db = LazyAsync(async () => {
|
|
1984
|
+
* console.log('Connecting...');
|
|
1985
|
+
* return await Database.connect(url);
|
|
1986
|
+
* });
|
|
1987
|
+
*
|
|
1988
|
+
* // Multiple concurrent accesses - only one connection
|
|
1989
|
+
* const [db1, db2] = await Promise.all([
|
|
1990
|
+
* db.force(),
|
|
1991
|
+
* db.force(),
|
|
1992
|
+
* ]);
|
|
1993
|
+
* // db1 === db2
|
|
1994
|
+
* ```
|
|
1995
|
+
*/
|
|
1996
|
+
interface LazyAsync<T> {
|
|
1997
|
+
/**
|
|
1998
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
1999
|
+
* Returns `'LazyAsync'` so that `Object.prototype.toString.call(lazy)` produces `'[object LazyAsync]'`.
|
|
2000
|
+
*
|
|
2001
|
+
* @internal
|
|
2002
|
+
*/
|
|
2003
|
+
readonly [Symbol.toStringTag]: 'LazyAsync';
|
|
2004
|
+
/**
|
|
2005
|
+
* Forces the evaluation of this lazy value and returns a promise to the result.
|
|
2006
|
+
*
|
|
2007
|
+
* If the value has already been initialized, returns the cached value.
|
|
2008
|
+
* If initialization is in progress, waits for it to complete.
|
|
2009
|
+
* Otherwise, starts initialization.
|
|
2010
|
+
*
|
|
2011
|
+
* @returns A promise that resolves to the initialized value.
|
|
2012
|
+
*
|
|
2013
|
+
* @example
|
|
2014
|
+
* ```ts
|
|
2015
|
+
* const lazy = LazyAsync(async () => {
|
|
2016
|
+
* await delay(100);
|
|
2017
|
+
* return 42;
|
|
2018
|
+
* });
|
|
2019
|
+
* console.log(await lazy.force()); // 42
|
|
2020
|
+
* ```
|
|
2021
|
+
*/
|
|
2022
|
+
force(): Promise<T>;
|
|
2023
|
+
/**
|
|
2024
|
+
* Gets the value if it has been initialized.
|
|
2025
|
+
*
|
|
2026
|
+
* Unlike `force()`, this does not trigger initialization.
|
|
2027
|
+
*
|
|
2028
|
+
* @returns `Some(value)` if initialized, `None` otherwise.
|
|
2029
|
+
*
|
|
2030
|
+
* @example
|
|
2031
|
+
* ```ts
|
|
2032
|
+
* const lazy = LazyAsync(async () => 42);
|
|
2033
|
+
* console.log(lazy.get()); // None
|
|
2034
|
+
*
|
|
2035
|
+
* await lazy.force();
|
|
2036
|
+
* console.log(lazy.get()); // Some(42)
|
|
2037
|
+
* ```
|
|
2038
|
+
*/
|
|
2039
|
+
get(): Option<T>;
|
|
2040
|
+
/**
|
|
2041
|
+
* Returns `true` if the value has been initialized.
|
|
2042
|
+
*
|
|
2043
|
+
* Note: Returns `false` while initialization is in progress.
|
|
2044
|
+
*
|
|
2045
|
+
* @example
|
|
2046
|
+
* ```ts
|
|
2047
|
+
* const lazy = LazyAsync(async () => 42);
|
|
2048
|
+
* console.log(lazy.isInitialized()); // false
|
|
2049
|
+
*
|
|
2050
|
+
* await lazy.force();
|
|
2051
|
+
* console.log(lazy.isInitialized()); // true
|
|
2052
|
+
* ```
|
|
2053
|
+
*/
|
|
2054
|
+
isInitialized(): boolean;
|
|
2055
|
+
/**
|
|
2056
|
+
* Custom `toString` implementation.
|
|
2057
|
+
* @example
|
|
2058
|
+
* ```ts
|
|
2059
|
+
* const lazy = LazyAsync(async () => 42);
|
|
2060
|
+
* console.log(lazy.toString()); // 'LazyAsync(<uninitialized>)'
|
|
2061
|
+
*
|
|
2062
|
+
* await lazy.force();
|
|
2063
|
+
* console.log(lazy.toString()); // 'LazyAsync(42)'
|
|
2064
|
+
* ```
|
|
2065
|
+
*/
|
|
2066
|
+
toString(): string;
|
|
2067
|
+
}
|
|
2068
|
+
/**
|
|
2069
|
+
* Creates a new `LazyAsync<T>` with the given async initialization function.
|
|
2070
|
+
*
|
|
2071
|
+
* The function is called at most once, on first access via `force()`.
|
|
2072
|
+
* Concurrent calls to `force()` before initialization completes will
|
|
2073
|
+
* wait for the single initialization to finish.
|
|
2074
|
+
*
|
|
2075
|
+
* @typeParam T - The type of value to store.
|
|
2076
|
+
* @param fn - The async initialization function that produces the value.
|
|
2077
|
+
* @returns A new `LazyAsync<T>` instance.
|
|
2078
|
+
*
|
|
2079
|
+
* @example
|
|
2080
|
+
* ```ts
|
|
2081
|
+
* // Basic usage
|
|
2082
|
+
* const lazy = LazyAsync(async () => {
|
|
2083
|
+
* const response = await fetch('/api/data');
|
|
2084
|
+
* return await response.json();
|
|
2085
|
+
* });
|
|
2086
|
+
*
|
|
2087
|
+
* const data = await lazy.force();
|
|
2088
|
+
* ```
|
|
2089
|
+
*
|
|
2090
|
+
* @example
|
|
2091
|
+
* ```ts
|
|
2092
|
+
* // Database connection singleton
|
|
2093
|
+
* const db = LazyAsync(async () => {
|
|
2094
|
+
* console.log('Connecting to database...');
|
|
2095
|
+
* return await Database.connect(connectionString);
|
|
2096
|
+
* });
|
|
2097
|
+
*
|
|
2098
|
+
* async function getDb(): Promise<Database> {
|
|
2099
|
+
* return await db.force();
|
|
2100
|
+
* }
|
|
2101
|
+
*
|
|
2102
|
+
* // Multiple calls - connection happens only once
|
|
2103
|
+
* const [db1, db2] = await Promise.all([getDb(), getDb()]);
|
|
2104
|
+
* console.log(db1 === db2); // true
|
|
2105
|
+
* ```
|
|
2106
|
+
*
|
|
2107
|
+
* @example
|
|
2108
|
+
* ```ts
|
|
2109
|
+
* // Configuration loader
|
|
2110
|
+
* const config = LazyAsync(async () => {
|
|
2111
|
+
* const response = await fetch('/api/config');
|
|
2112
|
+
* if (!response.ok) {
|
|
2113
|
+
* throw new Error(`Failed to load config: ${response.status}`);
|
|
2114
|
+
* }
|
|
2115
|
+
* return await response.json() as Config;
|
|
2116
|
+
* });
|
|
2117
|
+
*
|
|
2118
|
+
* // Used throughout the app
|
|
2119
|
+
* async function getApiEndpoint(): Promise<string> {
|
|
2120
|
+
* const cfg = await config.force();
|
|
2121
|
+
* return cfg.apiEndpoint;
|
|
2122
|
+
* }
|
|
2123
|
+
* ```
|
|
2124
|
+
*/
|
|
2125
|
+
declare function LazyAsync<T>(fn: () => Promise<T>): LazyAsync<T>;
|
|
2126
|
+
|
|
2127
|
+
/**
|
|
2128
|
+
* @fileoverview
|
|
2129
|
+
* Rust-inspired [Mutex](https://doc.rust-lang.org/std/sync/struct.Mutex.html) for async mutual exclusion.
|
|
2130
|
+
*
|
|
2131
|
+
* In JavaScript's single-threaded environment, `Mutex<T>` is used to serialize
|
|
2132
|
+
* async operations, ensuring only one async task accesses the protected resource at a time.
|
|
2133
|
+
*/
|
|
2134
|
+
|
|
2135
|
+
/**
|
|
2136
|
+
* A guard that provides access to the mutex-protected value.
|
|
2137
|
+
*
|
|
2138
|
+
* The guard must be released after use by calling `unlock()`.
|
|
2139
|
+
* Failure to unlock will cause deadlock for subsequent lock attempts.
|
|
2140
|
+
*
|
|
2141
|
+
* @typeParam T - The type of the protected value.
|
|
2142
|
+
*/
|
|
2143
|
+
interface MutexGuard<T> {
|
|
2144
|
+
/**
|
|
2145
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
2146
|
+
* Returns `'MutexGuard'` so that `Object.prototype.toString.call(guard)` produces `'[object MutexGuard]'`.
|
|
2147
|
+
*
|
|
2148
|
+
* @internal
|
|
2149
|
+
*/
|
|
2150
|
+
readonly [Symbol.toStringTag]: 'MutexGuard';
|
|
2151
|
+
/**
|
|
2152
|
+
* The protected value. Can be read or modified while the guard is held.
|
|
2153
|
+
*/
|
|
2154
|
+
value: T;
|
|
2155
|
+
/**
|
|
2156
|
+
* Releases the lock, allowing other waiters to acquire it.
|
|
2157
|
+
*
|
|
2158
|
+
* Must be called when done with the protected value.
|
|
2159
|
+
* After calling `unlock()`, the guard should not be used.
|
|
2160
|
+
*
|
|
2161
|
+
* @example
|
|
2162
|
+
* ```ts
|
|
2163
|
+
* const guard = await mutex.lock();
|
|
2164
|
+
* try {
|
|
2165
|
+
* guard.value.push('item');
|
|
2166
|
+
* } finally {
|
|
2167
|
+
* guard.unlock();
|
|
2168
|
+
* }
|
|
2169
|
+
* ```
|
|
2170
|
+
*/
|
|
2171
|
+
unlock(): void;
|
|
2172
|
+
/**
|
|
2173
|
+
* Custom `toString` implementation.
|
|
2174
|
+
* @example
|
|
2175
|
+
* ```ts
|
|
2176
|
+
* const guard = await mutex.lock();
|
|
2177
|
+
* console.log(guard.toString()); // 'MutexGuard(42)'
|
|
2178
|
+
* ```
|
|
2179
|
+
*/
|
|
2180
|
+
toString(): string;
|
|
2181
|
+
}
|
|
2182
|
+
/**
|
|
2183
|
+
* An async mutual exclusion primitive for protecting shared data.
|
|
2184
|
+
*
|
|
2185
|
+
* This mutex provides exclusive access to the contained value, ensuring
|
|
2186
|
+
* that only one async operation can access it at a time. This is useful
|
|
2187
|
+
* for preventing race conditions in async code.
|
|
2188
|
+
*
|
|
2189
|
+
* Unlike Rust's Mutex which is for multi-threading, this JavaScript version
|
|
2190
|
+
* serializes async operations in the single-threaded event loop.
|
|
2191
|
+
*
|
|
2192
|
+
* @typeParam T - The type of the protected value.
|
|
2193
|
+
*
|
|
2194
|
+
* @example
|
|
2195
|
+
* ```ts
|
|
2196
|
+
* const mutex = Mutex({ balance: 100 });
|
|
2197
|
+
*
|
|
2198
|
+
* // Safe concurrent updates
|
|
2199
|
+
* await Promise.all([
|
|
2200
|
+
* mutex.withLock(async (account) => {
|
|
2201
|
+
* account.balance -= 50;
|
|
2202
|
+
* }),
|
|
2203
|
+
* mutex.withLock(async (account) => {
|
|
2204
|
+
* account.balance += 30;
|
|
2205
|
+
* }),
|
|
2206
|
+
* ]);
|
|
2207
|
+
* ```
|
|
2208
|
+
*/
|
|
2209
|
+
interface Mutex<T> {
|
|
2210
|
+
/**
|
|
2211
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
2212
|
+
* Returns `'Mutex'` so that `Object.prototype.toString.call(mutex)` produces `'[object Mutex]'`.
|
|
2213
|
+
*
|
|
2214
|
+
* @internal
|
|
2215
|
+
*/
|
|
2216
|
+
readonly [Symbol.toStringTag]: 'Mutex';
|
|
2217
|
+
/**
|
|
2218
|
+
* Acquires the lock and executes the callback with the protected value.
|
|
2219
|
+
*
|
|
2220
|
+
* This is the recommended way to use the mutex as it automatically
|
|
2221
|
+
* releases the lock when the callback completes (or throws).
|
|
2222
|
+
*
|
|
2223
|
+
* @typeParam U - The return type of the callback.
|
|
2224
|
+
* @param fn - The callback that receives the protected value.
|
|
2225
|
+
* @returns A promise that resolves to the callback's return value.
|
|
2226
|
+
*
|
|
2227
|
+
* @example
|
|
2228
|
+
* ```ts
|
|
2229
|
+
* const mutex = Mutex<number[]>([]);
|
|
2230
|
+
*
|
|
2231
|
+
* await mutex.withLock(async (arr) => {
|
|
2232
|
+
* arr.push(await fetchItem());
|
|
2233
|
+
* });
|
|
2234
|
+
* ```
|
|
2235
|
+
*/
|
|
2236
|
+
withLock<U>(fn: (value: T) => Promise<U> | U): Promise<U>;
|
|
2237
|
+
/**
|
|
2238
|
+
* Acquires the lock and returns a guard for manual control.
|
|
2239
|
+
*
|
|
2240
|
+
* Use this when you need more control over when to release the lock.
|
|
2241
|
+
* **Important:** Always release the lock in a `finally` block to prevent deadlocks.
|
|
2242
|
+
*
|
|
2243
|
+
* @returns A promise that resolves to a guard providing access to the value.
|
|
2244
|
+
*
|
|
2245
|
+
* @example
|
|
2246
|
+
* ```ts
|
|
2247
|
+
* const guard = await mutex.lock();
|
|
2248
|
+
* try {
|
|
2249
|
+
* // Long-running operation with the protected value
|
|
2250
|
+
* await processData(guard.value);
|
|
2251
|
+
* guard.value = transformedData;
|
|
2252
|
+
* } finally {
|
|
2253
|
+
* guard.unlock();
|
|
2254
|
+
* }
|
|
2255
|
+
* ```
|
|
2256
|
+
*/
|
|
2257
|
+
lock(): Promise<MutexGuard<T>>;
|
|
2258
|
+
/**
|
|
2259
|
+
* Attempts to acquire the lock without waiting.
|
|
2260
|
+
*
|
|
2261
|
+
* Returns immediately with `Some(guard)` if the lock is available,
|
|
2262
|
+
* or `None` if it's currently held by another operation.
|
|
2263
|
+
*
|
|
2264
|
+
* @returns `Some(guard)` if acquired, `None` if locked.
|
|
2265
|
+
*
|
|
2266
|
+
* @example
|
|
2267
|
+
* ```ts
|
|
2268
|
+
* const maybeGuard = mutex.tryLock();
|
|
2269
|
+
* if (maybeGuard.isSome()) {
|
|
2270
|
+
* const guard = maybeGuard.unwrap();
|
|
2271
|
+
* try {
|
|
2272
|
+
* // Use the value
|
|
2273
|
+
* } finally {
|
|
2274
|
+
* guard.unlock();
|
|
2275
|
+
* }
|
|
2276
|
+
* } else {
|
|
2277
|
+
* console.log('Mutex is busy');
|
|
2278
|
+
* }
|
|
2279
|
+
* ```
|
|
2280
|
+
*/
|
|
2281
|
+
tryLock(): Option<MutexGuard<T>>;
|
|
2282
|
+
/**
|
|
2283
|
+
* Returns `true` if the mutex is currently locked.
|
|
2284
|
+
*
|
|
2285
|
+
* Note: This is a snapshot and may change immediately after the call.
|
|
2286
|
+
*
|
|
2287
|
+
* @example
|
|
2288
|
+
* ```ts
|
|
2289
|
+
* console.log(mutex.isLocked()); // false
|
|
2290
|
+
* const guard = await mutex.lock();
|
|
2291
|
+
* console.log(mutex.isLocked()); // true
|
|
2292
|
+
* guard.unlock();
|
|
2293
|
+
* console.log(mutex.isLocked()); // false
|
|
2294
|
+
* ```
|
|
2295
|
+
*/
|
|
2296
|
+
isLocked(): boolean;
|
|
2297
|
+
/**
|
|
2298
|
+
* Custom `toString` implementation.
|
|
2299
|
+
* @example
|
|
2300
|
+
* ```ts
|
|
2301
|
+
* const mutex = Mutex(42);
|
|
2302
|
+
* console.log(mutex.toString()); // 'Mutex(<unlocked>)'
|
|
2303
|
+
*
|
|
2304
|
+
* const guard = await mutex.lock();
|
|
2305
|
+
* console.log(mutex.toString()); // 'Mutex(<locked>)'
|
|
2306
|
+
* ```
|
|
2307
|
+
*/
|
|
2308
|
+
toString(): string;
|
|
2309
|
+
}
|
|
2310
|
+
/**
|
|
2311
|
+
* Creates a new `Mutex<T>` protecting the given value.
|
|
2312
|
+
*
|
|
2313
|
+
* @typeParam T - The type of the protected value.
|
|
2314
|
+
* @param value - The initial value to protect.
|
|
2315
|
+
* @returns A new `Mutex<T>` instance.
|
|
2316
|
+
*
|
|
2317
|
+
* @example
|
|
2318
|
+
* ```ts
|
|
2319
|
+
* // Protect a simple value
|
|
2320
|
+
* const counter = Mutex(0);
|
|
2321
|
+
*
|
|
2322
|
+
* // Protect an object
|
|
2323
|
+
* const state = Mutex({ users: [], lastUpdate: Date.now() });
|
|
2324
|
+
*
|
|
2325
|
+
* // Protect a resource
|
|
2326
|
+
* const db = Mutex(await createConnection());
|
|
2327
|
+
* ```
|
|
2328
|
+
*
|
|
2329
|
+
* @example
|
|
2330
|
+
* ```ts
|
|
2331
|
+
* // Database transaction safety
|
|
2332
|
+
* const connection = Mutex(db);
|
|
2333
|
+
*
|
|
2334
|
+
* async function transfer(from: string, to: string, amount: number) {
|
|
2335
|
+
* await connection.withLock(async (conn) => {
|
|
2336
|
+
* await conn.beginTransaction();
|
|
2337
|
+
* try {
|
|
2338
|
+
* const balance = await conn.query('SELECT balance FROM accounts WHERE id = ?', [from]);
|
|
2339
|
+
* if (balance < amount) {
|
|
2340
|
+
* throw new Error('Insufficient funds');
|
|
2341
|
+
* }
|
|
2342
|
+
* await conn.query('UPDATE accounts SET balance = balance - ? WHERE id = ?', [amount, from]);
|
|
2343
|
+
* await conn.query('UPDATE accounts SET balance = balance + ? WHERE id = ?', [amount, to]);
|
|
2344
|
+
* await conn.commit();
|
|
2345
|
+
* } catch (e) {
|
|
2346
|
+
* await conn.rollback();
|
|
2347
|
+
* throw e;
|
|
2348
|
+
* }
|
|
2349
|
+
* });
|
|
2350
|
+
* }
|
|
2351
|
+
* ```
|
|
2352
|
+
*
|
|
2353
|
+
* @example
|
|
2354
|
+
* ```ts
|
|
2355
|
+
* // Token refresh with mutex
|
|
2356
|
+
* const authState = Mutex({ token: '', expiresAt: 0 });
|
|
2357
|
+
*
|
|
2358
|
+
* async function getToken(): Promise<string> {
|
|
2359
|
+
* return await authState.withLock(async (state) => {
|
|
2360
|
+
* if (Date.now() > state.expiresAt) {
|
|
2361
|
+
* const response = await fetch('/api/refresh');
|
|
2362
|
+
* const data = await response.json();
|
|
2363
|
+
* state.token = data.token;
|
|
2364
|
+
* state.expiresAt = Date.now() + data.expiresIn * 1000;
|
|
2365
|
+
* }
|
|
2366
|
+
* return state.token;
|
|
2367
|
+
* });
|
|
2368
|
+
* }
|
|
2369
|
+
* ```
|
|
2370
|
+
*
|
|
2371
|
+
* @example
|
|
2372
|
+
* ```ts
|
|
2373
|
+
* // File write serialization
|
|
2374
|
+
* const fileLock = Mutex('/path/to/file.json');
|
|
2375
|
+
*
|
|
2376
|
+
* async function appendToFile(data: string) {
|
|
2377
|
+
* await fileLock.withLock(async (path) => {
|
|
2378
|
+
* const content = await fs.readFile(path, 'utf-8');
|
|
2379
|
+
* const json = JSON.parse(content);
|
|
2380
|
+
* json.entries.push(data);
|
|
2381
|
+
* await fs.writeFile(path, JSON.stringify(json, null, 2));
|
|
2382
|
+
* });
|
|
2383
|
+
* }
|
|
2384
|
+
* ```
|
|
2385
|
+
*/
|
|
2386
|
+
declare function Mutex<T>(value: T): Mutex<T>;
|
|
2387
|
+
|
|
2388
|
+
/**
|
|
2389
|
+
* @fileoverview
|
|
2390
|
+
* Rust-inspired [OnceLock](https://doc.rust-lang.org/std/sync/struct.OnceLock.html) for one-time initialization.
|
|
2391
|
+
*
|
|
2392
|
+
* `Once<T>` is a container which can be written to only once. It provides safe access
|
|
2393
|
+
* to lazily initialized data, supporting both sync and async initialization.
|
|
2394
|
+
*/
|
|
2395
|
+
|
|
2396
|
+
/**
|
|
2397
|
+
* A container which can be written to only once.
|
|
2398
|
+
*
|
|
2399
|
+
* This is useful for lazy initialization of global data or expensive computations
|
|
2400
|
+
* that should only happen once. Supports both synchronous and asynchronous
|
|
2401
|
+
* initialization functions via separate methods.
|
|
2402
|
+
*
|
|
2403
|
+
* @typeParam T - The type of the value stored.
|
|
2404
|
+
*
|
|
2405
|
+
* @example
|
|
2406
|
+
* ```ts
|
|
2407
|
+
* const once = Once<number>();
|
|
2408
|
+
*
|
|
2409
|
+
* // Set value (only works once)
|
|
2410
|
+
* once.set(42); // Ok(undefined)
|
|
2411
|
+
* once.set(100); // Err(100) - already set
|
|
2412
|
+
*
|
|
2413
|
+
* // Get value
|
|
2414
|
+
* console.log(once.get()); // Some(42)
|
|
2415
|
+
* ```
|
|
2416
|
+
*
|
|
2417
|
+
* @example
|
|
2418
|
+
* ```ts
|
|
2419
|
+
* // Sync lazy initialization
|
|
2420
|
+
* const config = Once<Config>();
|
|
2421
|
+
* const cfg = config.getOrInit(() => loadConfigFromFile());
|
|
2422
|
+
* ```
|
|
2423
|
+
*
|
|
2424
|
+
* @example
|
|
2425
|
+
* ```ts
|
|
2426
|
+
* // Async lazy initialization
|
|
2427
|
+
* const db = Once<Database>();
|
|
2428
|
+
* const conn = await db.getOrInitAsync(async () => Database.connect(url));
|
|
2429
|
+
* ```
|
|
2430
|
+
*/
|
|
2431
|
+
interface Once<T> {
|
|
2432
|
+
/**
|
|
2433
|
+
* The well-known symbol `Symbol.toStringTag` used by `Object.prototype.toString()`.
|
|
2434
|
+
* Returns `'Once'` so that `Object.prototype.toString.call(once)` produces `'[object Once]'`.
|
|
2435
|
+
*
|
|
2436
|
+
* @internal
|
|
2437
|
+
*/
|
|
2438
|
+
readonly [Symbol.toStringTag]: 'Once';
|
|
2439
|
+
/**
|
|
2440
|
+
* Gets the reference to the underlying value.
|
|
2441
|
+
*
|
|
2442
|
+
* @returns `Some(value)` if initialized, `None` otherwise.
|
|
2443
|
+
*
|
|
2444
|
+
* @example
|
|
2445
|
+
* ```ts
|
|
2446
|
+
* const once = Once<number>();
|
|
2447
|
+
* console.log(once.get()); // None
|
|
2448
|
+
*
|
|
2449
|
+
* once.set(42);
|
|
2450
|
+
* console.log(once.get()); // Some(42)
|
|
2451
|
+
* ```
|
|
2452
|
+
*/
|
|
2453
|
+
get(): Option<T>;
|
|
2454
|
+
/**
|
|
2455
|
+
* Sets the contents to `value`.
|
|
2456
|
+
*
|
|
2457
|
+
* @param value - The value to store.
|
|
2458
|
+
* @returns `Ok(undefined)` if empty, `Err(value)` if already initialized.
|
|
2459
|
+
*
|
|
2460
|
+
* @example
|
|
2461
|
+
* ```ts
|
|
2462
|
+
* const once = Once<number>();
|
|
2463
|
+
*
|
|
2464
|
+
* console.log(once.set(42)); // Ok(undefined)
|
|
2465
|
+
* console.log(once.set(100)); // Err(100) - value returned back
|
|
2466
|
+
* console.log(once.get()); // Some(42)
|
|
2467
|
+
* ```
|
|
2468
|
+
*/
|
|
2469
|
+
set(value: T): Result<void, T>;
|
|
2470
|
+
/**
|
|
2471
|
+
* Gets the contents, initializing it with `fn` if empty.
|
|
2472
|
+
*
|
|
2473
|
+
* @param fn - The synchronous initialization function, called only if empty.
|
|
2474
|
+
* @returns The stored value.
|
|
2475
|
+
*
|
|
2476
|
+
* @example
|
|
2477
|
+
* ```ts
|
|
2478
|
+
* const once = Once<number>();
|
|
2479
|
+
*
|
|
2480
|
+
* const value = once.getOrInit(() => {
|
|
2481
|
+
* console.log('Initializing...');
|
|
2482
|
+
* return 42;
|
|
2483
|
+
* });
|
|
2484
|
+
* console.log(value); // 42
|
|
2485
|
+
*
|
|
2486
|
+
* // Second call - fn is not called
|
|
2487
|
+
* const value2 = once.getOrInit(() => 100);
|
|
2488
|
+
* console.log(value2); // 42
|
|
2489
|
+
* ```
|
|
2490
|
+
*/
|
|
2491
|
+
getOrInit(fn: () => T): T;
|
|
2492
|
+
/**
|
|
2493
|
+
* Gets the contents, initializing it with async `fn` if empty.
|
|
2494
|
+
*
|
|
2495
|
+
* If multiple calls occur concurrently, only the first one will run the
|
|
2496
|
+
* initialization function. Other calls will wait for it to complete.
|
|
2497
|
+
*
|
|
2498
|
+
* @param fn - The async initialization function.
|
|
2499
|
+
* @returns A promise that resolves to the stored value.
|
|
2500
|
+
*
|
|
2501
|
+
* @example
|
|
2502
|
+
* ```ts
|
|
2503
|
+
* const db = Once<Database>();
|
|
2504
|
+
*
|
|
2505
|
+
* // Multiple concurrent calls - only one connection happens
|
|
2506
|
+
* const [db1, db2, db3] = await Promise.all([
|
|
2507
|
+
* db.getOrInitAsync(() => Database.connect(url)),
|
|
2508
|
+
* db.getOrInitAsync(() => Database.connect(url)),
|
|
2509
|
+
* db.getOrInitAsync(() => Database.connect(url)),
|
|
2510
|
+
* ]);
|
|
2511
|
+
* // db1 === db2 === db3
|
|
2512
|
+
* ```
|
|
2513
|
+
*/
|
|
2514
|
+
getOrInitAsync(fn: () => Promise<T>): Promise<T>;
|
|
2515
|
+
/**
|
|
2516
|
+
* Gets the contents, initializing it with `fn` if empty.
|
|
2517
|
+
* If `fn` returns `Err`, remains uninitialized.
|
|
2518
|
+
*
|
|
2519
|
+
* @typeParam E - The error type.
|
|
2520
|
+
* @param fn - The initialization function that may fail.
|
|
2521
|
+
* @returns `Ok(value)` if initialized, `Err(error)` if initialization failed.
|
|
2522
|
+
*
|
|
2523
|
+
* @example
|
|
2524
|
+
* ```ts
|
|
2525
|
+
* const once = Once<Config>();
|
|
2526
|
+
*
|
|
2527
|
+
* const result = once.getOrTryInit(() => {
|
|
2528
|
+
* const config = parseConfig(rawData);
|
|
2529
|
+
* return config ? Ok(config) : Err(new Error('Invalid config'));
|
|
2530
|
+
* });
|
|
2531
|
+
*
|
|
2532
|
+
* if (result.isOk()) {
|
|
2533
|
+
* console.log('Config loaded:', result.unwrap());
|
|
2534
|
+
* }
|
|
2535
|
+
* ```
|
|
2536
|
+
*/
|
|
2537
|
+
getOrTryInit<E>(fn: () => Result<T, E>): Result<T, E>;
|
|
2538
|
+
/**
|
|
2539
|
+
* Gets the contents, initializing it with async `fn` if empty.
|
|
2540
|
+
* If `fn` returns `Err`, remains uninitialized.
|
|
2541
|
+
*
|
|
2542
|
+
* If multiple calls occur concurrently, only the first one will run the
|
|
2543
|
+
* initialization function. Other calls will wait for it to complete.
|
|
2544
|
+
*
|
|
2545
|
+
* @typeParam E - The error type.
|
|
2546
|
+
* @param fn - The async initialization function that may fail.
|
|
2547
|
+
* @returns A promise that resolves to `Ok(value)` or `Err(error)`.
|
|
2548
|
+
*
|
|
2549
|
+
* @example
|
|
2550
|
+
* ```ts
|
|
2551
|
+
* const config = Once<Config>();
|
|
2552
|
+
*
|
|
2553
|
+
* const result = await config.getOrTryInitAsync(async () => {
|
|
2554
|
+
* try {
|
|
2555
|
+
* const response = await fetch('/api/config');
|
|
2556
|
+
* return Ok(await response.json());
|
|
2557
|
+
* } catch (e) {
|
|
2558
|
+
* return Err(e as Error);
|
|
2559
|
+
* }
|
|
2560
|
+
* });
|
|
2561
|
+
* ```
|
|
2562
|
+
*/
|
|
2563
|
+
getOrTryInitAsync<E>(fn: () => Promise<Result<T, E>>): Promise<Result<T, E>>;
|
|
2564
|
+
/**
|
|
2565
|
+
* Takes the value out, leaving it uninitialized.
|
|
2566
|
+
*
|
|
2567
|
+
* @returns `Some(value)` if initialized, `None` otherwise.
|
|
2568
|
+
*
|
|
2569
|
+
* @example
|
|
2570
|
+
* ```ts
|
|
2571
|
+
* const once = Once<number>();
|
|
2572
|
+
* once.set(42);
|
|
2573
|
+
*
|
|
2574
|
+
* console.log(once.take()); // Some(42)
|
|
2575
|
+
* console.log(once.get()); // None - now empty
|
|
2576
|
+
* console.log(once.take()); // None
|
|
2577
|
+
* ```
|
|
2578
|
+
*/
|
|
2579
|
+
take(): Option<T>;
|
|
2580
|
+
/**
|
|
2581
|
+
* Returns `true` if initialized.
|
|
2582
|
+
*
|
|
2583
|
+
* @example
|
|
2584
|
+
* ```ts
|
|
2585
|
+
* const once = Once<number>();
|
|
2586
|
+
* console.log(once.isInitialized()); // false
|
|
2587
|
+
*
|
|
2588
|
+
* once.set(42);
|
|
2589
|
+
* console.log(once.isInitialized()); // true
|
|
2590
|
+
* ```
|
|
2591
|
+
*/
|
|
2592
|
+
isInitialized(): boolean;
|
|
2593
|
+
/**
|
|
2594
|
+
* Custom `toString` implementation.
|
|
2595
|
+
* @example
|
|
2596
|
+
* ```ts
|
|
2597
|
+
* const once = Once<number>();
|
|
2598
|
+
* console.log(once.toString()); // 'Once(<uninitialized>)'
|
|
2599
|
+
*
|
|
2600
|
+
* once.set(42);
|
|
2601
|
+
* console.log(once.toString()); // 'Once(42)'
|
|
2602
|
+
* ```
|
|
2603
|
+
*/
|
|
2604
|
+
toString(): string;
|
|
2605
|
+
}
|
|
2606
|
+
/**
|
|
2607
|
+
* Creates a new empty `Once<T>`.
|
|
2608
|
+
*
|
|
2609
|
+
* @typeParam T - The type of value to store.
|
|
2610
|
+
* @returns A new uninitialized `Once`.
|
|
2611
|
+
*
|
|
2612
|
+
* @example
|
|
2613
|
+
* ```ts
|
|
2614
|
+
* // Basic usage
|
|
2615
|
+
* const once = Once<string>();
|
|
2616
|
+
* once.set('hello');
|
|
2617
|
+
* console.log(once.get().unwrap()); // 'hello'
|
|
2618
|
+
* ```
|
|
2619
|
+
*
|
|
2620
|
+
* @example
|
|
2621
|
+
* ```ts
|
|
2622
|
+
* // Sync lazy singleton pattern
|
|
2623
|
+
* const logger = Once<Logger>();
|
|
2624
|
+
*
|
|
2625
|
+
* function getLogger(): Logger {
|
|
2626
|
+
* return logger.getOrInit(() => new Logger('app'));
|
|
2627
|
+
* }
|
|
2628
|
+
* ```
|
|
2629
|
+
*
|
|
2630
|
+
* @example
|
|
2631
|
+
* ```ts
|
|
2632
|
+
* // Async lazy initialization
|
|
2633
|
+
* const db = Once<Database>();
|
|
2634
|
+
*
|
|
2635
|
+
* async function getDb(): Promise<Database> {
|
|
2636
|
+
* return await db.getOrInitAsync(async () => {
|
|
2637
|
+
* console.log('Connecting to database...');
|
|
2638
|
+
* return await Database.connect(connectionString);
|
|
2639
|
+
* });
|
|
2640
|
+
* }
|
|
2641
|
+
*
|
|
2642
|
+
* // Multiple calls - connection happens only once
|
|
2643
|
+
* const [db1, db2] = await Promise.all([getDb(), getDb()]);
|
|
2644
|
+
* console.log(db1 === db2); // true
|
|
2645
|
+
* ```
|
|
2646
|
+
*
|
|
2647
|
+
* @example
|
|
2648
|
+
* ```ts
|
|
2649
|
+
* // Fallible async initialization
|
|
2650
|
+
* const config = Once<Config>();
|
|
2651
|
+
*
|
|
2652
|
+
* async function loadConfig(): Promise<Result<Config, Error>> {
|
|
2653
|
+
* return await config.getOrTryInitAsync(async () => {
|
|
2654
|
+
* try {
|
|
2655
|
+
* const response = await fetch('/api/config');
|
|
2656
|
+
* if (!response.ok) {
|
|
2657
|
+
* return Err(new Error(`HTTP ${response.status}`));
|
|
2658
|
+
* }
|
|
2659
|
+
* return Ok(await response.json());
|
|
2660
|
+
* } catch (e) {
|
|
2661
|
+
* return Err(e as Error);
|
|
2662
|
+
* }
|
|
2663
|
+
* });
|
|
2664
|
+
* }
|
|
2665
|
+
* ```
|
|
2666
|
+
*/
|
|
2667
|
+
declare function Once<T>(): Once<T>;
|
|
2668
|
+
|
|
2669
|
+
export { Break, Continue, Err, Lazy, LazyAsync, Mutex, None, Ok, Once, RESULT_FALSE, RESULT_TRUE, RESULT_VOID, RESULT_ZERO, Some, isControlFlow, isOption, isResult, promiseToAsyncResult };
|
|
2670
|
+
export type { AsyncIOResult, AsyncOption, AsyncResult, AsyncVoidIOResult, AsyncVoidResult, ControlFlow, IOResult, MutexGuard, Option, Result, VoidIOResult, VoidResult };
|