一起使用 async await 和 .then
Posted
技术标签:
【中文标题】一起使用 async await 和 .then【英文标题】:using async await and .then together 【发布时间】:2019-07-27 21:54:35 【问题描述】:async/await
和.then().catch()
一起使用有什么坏处吗,比如:
async apiCall(params)
var results = await this.anotherCall()
.then(results =>
//do any results transformations
return results;
)
.catch(error =>
//handle any errors here
);
return results;
【问题讨论】:
我想anotherCall
是.then
打电话吗?
抱歉,忘记了。现在添加它。
不,没有害处。您只是使用await
将承诺链的最终值传递给result
变量。
【参考方案1】:
我总是使用async/await
和.catch()
而不是使用async/await
和try/catch
来紧凑地编写代码。
async function asyncTask()
throw new Error('network')
async function main()
const result = await asyncTask().catch(error => console.error(error));
console.log('result:', result)
main();
如果你想在错误发生时获得一个回退值,你可以忽略错误并在.catch()
方法中返回一个值
async function asyncTask()
throw new Error('network')
async function main()
const result = await asyncTask().catch(_ => 'fallback value');
console.log('result:', result)
main();
【讨论】:
我没有想到你的方式,但我真的很喜欢!我通常以相反的方式混合它们,使用带有 await 的 try / catch 语句并使用 .then 来执行额外的转换或对已解决的承诺进行任何操作。 假设您在result =
行之后有更多代码。假设有一个错误。 result
然后是未定义的吗?
@JeffPadgett 是的,您可以从 .catch()
方法返回一个备用值
您介意使用 .catch()
方法的后备更新您的答案吗?
@JeffPadgett 更新了答案。【参考方案2】:
一个异步函数可以包含一个等待表达式来暂停 执行异步函数并等待传递的 Promise 解决,然后恢复异步函数的执行和 返回解析后的值。
从下面的示例中可以看出,您可以使用两种方法来处理等待结果和错误,关键字 await 使 javascript 等到该承诺解决并返回其结果(一个您从已解决的承诺中获得)。因此有没有害处(我不完全理解你在这里所说的危害)。
function returnpromise(val)
return new Promise((resolve, reject) =>
if (val > 5)
resolve("resolved"); // fulfilled
else
reject("rejected"); // rejected
);
//This is how you handle errors in await
async function apicall()
try
console.log(await returnpromise(5))
catch (error)
console.log(error)
async function apicall2()
let data = await returnpromise(2).catch((error) =>
console.log(error)
)
apicall2();
apicall();
更多参考请看-MDN DOCS
【讨论】:
【参考方案3】:不想让死人复活,但想指出使用await
和then
链意味着:
const x = await someAsyncFn().then(() => doSomeLogging());
x
的值被赋值为.then
的返回值,这对我来说不是很直观。
【讨论】:
【参考方案4】:如果您使用 Async/await,则无需链接 .then()
,只需将 resolve()
返回的结果存储在变量中(示例中为 response
),但如果您想处理您遇到的错误尝试/捕获您的代码:
async function f()
try
let response = await fetch('http://no-such-url');
catch(err)
alert(err); // TypeError: failed to fetch
在你的承诺中使用:
throw new Error("oops!");
或者
Promise.reject(new Error("Whoops!"));
【讨论】:
我一直在使用它,它比使用 .then + 另一个使整个事情难以辨认的匿名异步函数更好【参考方案5】:我认为混合使用 async/await + then 不是一个好主意。尤其是当你专注于 async func 的 res 时,混合使用会带来一些风险,会默默地扭曲你的 res。
示例:
const res = await fetchData().then(()=>return "something else").catch((err)=>);
console.log(res); // not expected res data but something else
所以,混用是危险的,顺便说一下,读码是有害的。
【讨论】:
建议:添加代码围栏和语言标识符以突出显示代码并使其更具可读性。以上是关于一起使用 async await 和 .then的主要内容,如果未能解决你的问题,请参考以下文章
如何使用 async/await 编写 .then 函数,以便捕获来自 axios 的响应(在单独的文件和方法中,在 vue 中)
Async / await vs then 哪个最适合性能?