'nodejs avoid continuously api call [duplicate]
I have scheduler that calls api urls every minute (totally 3 api urls) the problem is instead of calling 3 urls every minute it calls those 3 urls continuously and so i could end up calling those 3 urls 50 times or more each minute.
My question is how to avoid those extra calls?
My code sample: commented for better understanding
// adding sleep between api calls
function sleep(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
// call for apis every minutes
cron.schedule("* */1 * * * *", () => {
// total of 3 url addresses (so every minute call 3 urls)
addresses.forEach(async (address) => {
await sleep(3000);
await showTransactionMessage(id, userName, address);
});
});
// get api data and call message function to send message
async function showTransactionMessage(id, userName, address) {
await axios.get(address).then(async (response) => {
if ( response.data.result && Array.isArray( response.data.result ) ) {
response.data.result.map(async (item) => {
//start
const start = async () => {
await asyncForEach(
time = new Date(parseInt(item.timeStamp * 1000)).toLocaleString().split(", ")[1],
date = new Date(parseInt(item.timeStamp * 1000)).toISOString().slice(0, 10).split('-').join('/'),
timestamp = item.timeStamp,
hash = item.hash,
from = item.from,
to = item.to,
value = item.value.toString().slice(0, '-' + item.tokenDecimal),
userName,
async (response) => {
bot.sendMessage(id, response, keyboard);
});
console.log('Done');
};
await sleep(6000); //every 6 seconds send 1 message
start();
//end
});
console.log('address: ', address); // sample result, below
} else {
console.log('Got issue with response array.');
}
}).catch((err) => {
console.log('error1', err)
});
};
// send message by api data provided from `showTransactionMessage` fiunction
async function asyncForEach(time, date, timestamp, hash, from, to, value, userName, callback) {
let response = "";
response += 'Date: '+date+'\n';
response += 'Time: '+time+'\n';
response += 'TX: '+hash+'\n';
response += 'Receiver: '+to+'\n';
await callback(response);
}
What I end up with code above is
address: address 1
address: address 3
address: address 1
address: address 2
address: address 2
address: address 3
address: address 1
address: address 3
address: address 2
address: address 1
address: address 1
Instead of
address: address 1
address: address 2
address: address 3
Any suggestions?
Solution 1:[1]
From what I know, forEach wouldn't wait on an async function and just simply runs it..
try using for(...){await ...} so maybe it might solve the problem
// adding sleep between api calls
function sleep(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
// call for apis every minutes
cron.schedule("* */1 * * * *", async() => {
// total of 3 url addresses (so every minute call 3 urls)
for (let address of addresses) {
await sleep(3000);
await showTransactionMessage(id, userName, address);
}
});
// get api data and call message function to send message
async function showTransactionMessage(id, userName, address) {
//because if you're not waiting, what's the point of showTransactionMessage being async?
try{var response = await axios.get(address);} //var scope perfect for this
catch(err){return console.log('error1', err);} //return because no further action if this fails
if ( response.data.result && Array.isArray( response.data.result ) ) {
for (let item of response.data.result) {
//start
const start = async () => {
await asyncForEach(
time = new Date(parseInt(item.timeStamp * 1000)).toLocaleString().split(", ")[1],
date = new Date(parseInt(item.timeStamp * 1000)).toISOString().slice(0, 10).split('-').join('/'),
timestamp = item.timeStamp,
hash = item.hash,
from = item.from,
to = item.to,
value = item.value.toString().slice(0, '-' + item.tokenDecimal),
userName,
async (response) => { //because if you're not waiting, what's the point of callback being async?
await bot.sendMessage(id, response, keyboard);
});
console.log('Done');
};
await sleep(6000); //every 6 seconds send 1 message
await start(); //why don't you wait for start to finish?
//end
}
console.log('address: ', address); // sample result, below
} else {
console.log('Got issue with response array.');
}
};
// send message by api data provided from `showTransactionMessage` function
async function asyncForEach(time, date, timestamp, hash, from, to, value, userName, callback) {
let response = "";
response += 'Date: '+date+'\n';
response += 'Time: '+time+'\n';
response += 'TX: '+hash+'\n';
response += 'Receiver: '+to+'\n';
await callback(response);
}
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | The Bomb Squad |
