Skip to content

Commit

Permalink
improve-async-detection
Browse files Browse the repository at this point in the history
  • Loading branch information
uriva committed Jan 7, 2025
1 parent 9d585a1 commit 1bed975
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 4 deletions.
15 changes: 13 additions & 2 deletions src/composition.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -87,11 +87,22 @@ const _1 = <T, Fn extends (x: T) => number>(f: Fn) => {
pipe((x: T) => x, f);
};

// Generics does not make everything async.
const _2: number = pipe(<T extends number>(x: T) => x, (y: number) => y)(1);

// Generics extends Promise is considered async.
const _3: number = await pipe(
<T extends number>(x: T) => Promise.resolve(x),
(y: number) => y,
)(1);

// failing typing tests:

// const _2 = pipe(<T extends number>(x: T) => x, (y: number) => y)(1) + 7;
// Generics can infer by the last function
// const _4: number = pipe((y: number) => y, <T >(x: T) => x)(1);

// const _3 = <Fn extends (x: string) => number>(f: Fn) => {
// Generics understands contextual extends
// const _5 = <Fn extends (x: string) => number>(f: Fn) => {
// // @ts-expect-error first function does not match second
// pipe((x: number) => x, f);
// };
Expand Down
10 changes: 8 additions & 2 deletions src/typing.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,15 @@ export type Union<T extends any[]> = T[number];
// deno-lint-ignore no-explicit-any
export type AsyncFunction = (...args: any[]) => Promise<any>;

export type AnyAsync<Functions> = Functions extends [infer f, ...infer rest]
export type AnyAsync<Functions> = Functions extends [infer F, ...infer Rest]
// deno-lint-ignore no-explicit-any
? f extends AsyncFunction ? any : AnyAsync<rest>
? F extends (...args: any[]) => infer R // Extract return type
// deno-lint-ignore no-explicit-any
? R extends Promise<any> // Check if it returns a Promise
// deno-lint-ignore no-explicit-any
? any
: AnyAsync<Rest>
: AnyAsync<Rest>
: never;

export type Unary<Input, Output> = (_: Input) => Output;
Expand Down

0 comments on commit 1bed975

Please sign in to comment.