I use a generator function to consume logs and serve it piece by piece. Furthermore the function preload the next logs once the queue is empty. I now like to extend the preload feature so that the preload is triggered once the log array falls below a threshold of 500 entries. I don’t came up with a good solution that’s why I’m asking for help!
async function* getSwaps(project, fromBlock, toBlock, limit) {
const startBlock = fromBlock;
const endBlock = toBlock;
let logs = [];
let queue = [];
do {
if (!queue.length && toBlock < endBlock) {
if (endBlock > fromBlock + limit) {
toBlock = fromBlock + limit;
} else {
toBlock = endBlock;
}
const promise = project.getSwaps(fromBlock, toBlock);
queue.push(promise);
fromBlock += limit + 1;
}
if (!logs.length && queue.length > 0) {
logs = await queue.shift();
}
yield logs.shift();
} while(logs.length > 0 || fromBlock < endBlock);
}
2
Answers
Made some small adjustments as it's possible that a block range doesn't return data
You don’t really need
queue
. It is enough to know there is an unresolvedpromise
. Also, I would expectpromise
to resolve to an array of data (for blocksfromBlock
totoBlock
), so you shouldn’t doqueue.push(promise)
, but push the values from that promised array (individually) to your array (but that could belogs
).I think you need two concepts of limits:
loadSize
: An indication how many items you will request per call ofproject.getSwaps
lowThreshold
: if the size oflogs
drops below this level, a next batch should be requested with a call toproject.getSwaps
, unless all blocks were already requested.Here is what you could do: