如何在打字稿中使用 promise.allSettled?

Str*_*ch0 4 javascript node.js promise typescript

打字稿构建失败,因为它似乎不喜欢Promise.allSetttled即使我已经设置了 ts config comilerOptions"lib": [ "ES2020.Promise" ],

似乎对 的响应promise.allSettled不包括resultreason

运行 typescript build 时出现以下错误:

Property 'reason' does not exist on type 'PromiseSettledResult<IMyPromiseResult>'.
Run Code Online (Sandbox Code Playgroud)

Property 'value' does not exist on type 'PromiseRejectedResult'.
Run Code Online (Sandbox Code Playgroud)

我的代码块看起来像这样,正如您所看到的,我正在尝试访问reasonresult从中获取已解决的承诺。

const myPromise = async () : Promise<IMyPromiseResult> {
  return new Promise((resolve) => {
    resolve("hello world")
  })
}

const data = await Promise.allSettled([
  myPromise()
]);

const response = data.find(res => res.status === 'fulfilled')?.result;

if(!response) {
  const error = data.find(res => res.status === 'rejected')?.reason;
  throw new Error(error);
}
Run Code Online (Sandbox Code Playgroud)

如何更新 Promise.allSettled 声明以包含正确的接口?

ves*_*sse 44

就像bela53所说的那样,使用类型保护。比内联类型保护更优雅的解决方案是将它们定义为单独的函数,并且通过泛型绑定,您也可以获得已实现的承诺的正确值,并且可以重用以满足任何allSettled过滤需求。

不需要铸造(通常应该避免)。

const isRejected = (input: PromiseSettledResult<unknown>): input is PromiseRejectedResult => 
  input.status === 'rejected'

const isFulfilled = <T>(input: PromiseSettledResult<T>): input is PromiseFulfilledResult<T> => 
  input.status === 'fulfilled'

const myPromise = async () => Promise.resolve("hello world");

const data = await Promise.allSettled([myPromise()]);

const response = data.find(isFulfilled)?.value
const error = data.find(isRejected)?.reason
Run Code Online (Sandbox Code Playgroud)


sar*_*ink 24

使用类型保护:

const isFulfilled = <T,>(p:PromiseSettledResult<T>): p is PromiseFulfilledResult<T> => p.status === 'fulfilled';
const isRejected = <T,>(p:PromiseSettledResult<T>): p is PromiseRejectedResult => p.status === 'rejected';

const results = await Promise.allSettled(...);
const fulfilledValues = results.filter(isFulfilled).map(p => p.value);
const rejectedReasons = results.filter(isRejected).map(p => p.reason);
Run Code Online (Sandbox Code Playgroud)


Jen*_*ens 7

就像 Bergi 提到的,TypeScript在检查类型时不知道类型是否为PromiseFulfilledResult/ PromiseRejectedResult

唯一的方法是投射承诺结果。之所以可以这样做,是因为您已经验证了已解决的承诺是否已完成或已被拒绝。

看这个例子:

const myPromise = async (): Promise<string> => {
  return new Promise((resolve) => {
    resolve("hello world");
  });
};

const data = await Promise.allSettled([myPromise()]);

const response = (data.find(
  (res) => res.status === "fulfilled"
) as PromiseFulfilledResult<string> | undefined)?.value;

if (!response) {
  const error = (data.find(
    (res) => res.status === "rejected"
  ) as PromiseRejectedResult | undefined)?.reason;
  throw new Error(error);
}
Run Code Online (Sandbox Code Playgroud)

  • 投射不是**唯一的方法,请不要投射,而是检查其他答案。 (3认同)
  • 应该是`| 尽管“find”可能不会返回结果,但未定义。 (2认同)