簡體   English   中英

如何在forEach循環中每秒運行一次setTimeout?

[英]How do you run a setTimeout once a second inside a forEach loop?

我的代碼,以便在每分鍾60個寫限制的在線服務中創建多個展示位置:

  placementsToAdd.forEach((placement, index) => {
    setTimeout(() => {
      options.url = `https://api.company.com/placement?publisher_id=${existingPub ? existingPub : placementsJson[0].PublisherId}&site_id=${placement.siteId}`
      options.body = `{"placement":{"name":"${placement.placement}"}}`
      request(options, callback);  
    },1000 * (index + 1))
  })

它是這樣工作的,但我擔心的是等待時間,如果一次有2000或3000個展示位置列表,等待時間可能會過長。

是否有更好的方法來重構此代碼,以使我的請求每秒生成一次,無論如何? 如果沒有該“ *(索引+ 1)”,它似乎總是試圖在60歲以后立即將所有建築物都撞牆。

我試圖使用Promise和async等待(這對我來說是新的),但它似乎並沒有改變行為。

謝謝!

根據要求,顯示我如何嘗試通過以下代碼使用promise:

  async function createThePlacements() {
    let promise = new Promise((resolve, reject) => {
      for (let i = 0; i < placementsToAdd.length; i++) {
        setTimeout(() => {
          options.url = `https://api.company.com/placement?publisher_id=${existingPub ? existingPub : placementsJson[0].PublisherId}&site_id=${placementsToAdd[i].siteId}`
          options.body = `{"placement":{"name":"${placementsToAdd[i].placement}"}}`
          request(options, callback);  
        },1000)
      }
    });

    let result = await promise; // pause till the promise resolves 
    console.log('result - ', result);
  }

  createThePlacements();

因此,免責聲明-如前所述,我從未使用過Async Await,因此請仔細閱讀以了解其工作原理。 這似乎是語法,但目前我的結果似乎什么都沒有,但是代碼也繼續執行應做的工作,只是嘗試一次一次在300個測試中進行所有調用。

另外,值得注意的是,我在請求調用的回調中有一個解決方法。 它可以解決,因此即使我的應用程序的下一部分也一直完成到最后。 這就是為什么我在這里沒有拒絕或解決的原因。

如何在forEach循環中每秒運行一次setTimeout?

最直接的方法是:

const wait = ms => new Promise(resolve => setTimeout(resolve, ms));

for (const placement of placementsToAdd) {
  const options = {...};
  request(options, callback);  
  await wait(1000);
}

await在普通的for循環內而不是forEach內可預測地工作。

我沒有碰過您的callback但它需要處理錯誤。 更多重構是可能的。

我認為,這里最重要的改進是我們不會提前推送請求。 通過這種方式,我們可以保持控制力,並且在需要進行更改或發生任何麻煩的情況下,我們可以擺脫循環,而不會向服務器發送垃圾郵件一分鍾。

最好的選擇是擁有一個返回Promise的request方法。

然后,您可以像這樣重寫代碼。

function sleep(ms) {
  return new Promise(resolve => setTimeout(resolve, ms));
}

function requestPlacement(placement) {
  const options = {...};
  return request(options);
}

async function requestAllPlacements(placements) {
  for(let i = 0; i < placements.length; i+=60) {
    if (i > 0) {
      // wait 1 minute
      await(sleep(60000));
    }

    await Promise.all(
      placements
        .slice(i, 60)
        .map(requestPlacement);
    );
  }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM