I am trying to simulate HTTP-request throttling with the following code. (Inside step 2)
I want to queue the request if the request is made in less than 300 milliseconds. Later I need to dequeue but keeping the same constraint of 300 milliseconds while making requests.
The code works fine, but I am somewhere incorrect in the dequeue logic. I am unable to keep the constraint of 300 milliseconds during the dequeue process. Sometimes, the difference between lastRequestMade
and now
is less than 300 ms, when the set timeout was set to 300 + x
. What could be the reason for this?
const moment = require('moment');
const crypto = require('crypto');
let lastRequestMade = null;
let queue = [];
let requestIdList = [];
let lastRequestEq = null;
let timeoutInterval = 0;
// STEP 1
for (let x = 0; x < 100; x++) {
// Init the request queue with the request ids
requestIdList.push(crypto.randomBytes(8).toString('hex'));
}
// STEP 2
for (let x = 0; x < 100; x++) {
if (lastRequestMade && moment().diff(lastRequestMade) < 300) { // Rate limit to 300 milliseconds
// If the last request made was less than 300 milliseconds
// queue the request
queue.push(requestIdList[x]);
console.log(`Enqueue ${requestIdList[x]}`);
timeoutInterval += 300;
setTimeout(() => {
let rid = queue.splice(0, 1);
sendRequest(...rid);
if (queue.length == 0)
console.log('No request left in the queue');
}, timeoutInterval);
} else {
sendRequest(requestIdList[x]);
}
}
/**
* Request maker
*/
function sendRequest(requestId) {
if (lastRequestMade && moment().diff(lastRequestMade) < 300)
console.log('Attempted before 300 ms', moment().diff(lastRequestMade));
// Make a request
lastRequestMade = moment();
console.log(`Request with ${requestId} made !!`);
}
There are some requests that are made in less than 300 seconds. I delay each request using setTimeout
and have kept the multiplying factor equal to the current queue length.