介绍
在前端开发中,我们经常需要编写异步的代码来处理数据或者请求。在 Node.js 中,我们有一些内置的模块,例如 fs
和 http
,提供了异步的 API。为了更好地处理异步代码,Node.js 从 7.6 版本开始支持了 async/await
。该特性让异步代码看起来更加具有同步代码的流畅性,并减少了回调嵌套和错误处理代码的复杂程度。
本文将介绍 async/await
的使用细节及其指导意义,并附带代码示例。
async/await 的基本语法
在使用 async/await
之前,请确保您已经熟悉异步编程和 Promise 对象的用法。async/await
只是一种编写异步代码的方式,它并不能完全替代 Promise。
async
关键字 async
可以修饰一个函数,它表明该函数总是返回一个 Promise 对象。下面是一个简单的例子:
async function test() { return 'Hello, world!'; } test().then(console.log); // 输出 Hello, world!
我们定义了一个 async
函数 test
,它的返回值是一个字符串 "Hello, world!"
。在调用 test
后,我们通过 Promise 的 then
方法获取结果并将其输出到控制台。
await
关键字 await
可以放在一个 Promise 对象前面,表示等到该 Promise 对象执行完毕并返回结果后,再执行下一步操作。例如:
-- -------------------- ---- ------- -------- ------------ - ------ --- --------------- -- ------------------- -------- - ----- -------- ------ - --------------------- ----- ------------ -- -- - - ------------------- - ------- -- -- ----- - -------- - -
在 test
函数中,我们使用 sleep
函数来模拟延迟,接着使用 await
关键字等待该 Promise 对象返回结果。由于 sleep
函数返回的是一个 Promise 对象,所以 await sleep(1000)
的作用就是等待 1 秒钟,然后再继续执行下一步操作。
async/await 的高级用法
错误处理
在异步代码中,我们经常需要处理错误。在使用 async/await
时,我们可以使用 try/catch
语句来捕获 Promise 执行过程中的异常。例如:
-- -------------------- ---- ------- ----- -------- ------ - --- - ----- ------- - ----- ------------------- ----- ------- - ----- ------------------ ----------------- - ----- ------- - ----------------------------- - - ------- -- -- ------
该例子中,我们在 test
函数中使用了两个 Promise,第一个 Promise 是 Promise.resolve
,表示成功执行并返回了数字 1
。第二个 Promise 是 Promise.reject
,表示执行失败并返回了一个 Error 对象,我们使用 try/catch
语句捕获了该异常,并将其输出到控制台。
并行执行
在异步编程中,有时候我们需要同时执行多个异步操作,并在它们都完成后进行下一步操作。使用 Promise.all
可以很方便地实现该功能。例如:
-- -------------------- ---- ------- ----- -------- ------ - ----- --------- -------- - ----- ------------- ------------------- ------------------ --- ------------------- - --------- -- -- - - -------
在该例子中,我们使用了 Promise.all
函数同时执行了两个 Promise 对象,因为它们的返回值是不相关的,所以可以在它们都执行完毕后进行下一步操作,例如将它们的返回值相加。
超时处理
在异步编程中,我们有时候需要设置超时时间,如果异步操作在超时时间内没有执行完毕,就算作失败并进行下一步操作。使用 Promise.race
可以实现该功能。例如:
-- -------------------- ---- ------- -------- ------------ - ------ --- --------------- -- ------------------- -------- - ----- -------- ------ - --- - ----- ------ - ----- -------------- ------------ -- -- - - --- ----------------- ------- -- ------------- -- ---------- ------------------- ----- - -- ----- - - --- -------------------- - ----- ------- - ----------------------------- - - ------- -- -- --------
在该例子中,我们使用了 Promise.race
函数同时执行了两个 Promise,其中 sleep(2000)
表示延迟 2 秒执行, new Promise(...)
表示延迟 1 秒后返回一个失败的 Promise,模拟了超时的情况。因为 sleep(2000)
的时间比超时时间长,所以会先执行完毕并返回结果,但由于我们使用 Promise.race
函数,所以只有在超时时间内返回结果的 Promise 才会被接受。
实践示例
-- -------------------- ---- ------- ----- ----- - ---------------------- ----- -------- ------------ - --- - ----- -------- - ----- ----------- ----- ---- - ----- ---------------- ----- ---- - ----------------- ------ ----- - ----- ------- - ----------------------------- - - ----- -------- ------ - ----- ---- - ----- ------------------------------------------------ ----------------------- -- -- ---- -------- - -------
在该例子中,我们定义了一个 getJSON
函数,它使用了 node-fetch
模块来获取指定 URL 的 JSON 数据。该函数通过 await
关键字等待 fetch
函数和 JSON.parse
函数执行完毕,并返回解析后的 JSON 数据。接着在 test
函数中调用了 getJSON
函数来获取 GitHub 用户 octocat
的信息,并将其输出到控制台。如果获取失败,则会使用 console.error
方法输出错误信息。
总结
使用 async/await
可以大大简化异步编程的代码,增加其可读性和可维护性。在编写异步代码时,我们应该善于使用 async/await
来提高效率、减少错误,并且更加方便地处理异步操作。同时,在使用 async/await
时,我们应该注意其细节和常用模式,以编写出更加健壮和可靠的异步代码。
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/646afc13968c7c53b0a700d4