2016-07-20 6 views
0

Мой код:ограничение скорости запросов к третьей стороной API

const limit = require('simple-rate-limiter') 
const request = limit(require('request').defaults({ 
    gzip: true 
})).to(15).per(10 * 1000) // 15 requests per 10 seconds 

request(API_ENDPOINT, callback) // call API thousands of times 

библиотеки: simple-rate-limiter и хорошо известная request библиотека.


Мне нужно вызывать сторонний API тысячи раз, что позволяет только 15 запросов каждые 10 секунд. Вышеприведенный код не ограничивает мои запросы правильно, поэтому сервер отправляет код состояния HTTP 429 Too Many Requests.

Я могу отправить 15 запросов одновременно, но тогда программе придется ждать в течение 10 секунд, прежде чем он сможет отправить еще какие-либо запросы, или снова получит ответ 429.

Я думаю, это связано с тем, что подключение к серверу занимает от нескольких сотен миллисекунд до нескольких секунд (300ms-2s). Таким образом, время моего запроса отличается от времени, когда сервер получает запрос.

Ответы с сервера содержат заголовок Date. Может ли это как-то правильно ограничивать запросы? Есть ли библиотека, которая делает это проще? Даже после правильного ограничения скорости, если вы получаете ответ 429, есть ли простой способ повторить это тоже?

+0

вы хотите обмануть API и назвать конечную точку больше, чем ее ограничения? я тебя понял? – Rouz

+0

Нет, я хочу назвать это в соответствии с ограничениями. Если я этого не сделаю, я получаю ответ «429» HTTP, который я не хочу получать. – Elmo

ответ

0

ОК, поэтому подход заключается в проверке того, сколько времени прошло с самого начала до конца разговора. Я буду считать, что безопасно вызывать API каждые 667 миллисекунд.

var startTime, 
    endTime; 

function timeDiff() { 
    return (endTime.getTime() - startTime.getTime()); 
} 
function startRequest() { 
    startTime = new Date(); 
    request(API_ENDPOINT, requestCallback) 
} 
function requestCallback(data) { 
    //do what you please with data 
    endTime = new Date(); 
    var diff = timeDiff(); 
    if(diff < 667) { 
     //To early to start API, need to wait. 
     setTimeout(startRequest, 667 - diff); 
    } else { 
     //It is fine to start request now. 
     setTimeout(startRequest); 
    } 
} 

startRequest(); 

Этот код будет продолжать называть API, как только вызов завершается, если она не закончена быстрее, чем 667 миллисекунд.