🚀Promise 全家桶:原理、实现、API、实战,一篇搞定

#金石焕新程

🚀《Promise 全家桶:原理、实现、API、实战,一篇搞定》

Promise 是前端开发中异步编程的基石,但你真的用对了吗?本文从 Promise 的原理讲起,带你实现一个迷你 Promise,再把 Promise 的 10+ 方法一网打尽,最后结合实际开发场景,教你如何优雅地处理异步任务。


一、Promise 是什么?

Promise 是一个表示异步操作最终完成(或失败)及其结果的对象。它有三种状态:

  • Pending(进行中)
  • Fulfilled(已成功)
  • Rejected(已失败)

Promise 的核心在于,它允许你通过 .then().catch() 方法来处理异步操作的结果。


二、Promise 的原理

Promise 的核心是 事件循环微任务队列。当一个 Promise 被创建时,它会立即执行,并将回调函数放入微任务队列中。一旦 Promise 的状态变为 Fulfilled 或 Rejected,对应的回调函数就会被触发。

javascript 复制代码
const promise = new Promise((resolve, reject) => {
  // 异步操作
  setTimeout(() => resolve('Success'), 1000);
});

promise.then(result => console.log(result)); // 'Success'

三、实现一个迷你 Promise

javascript 复制代码
class MiniPromise {
  constructor(executor) {
    this.state = 'pending';
    this.value = undefined;
    this.handlers = [];

    const resolve = value => {
      if (this.state === 'pending') {
        this.state = 'fulfilled';
        this.value = value;
        this.handlers.forEach(handler => handler());
      }
    };

    const reject = reason => {
      if (this.state === 'pending') {
        this.state = 'rejected';
        this.value = reason;
        this.handlers.forEach(handler => handler());
      }
    };

    executor(resolve, reject);
  }

  then(onFulfilled, onRejected) {
    return new MiniPromise((resolve, reject) => {
      this.handlers.push(() => {
        if (this.state === 'fulfilled') {
          onFulfilled(this.value);
        } else if (this.state === 'rejected') {
          onRejected(this.value);
        }
      });
    });
  }
}

四、Promise 的 API

1. Promise.resolve(value)

  • 作用:返回一个状态为 Fulfilled 的 Promise。
  • 示例
javascript 复制代码
Promise.resolve('Hello').then(console.log); // 'Hello'

2. Promise.reject(reason)

  • 作用:返回一个状态为 Rejected 的 Promise。
  • 示例
javascript 复制代码
Promise.reject('Error').catch(console.error); // 'Error'

3. Promise.all(iterable)

  • 作用:接收一个 Promise 数组,当所有 Promise 都成功时返回一个包含所有结果的数组。
  • 示例
javascript 复制代码
Promise.all([fetch('/api/user'), fetch('/api/posts')])
  .then(([user, posts]) => console.log(user, posts));

4. Promise.race(iterable)

  • 作用:接收一个 Promise 数组,返回第一个完成的 Promise 的结果。
  • 示例
javascript 复制代码
Promise.race([fetch('/api/user'), fetch('/api/posts')])
  .then(result => console.log(result));

5. Promise.allSettled(iterable)

  • 作用:接收一个 Promise 数组,返回一个包含所有 Promise 结果的数组(无论成功还是失败)。
  • 示例
javascript 复制代码
Promise.allSettled([fetch('/api/user'), fetch('/api/posts')])
  .then(results => console.log(results));

6. Promise.any(iterable)

  • 作用:接收一个 Promise 数组,返回第一个成功的 Promise 的结果。
  • 示例
javascript 复制代码
Promise.any([fetch('/api/user'), fetch('/api/posts')])
  .then(result => console.log(result));

五、Promise 的链式调用

javascript 复制代码
fetch('/api/user')
  .then(response => response.json())
  .then(user => console.log(user))
  .catch(error => console.error(error));

1. .then(onFulfilled, onRejected)

  • 作用:处理 Promise 的成功和失败。
  • 示例
javascript 复制代码
fetch('/api/user')
  .then(response => response.json())
  .then(user => console.log(user))
  .catch(error => console.error(error));

2. .catch(onRejected)

  • 作用:捕获 Promise 的错误。
  • 示例
javascript 复制代码
fetch('/api/user')
  .then(response => response.json())
  .catch(error => console.error(error));

3. .finally(onFinally)

  • 作用:无论成功还是失败都会执行的回调。
  • 示例
javascript 复制代码
fetch('/api/user')
  .then(response => response.json())
  .finally(() => console.log('Done'));

六、Promise 的实际应用

1. 数据加载

javascript 复制代码
function fetchData(url) {
  return fetch(url)
    .then(response => response.json())
    .catch(error => console.error('Error:', error));
}

fetchData('/api/user').then(user => console.log(user));

2. 异步表单提交

javascript 复制代码
function submitForm(data) {
  return fetch('/api/submit', {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify(data)
  }).then(response => response.json());
}

submitForm({ name: 'John', email: 'john@example.com' })
  .then(result => console.log(result))
  .catch(error => console.error(error));

3. 超时处理

javascript 复制代码
function timeoutPromise(promise, ms) {
  return new Promise((resolve, reject) => {
    const timeout = setTimeout(() => reject(new Error('Timeout')), ms);
    promise.then(result => {
      clearTimeout(timeout);
      resolve(result);
    }).catch(error => {
      clearTimeout(timeout);
      reject(error);
    });
  });
}

timeoutPromise(fetch('/api/user'), 5000)
  .then(response => response.json())
  .then(user => console.log(user))
  .catch(error => console.error(error));

4. 错误处理

javascript 复制代码
function fetchData(url) {
  return fetch(url)
    .then(response => {
      if (!response.ok) throw new Error('Network response was not ok');
      return response.json();
    })
    .catch(error => console.error('Error:', error));
}

fetchData('/api/user').then(user => console.log(user));

七、总结

Promise 是 JavaScript 异步编程的核心工具,通过 .then().catch().finally() 方法,可以优雅地处理异步任务。Promise 的链式调用和组合方法(如 Promise.allPromise.race)让复杂的异步流程变得简洁明了。希望本文能帮助你在实际开发中更好地使用 Promise。


🏁 一句话总结

Promise = 异步编程基石.then() 处理结果,.catch() 捕获错误,Promise.all 组合多个 Promise,链式调用让异步流程清晰易读。

相关推荐
Web极客码12 分钟前
如何为WordPress启用LiteSpeed缓存
前端·缓存
咕噜分发企业签名APP加固彭于晏28 分钟前
白嫖价值千元的EO
前端·javascript
前端开发爱好者30 分钟前
首个「完整级」WebSocket 调试神器来了!
前端·javascript·vue.js
前端Hardy32 分钟前
HTML&CSS&JS:高颜值登录注册页面—建议收藏
前端·javascript·css
白雾茫茫丶34 分钟前
如何动态执行 JS 脚本
javascript
Ali酱35 分钟前
远程这两年,我才真正感受到——工作,原来可以不必吞噬生活。
前端·面试·远程工作
金金金__40 分钟前
优化前端性能必读:浏览器渲染流程原理全揭秘
前端·浏览器
Data_Adventure44 分钟前
Vue 3 手机外观组件库
前端·github copilot
泯泷1 小时前
Tiptap 深度教程(二):构建你的第一个编辑器
前端·架构·typescript
屁__啦1 小时前
前端错误-null结构
前端