You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何实现带时间间隔的Promise.all式批量Imgur图片上传?

实现带间隔的串行批量上传并保留Promise.all风格的响应格式

要实现每两次上传间隔1秒,同时保留Promise.all的.then((responseArray) => ...)响应格式,核心思路是串行执行上传任务,每次任务(除第一个)执行前等待指定间隔,最后收集所有结果返回一个Promise。以下是两种可行的实现方式:

方式一:使用Promise.reduce构建链式调用

这种方式通过Array.reduce逐步构建Promise链,自动收集每个上传任务的结果:

1. 定义延迟工具函数

// 返回一个延迟指定毫秒的Promise
const delay = (ms) => new Promise(resolve => setTimeout(resolve, ms));

2. 实现带间隔的上传函数

/**
 * 带间隔的串行批量上传函数
 * @param {Function[]} uploadTasks - 上传任务数组,每个元素是返回Promise的上传函数
 * @param {number} intervalMs - 两次上传之间的间隔毫秒数
 * @returns {Promise<any[]>} 返回包含所有上传结果的Promise
 */
function uploadWithInterval(uploadTasks, intervalMs) {
  return uploadTasks.reduce((promiseChain, task, index) => {
    return promiseChain
      // 非第一个任务,先等待间隔
      .then(results => index > 0 ? delay(intervalMs).then(() => results) : results)
      // 执行当前上传任务并收集结果
      .then(results => task().then(response => [...results, response]));
  }, Promise.resolve([])); // 初始Promise,结果数组为空
}

3. 使用示例

假设listOf20Tasks是包含20个上传任务的数组(每个任务是返回Promise的函数,比如调用Imgur上传API的函数):

uploadWithInterval(listOf20Tasks, 1000)
  .then(responseArray => {
    // 这里拿到和任务顺序一致的所有上传结果数组,和Promise.all的响应格式完全一致
    console.log('全部上传完成:', responseArray);
  })
  .catch(error => {
    // 任何一个上传失败都会触发这里,和Promise.all的错误行为一致
    console.error('上传失败:', error);
  });

方式二:使用async/await循环(更直观)

利用async/await的串行特性,循环执行任务并收集结果:

async function uploadWithInterval(uploadTasks, intervalMs) {
  const responseArray = [];
  for (let i = 0; i < uploadTasks.length; i++) {
    // 不是第一个任务,先等待间隔
    if (i > 0) {
      await delay(intervalMs);
    }
    // 执行当前上传任务并保存结果
    const response = await uploadTasks[i]();
    responseArray.push(response);
  }
  // 返回结果数组,async函数会自动包装为Promise
  return responseArray;
}

使用方式和上面完全相同,因为async函数返回的就是Promise,所以可以直接用.then拿到结果数组。

可选:容错处理(类似Promise.allSettled)

如果希望某个上传失败时不中断整个流程,而是继续执行后续任务并记录错误,可以修改上传任务的错误处理:

// 在执行task时添加catch,将错误存入结果数组
.then(results => task()
  .then(response => [...results, { success: true, data: response }])
  .catch(error => [...results, { success: false, error }])
)

这样最终的responseArray会包含每个任务的成功/失败状态,不会因为单个任务失败而reject。


内容的提问来源于stack exchange,提问作者Bhuwan Adhikari

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.17 18:15:38