ES12 的异步函数上下文管理

阅读时长 4 分钟读完

在 ES6 中引入了异步函数 async/await,它允许开发者以同步的方式编写异步代码。而在 ES12 中,异步函数的上下文管理得到了进一步的加强,使得代码编写更加简便,也更加易于维护。

异步函数的上下文问题

首先,让我们来看一下在异步函数中会存在什么样的上下文问题。

例如,我们希望在异步函数中保存一个计时器的值,然后在完成异步操作后输出它。我们可以尝试以下代码:

-- -------------------- ---- -------
----- -------- ------ -
  --- ----- - --

  -------------- -- -
    --------
  -- ------

  ----- --- ----------------- -- ------------------- -------

  ------------------- -- -
-

-------

然而,我们会发现计数器的值始终为 0,即使等待了 5 秒。这是因为计时器回调函数是在异步函数的上下文之外执行的,所以无法访问到它的作用域。

为了解决这个问题,我们可以将计时器的回调函数封装在另外一个函数中,并将计数器作为参数传递进去。

-- -------------------- ---- -------
----- -------- ------ -
  --- ----- - --

  -------- ------------- -
    --------
  -

  ------------------------ ------

  ----- --- ----------------- -- ------------------- -------

  ------------------- -- -
-

-------

现在我们成功地在异步函数里使用了计时器,并正确输出了计数器的值。

异步函数的上下文管理

然而,上面的代码显得有些冗余,还需要手动封装回调函数并传递参数。在 ES12 中,我们可以使用 AsyncLocalStorage 来更加简便地管理异步函数的上下文。

AsyncLocalStorage 可以让我们在异步函数之间传递数据,类似于全局变量,但是只在当前运行的异步函数中有效。

我们先安装 node:async_hooks,它包含了 AsyncLocalStorage:

接着我们可以以下面的方式在异步函数中使用 AsyncLocalStorage

-- -------------------- ---- -------
------ - ----------------- - ---- --------------

----- ----------------- - --- --------------------

----------------------- ------ - -- ----- -- -- -
  -------------- -- -
    ----- ----- - ----------------------------------- -- --
    ---------------------------------- - ----- - --
  -- ------
  
  ----- --- ----------------- -- ------------------- -------

  ------------------------------------------------- -- -
---

我们使用 asyncLocalStorage.run() 在异步上下文中创建了一个新的存储区域,并设置了一个初始值 { count: 0 }。接着我们可以使用 asyncLocalStorage.getStore() 在存储区域中获取或者更新值。

需要注意的是,在异步函数运行期间,存储区域中的数据只有在通过 asyncLocalStorage.getStore() 获取到之后才能改变。因此,在每个访问存储区域的点,asyncLocalStorage.getStore() 返回的实例往往是不同的。

结论

ES12 中的 AsyncLocalStorage 让异步函数的上下文管理变得更加简便,使得代码编写更加简单,也更加易于维护。

通过运用 AsyncLocalStorage,您可以避免在异步函数中频繁使用封装方法和传递参数的繁琐过程,而仅需要一个共享的全局存储区域即可。

来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/67455964c1a23897ea922bb7

纠错
反馈