ES10 中的新特性:Promise.prototype.finally() 的应用场景

背景

在前端开发中,Promise 是很常见的异步编程解决方案。它的出现让我们可以更便捷地处理异步操作,但是在过去的版本中,Promise 还存在一些烦人的问题,比如:

  • 处理不当会导致 unhandled rejection 错误
  • 是否成功都必须执行的某些代码很难维护

对于第二个问题,Promise.prototype.finally() 的出现为我们解决了这个问题。

Promise.prototype.finally()

Promise.prototype.finally() 是 ES10 新增的方法,它接受一个回调函数作为参数,该回调函数在 Promise 被 resolve 或 reject 后都会调用,无论 Promise 最后的状态是成功还是失败,也无论是否有 finally 回调函数注册。

Promise.prototype.finally = function(onFinally) {
  return this.then(
    result => Promise.resolve(onFinally()).then(() => result),
    reason => Promise.resolve(onFinally()).then(() => { throw reason })
  );
};

其内部实现是通过 Promise.resolve() 包装回调函数,并 Promise 链式调用 then() 方法,使得代码更加简洁明了。我们可以通过 Promise.prototype.finally() 实现清理资源、关闭网络连接等操作,而且不用担心它会影响 Promise 最终的状态。

应用场景

提供统一的处理逻辑

Promise.prototype.finally() 为 Promise 提供了一种处理成功和失败的方式,能够自动执行后续代码,避免了回调地狱。另外,它还可以用于提供统一的处理逻辑,比如:

function fetchApi() {
  return fetch('/api/v1/data')
    .then(response => response.json())
    .catch(error => { throw error; })
    .finally(() => { console.log('API request done.'); });
}

在上面的代码中,我们定义了一个 fetchApi() 函数,并在 Promise 函数链中通过 .finally() 注册了一个回调函数,用于在 fetch 接口请求完成后显示一条消息。

清理资源

function downloadFile(url) {
  return fetch(url)
    .then(response => response.blob())
    .finally(() => window.URL.revokeObjectURL(url)) // 清理资源
    .then(blob => { ... });
}

在上面的代码中,我们定义了一个 downloadFile() 函数用于下载文件,并在 fetch().finally() 函数链中带有资源清理逻辑,用于释放占用的内存和更新 GUI 界面。

关闭网络连接

function closeConnection() {
  return new Promise((resolve, reject) => {
    const socket = new WebSocket('ws://localhost:3000');
    socket.onopen = () => resolve(socket);
    socket.onclose = () => console.log('Socket connection has been closed.');
  })
    .finally(() => socket.close()); // 关闭网络连接
}

在上面的代码中,我们定义了一个 closeConnection() 函数来关闭 Websocket 网络连接,其中通过 Promise 封装 Websocket 连接,.finally() 注册了一个回调函数来关闭网络连接。

总结

Promise.prototype.finally() 可以使我们更好地处理 Promise 的逻辑,排除一些不必要的麻烦,同时也可以提高代码的清晰度和可读性。在网页开发中,我们会遇到很多异步操作,使用 Promise.prototype.finally() 改进代码逻辑可以使代码更加清晰易读。

来源:JavaScript中文网 ,转载请注明来源 本文地址:https://www.javascriptcn.com/post/65966ccfeb4cecbf2da3fc9a


纠错反馈