From f4a91ce1785d64ba0c814dc016381d73d5df62ec Mon Sep 17 00:00:00 2001 From: braxtonhall Date: Tue, 27 Jun 2023 12:38:13 +0200 Subject: [PATCH 1/4] Fix combineWithAllErrors types --- src/result-async.ts | 21 +++++------------- src/result.ts | 8 +++---- tests/typecheck-tests.ts | 48 ++++++++++++++++++++++++++++------------ 3 files changed, 44 insertions(+), 33 deletions(-) diff --git a/src/result-async.ts b/src/result-async.ts index 87285455..be685d05 100644 --- a/src/result-async.ts +++ b/src/result-async.ts @@ -219,22 +219,13 @@ type TraverseAsync = IsLiteralArray extends 1 : never // This type is similar to the `TraverseAsync` while the errors are also -// collected in order. For the checks/conditions made here, see that type +// collected in a list. For the checks/conditions made here, see that type // for the documentation. -type TraverseWithAllErrorsAsync = IsLiteralArray extends 1 - ? Combine extends [infer Oks, infer Errs] - ? ResultAsync, EmptyArrayToNever> - : never - : Writable extends Array - ? Combine, Depth> extends [infer Oks, infer Errs] - ? Oks extends unknown[] - ? Errs extends unknown[] - ? ResultAsync, EmptyArrayToNever> - : ResultAsync, Errs> - : Errs extends unknown[] - ? ResultAsync> - : ResultAsync - : never +type TraverseWithAllErrorsAsync = TraverseAsync< + T, + Depth +> extends ResultAsync + ? ResultAsync : never // Converts a reaodnly array into a writable array diff --git a/src/result.ts b/src/result.ts index c8f09971..8602fc24 100644 --- a/src/result.ts +++ b/src/result.ts @@ -497,11 +497,11 @@ type Traverse = Combine extends [infer Ok // Traverses an array of results and returns a single result containing // the oks combined and the array of errors combined. -type TraverseWithAllErrors = Combine extends [ +type TraverseWithAllErrors = Traverse extends Result< infer Oks, - infer Errs, -] - ? Result, EmptyArrayToNever> + infer Errs +> + ? Result : never // Combines the array of results into one result. diff --git a/tests/typecheck-tests.ts b/tests/typecheck-tests.ts index 849b2247..a38a90e4 100644 --- a/tests/typecheck-tests.ts +++ b/tests/typecheck-tests.ts @@ -854,7 +854,7 @@ type CreateTuple = (function describe(_ = 'combineWithAllErrors') { (function it(_ = 'combines different results into one') { - type Expectation = Result<[ number, string, never, never ], [never, never, string[], Error]>; + type Expectation = Result<[ number, string, never, never ], [string[] | Error, ...(string[] | Error)[]]>; const result = Result.combineWithAllErrors([ ok(1), @@ -868,7 +868,7 @@ type CreateTuple = }); (function it(_ = 'combines only ok results into one') { - type Expectation = Result<[ number, string ], [never, never]>; + type Expectation = Result<[ number, string ], never>; const result = Result.combineWithAllErrors([ ok(1), @@ -880,7 +880,7 @@ type CreateTuple = }); (function it(_ = 'combines only err results into one') { - type Expectation = Result<[ never, never ], [number, string]>; + type Expectation = Result<[ never, never ], [number | string, ...(number | string)[]]>; const result = Result.combineWithAllErrors([ err(1), @@ -901,10 +901,20 @@ type CreateTuple = const assignablefromCheck: typeof result = assignableToCheck; }); + (function it(_ = 'combines arrays of different results to a result of an array') { + type Expectation = Result<(string | boolean)[], (number | string)[]>; + const results: (Result | Result)[] = []; + + const result = Result.combineWithAllErrors(results); + + const assignableToCheck: Expectation = result; + const assignablefromCheck: typeof result = assignableToCheck; + }); + (function describe(_ = 'inference on large tuples') { (function it(_ = 'Should correctly infer the type on tuples with 6 elements') { type Input = CreateTuple<6, Result> - type Expectation = Result, CreateTuple<6, number>> + type Expectation = Result, [number, ...number[]]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -916,7 +926,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 15 elements') { type Input = CreateTuple<15, Result> - type Expectation = Result, CreateTuple<15, number>> + type Expectation = Result, [number, ...number[]]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -928,7 +938,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 30 elements') { type Input = CreateTuple<30, Result> - type Expectation = Result, CreateTuple<30, number>> + type Expectation = Result, [number, ...number[]]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -940,7 +950,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 49 elements') { type Input = CreateTuple<49 , Result> - type Expectation = Result, CreateTuple<49, number>> + type Expectation = Result, [number, ...number[]]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -1858,7 +1868,7 @@ type CreateTuple = (function describe(_ = 'combineWithAllErrors') { (function it(_ = 'combines different result asyncs into one') { - type Expectation = ResultAsync<[ number, string, never, never ], [never, never, string[], Error]>; + type Expectation = ResultAsync<[ number, string, never, never ], [string[] | Error, ...(string[] | Error)[]]>; const result = ResultAsync.combineWithAllErrors([ okAsync(1), @@ -1872,7 +1882,7 @@ type CreateTuple = }); (function it(_ = 'combines only ok result asyncs into one') { - type Expectation = ResultAsync<[ number, string ], [never, never]>; + type Expectation = ResultAsync<[ number, string ], never>; const result = ResultAsync.combineWithAllErrors([ okAsync(1), @@ -1884,7 +1894,7 @@ type CreateTuple = }); (function it(_ = 'combines only err result asyncs into one') { - type Expectation = ResultAsync<[ never, never ], [number, string]>; + type Expectation = ResultAsync<[ never, never ], [number | string, ...(number | string)[]]>; const result = ResultAsync.combineWithAllErrors([ errAsync(1), @@ -1905,10 +1915,20 @@ type CreateTuple = const assignablefromCheck: typeof result = assignableToCheck; }); + (function it(_ = 'combines arrays of different result asyncs to a result of an array') { + type Expectation = ResultAsync<(string | boolean)[], (number | string)[]>; + const results: (ResultAsync | ResultAsync)[] = []; + + const result = ResultAsync.combineWithAllErrors(results); + + const assignableToCheck: Expectation = result; + const assignablefromCheck: typeof result = assignableToCheck; + }); + (function describe(_ = 'inference on large tuples') { (function it(_ = 'Should correctly infer the type on tuples with 6 elements') { type Input = CreateTuple<6, ResultAsync> - type Expectation = ResultAsync, CreateTuple<6, number>> + type Expectation = ResultAsync, [number, ...number[]]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) @@ -1920,7 +1940,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 15 elements') { type Input = CreateTuple<15, ResultAsync> - type Expectation = ResultAsync, CreateTuple<15, number>> + type Expectation = ResultAsync, [number, ...number[]]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) @@ -1932,7 +1952,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 30 elements') { type Input = CreateTuple<30, ResultAsync> - type Expectation = ResultAsync, CreateTuple<30, number>> + type Expectation = ResultAsync, [number, ...number[]]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) @@ -1944,7 +1964,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 49 elements') { type Input = CreateTuple<49 , ResultAsync> - type Expectation = ResultAsync, CreateTuple<49, number>> + type Expectation = ResultAsync, [number, ...number[]]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) From fa4bbb1b908cb256caaca630d5ee2ad0602fb538 Mon Sep 17 00:00:00 2001 From: braxtonhall Date: Tue, 27 Jun 2023 12:51:29 +0200 Subject: [PATCH 2/4] Remove non-empty type guarantee just to simplify --- src/result-async.ts | 2 +- src/result.ts | 2 +- tests/typecheck-tests.ts | 28 ++++++++++++++-------------- 3 files changed, 16 insertions(+), 16 deletions(-) diff --git a/src/result-async.ts b/src/result-async.ts index be685d05..904b8e36 100644 --- a/src/result-async.ts +++ b/src/result-async.ts @@ -225,7 +225,7 @@ type TraverseWithAllErrorsAsync = TraverseAsync< T, Depth > extends ResultAsync - ? ResultAsync + ? ResultAsync : never // Converts a reaodnly array into a writable array diff --git a/src/result.ts b/src/result.ts index 8602fc24..c5770bd3 100644 --- a/src/result.ts +++ b/src/result.ts @@ -501,7 +501,7 @@ type TraverseWithAllErrors = Traverse ext infer Oks, infer Errs > - ? Result + ? Result : never // Combines the array of results into one result. diff --git a/tests/typecheck-tests.ts b/tests/typecheck-tests.ts index a38a90e4..5116fc62 100644 --- a/tests/typecheck-tests.ts +++ b/tests/typecheck-tests.ts @@ -854,7 +854,7 @@ type CreateTuple = (function describe(_ = 'combineWithAllErrors') { (function it(_ = 'combines different results into one') { - type Expectation = Result<[ number, string, never, never ], [string[] | Error, ...(string[] | Error)[]]>; + type Expectation = Result<[ number, string, never, never ], (string[] | Error)[]>; const result = Result.combineWithAllErrors([ ok(1), @@ -868,7 +868,7 @@ type CreateTuple = }); (function it(_ = 'combines only ok results into one') { - type Expectation = Result<[ number, string ], never>; + type Expectation = Result<[ number, string ], never[]>; const result = Result.combineWithAllErrors([ ok(1), @@ -880,7 +880,7 @@ type CreateTuple = }); (function it(_ = 'combines only err results into one') { - type Expectation = Result<[ never, never ], [number | string, ...(number | string)[]]>; + type Expectation = Result<[ never, never ], (number | string)[]>; const result = Result.combineWithAllErrors([ err(1), @@ -914,7 +914,7 @@ type CreateTuple = (function describe(_ = 'inference on large tuples') { (function it(_ = 'Should correctly infer the type on tuples with 6 elements') { type Input = CreateTuple<6, Result> - type Expectation = Result, [number, ...number[]]> + type Expectation = Result, number[]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -926,7 +926,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 15 elements') { type Input = CreateTuple<15, Result> - type Expectation = Result, [number, ...number[]]> + type Expectation = Result, number[]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -938,7 +938,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 30 elements') { type Input = CreateTuple<30, Result> - type Expectation = Result, [number, ...number[]]> + type Expectation = Result, number[]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -950,7 +950,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 49 elements') { type Input = CreateTuple<49 , Result> - type Expectation = Result, [number, ...number[]]> + type Expectation = Result, number[]> const inputValues = input() const result = Result.combineWithAllErrors(inputValues) @@ -1868,7 +1868,7 @@ type CreateTuple = (function describe(_ = 'combineWithAllErrors') { (function it(_ = 'combines different result asyncs into one') { - type Expectation = ResultAsync<[ number, string, never, never ], [string[] | Error, ...(string[] | Error)[]]>; + type Expectation = ResultAsync<[ number, string, never, never ], (string[] | Error)[]>; const result = ResultAsync.combineWithAllErrors([ okAsync(1), @@ -1882,7 +1882,7 @@ type CreateTuple = }); (function it(_ = 'combines only ok result asyncs into one') { - type Expectation = ResultAsync<[ number, string ], never>; + type Expectation = ResultAsync<[ number, string ], never[]>; const result = ResultAsync.combineWithAllErrors([ okAsync(1), @@ -1894,7 +1894,7 @@ type CreateTuple = }); (function it(_ = 'combines only err result asyncs into one') { - type Expectation = ResultAsync<[ never, never ], [number | string, ...(number | string)[]]>; + type Expectation = ResultAsync<[ never, never ], (number | string)[]>; const result = ResultAsync.combineWithAllErrors([ errAsync(1), @@ -1928,7 +1928,7 @@ type CreateTuple = (function describe(_ = 'inference on large tuples') { (function it(_ = 'Should correctly infer the type on tuples with 6 elements') { type Input = CreateTuple<6, ResultAsync> - type Expectation = ResultAsync, [number, ...number[]]> + type Expectation = ResultAsync, number[]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) @@ -1940,7 +1940,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 15 elements') { type Input = CreateTuple<15, ResultAsync> - type Expectation = ResultAsync, [number, ...number[]]> + type Expectation = ResultAsync, number[]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) @@ -1952,7 +1952,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 30 elements') { type Input = CreateTuple<30, ResultAsync> - type Expectation = ResultAsync, [number, ...number[]]> + type Expectation = ResultAsync, number[]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) @@ -1964,7 +1964,7 @@ type CreateTuple = (function it(_ = 'Should correctly infer the type on tuples with 49 elements') { type Input = CreateTuple<49 , ResultAsync> - type Expectation = ResultAsync, [number, ...number[]]> + type Expectation = ResultAsync, number[]> const inputValues = input() const result = ResultAsync.combineWithAllErrors(inputValues) From aeb3cdf6c8b043bfdca63ab159464e0a0d082920 Mon Sep 17 00:00:00 2001 From: braxtonhall Date: Tue, 27 Jun 2023 13:06:41 +0200 Subject: [PATCH 3/4] Fix the tests --- tests/index.test.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/index.test.ts b/tests/index.test.ts index 7d2d056e..332d7bc1 100644 --- a/tests/index.test.ts +++ b/tests/index.test.ts @@ -583,7 +583,7 @@ describe('Utils', () => { okAsync(true), ] - type ExpecteResult = Result<[ string, number, boolean ], [string, number, boolean]> + type ExpecteResult = Result<[ string, number, boolean ], (string | number | boolean)[]> const result: ExpecteResult = await ResultAsync.combineWithAllErrors(heterogenousList) From 96f7f669ac83be705a389d47ed804e9d44a13932 Mon Sep 17 00:00:00 2001 From: m-shaka Date: Wed, 21 Aug 2024 10:29:48 +0900 Subject: [PATCH 4/4] Create thirty-grapes-drum.md --- .changeset/thirty-grapes-drum.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/thirty-grapes-drum.md diff --git a/.changeset/thirty-grapes-drum.md b/.changeset/thirty-grapes-drum.md new file mode 100644 index 00000000..10867d68 --- /dev/null +++ b/.changeset/thirty-grapes-drum.md @@ -0,0 +1,5 @@ +--- +"neverthrow": patch +--- + +Fix `combineWithAllErrors` types