首页 > 解决方案 > 如何实现将任何函数类型的返回类型转换为承诺的实用程序类型?

问题描述

我想编写一个实用程序类型,它能够将任何函数类型(包括泛型函数)转换为Promise作为返回类型。

我的想法是这样的:

type Promisify<T extends (...args: any) => any> = T extends (...args: infer A) => infer R
  ? (...args: A) => Promise<R>
  : never;

不幸的是,这不适用于泛型:

type Bar<T> = () => T extends string ? number: string

// ERROR: Generic type 'Bar' requires 1 type argument(s).
type PromisifyBar = Promisify<Bar>

在我的实际情况中,我想转换在接口(第 3 方库的)中声明的函数类型,并只更改返回类型:

interface Foo {
   baz<T extends { a?: string, b?: string}>(arg: T): T extends {a: string} ? string : number;
}

type Baz = Foo["baz"]
type PromisifiedBaz = Promisify<Foo["baz"]>

// Only type is relevant so skip implementaion
const baz: Baz = undefined as any;
const promisifiedBaz: PromisifiedBaz = undefined as any;

// CORRECT
const shouldBeNumber = baz({b: "b"});
// CORRECT
const shouldBeString = baz({a: "a", b: "b"});

// CORRECT
const shouldBePromiseNumber = promisifiedBaz({b: "b"});
// WRONG: it's of type Promise<number>
const shouldBePromiseString = promisifiedBaz({a: "a", b: "b"});

操场

正如你所看到的,它在最后一个工作期望shouldBePromiseString。我猜想类型推断存在问题(参见 参考资料infer APromisify,这就是错误推断返回类型的原因。

如何创建这样的实用程序类型?甚至可能吗?有替代品吗?有Promisify比我的建议更好的实现吗?

标签: typescripttypestypescript-typingstypescript-generics

解决方案


推荐阅读