What is the best way to limit concurrency when using ES6's Promise.all()?

前端 未结 17 783
执念已碎
执念已碎 2020-11-29 21:28

I have some code that is iterating over a list that was queried out of a database and making an HTTP request for each element in that list. That list can sometimes be a rea

17条回答
  •  陌清茗
    陌清茗 (楼主)
    2020-11-29 22:12

    expanding on the answer posted by @deceleratedcaviar, I created a 'batch' utility function that takes as argument: array of values, concurrency limit and processing function. Yes I realize that using Promise.all this way is more akin to batch processing vs true concurrency, but if the goal is to limit excessive number of HTTP calls at one time I go with this approach due to its simplicity and no need for external library.

    async function batch(o) {
      let arr = o.arr
      let resp = []
      while (arr.length) {
        let subset = arr.splice(0, o.limit)
        let results = await Promise.all(subset.map(o.process))
        resp.push(results)
      }
      return [].concat.apply([], resp)
    }
    
    let arr = []
    for (let i = 0; i < 250; i++) { arr.push(i) }
    
    async function calc(val) { return val * 100 }
    
    (async () => {
      let resp = await batch({
        arr: arr,
        limit: 100,
        process: calc
      })
      console.log(resp)
    })();

提交回复
热议问题