簡體   English   中英

GDAX API-超出了速率限制

[英]GDAX API - Rate limit exceeded

當我嘗試從GDAX請求歷史數據時,收到一條錯誤消息“超出速率限制”。 我使用promise和setInterval從GDAX請求歷史價格數據,如下所示:

let promiseArray = //Array with promises
let j = 0;
let grabPrices = setInterval(() => {
    if (j === promiseArray.length) {
        //Do something when all promises have been resolved
    } 
    else {
        promiseArray[j].then(
            data => {
                //Work with data
            }
        ).catch(error => console.log('An error occurred: ' + error));
        j++;
    }
}, 1000) //I have even tried to use 10 seconds (10000) as a second argument to setInterval, but it doesn't make any difference.

官方API文檔

速率限制超過速率限制時,將返回429個請求過多的狀態。

REST API公共端點我們通過IP限制公共端點:每秒3個請求,每秒最多6個請求。

當您有一個Promise時,該請求已經發出,因此您的promiseArray是一個正在進行的請求的數組。

假設我有一個網址數組,並使用fetch來獲取內容。 使用map將URL映射到一個Promise.all數組提供給Promise.all

Promise.all(
  urls.map(fetch)
).then(
  resulst=>...
);

如果網址有10個項目,則此程序將立即發出10個請求。

您可以將fetch函數傳遞給節流函數,該函數將以每秒僅調用3次的方式調度獲取。 節流功能將返回一個Promise,但不會立即調用fetch。

節流閥功能可以在這里找到。 如果您只打算從該模塊復制粘貼代碼而不導入整個模塊,那么您還需要后面的函數,因為節流閥取決於它。

const fetchMaxThreePerSecond = throttlePeriod(3,1100)/*give it an extra 100*/(fetch)
Promise.all(
  urls.map(fetchMaxThreePerSecond)
).then(
  resulst=>...
);

這可以解決節流問題,但是如果您知道Promise.all工作原理,那么您就會知道,只有一個拒絕,所有的Promise.all都會被拒絕。 因此,如果您有100個網址和99個解析地址,但其中一個拒絕了您的.then不會被調用。 您將丟失99個成功的請求。

您可以將一個承諾傳遞給Promise.all所有不會拒絕的承諾都可以通過捕獲被拒絕的承諾來實現,並在catch中返回一個特殊的值,您可以在處理結果時過濾掉該值:

const fetchMaxThreePerSecond = throttlePeriod(3,1100)/*give it an extra 100*/(fetch);
const Fail = function(reason){this.reason = reason;};
const isFail = x=>(x&&x.constructor)===Fail;
const isNotFail = x=>!isFail(x);
Promise.all(
  urls.map(
    url=>
      fetchMaxThreePerSecond(url)
      .catch(e=>new Fail([url,e]))//save url and error in Fail object
  )
)
.then(//even if a request fails, it will not reject
  results=>{
    const successes = results.filter(isNotFail);
    const failed = results.filter(isFail);
    if(failed.length!==0){
      console.log("some requests failed:");
      failed.forEach(
        (fail)=>{
          const [url,error] = fail.reason;
          console.log(`Url: ${url}`);
          console.log(JSON.stringify(error,undefined,2));
        }
      )
    }
  }
); 

將速率限制器設置為每2.1秒3個API調用時,GDAX歷史記錄調用沒有問題。

當我將速率限制器設置為每1.8秒3個API調用時,偶爾會遇到一些問題。

我已經用自動化測試測試了這些值。

重要提示:我對GDAX的所有呼叫均使用相同的速率限制器(!)

為保存起見,請使用@HMR答案中的代碼以及我測試過的參數。

暫無
暫無

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

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