如何在异步捕获中使用类型化错误()

如何在异步捕获中使用类型化错误()

问题描述:

我正在使用async函数调用现有的基于承诺的API,该API拒绝承诺带有类型错误的承诺。如何在异步捕获中使用类型化错误()

你可以嘲笑这种行为是这样的:使用async的时候,如果我尝试注释错误

api().catch((error: ApiError) => console.log(error.code, error.message)) 

但是:

interface ApiError { 
    code: number; 
    error: string; 
} 

function api(): Promise<any> { 
    return new Promise((resolve, reject) => { 
    reject({ code: 123, error: "Error!" }); 
    }); 
} 

现在用的承诺,我可以标注错误类型ApiError键入try ... catch()

async function test() { 
    try { 
    return await api(); 
    } catch (error: ApiError) { 
    console.log("error", error); 
    } 
} 

它与错误编译:

Catch clause variable cannot have a type annotation.

那么,如何,我知道我期待什么样的错误?我是否需要在catch()区块中写出断言?这是异步的错误/不完整的功能吗?

在TypeScript中,catch子句变量可能没有类型注释。这不是特定于async。下面是an explanation from Anders Hejlsberg

We don't allow type annotations on catch clauses because there's really no way to know what type an exception will have. You can throw objects of any type and system generated exceptions (such as out of memory exception) can technically happen at any time.

您可以检查在卡位体error.codeerror.message属性(任选地使用user-defined type guard)的存在。

+0

谢谢。我猜这就是'Promise.catch()'没有类型参数的原因。尽管如此,我希望我能写下我期待的错误......很多TS只是写下你期望的东西,当然不能保证你的类型在运行时会是真的! – Aaron

+0

@Aaron你总是可以做'const apiError:ApiError = error;'catch块内部(错误是'any'类型的) –

+1

是的,这就是我正在做的事情。它只是一个不太简洁的承诺。 – Aaron

此错误与async无关。你不能有类型的catch变量。

原因很简单:只有在编译代码之前,TypeScript中的类型才存在。一旦编译完成,你所拥有的就是无类型的JavaScript。

对catch子句使用类型过滤器需要在运行时检查错误的类型,并且根本没有可靠的方法来做到这一点,所以我会说这样的功能不太可能被支持。