Fetch txs only for blocks having relevant events (#436)

* Fix address filter usage in rpc-eth-client getLogs implementation

* Avoid fetching block txs when no relevant logs exist
This commit is contained in:
prathamesh0 2023-10-25 14:36:03 +05:30 committed by GitHub
parent 07887c160e
commit 320bf02938
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 31 additions and 21 deletions

View File

@ -626,7 +626,7 @@ export class Indexer implements IndexerInterface {
} }
async fetchEventsAndSaveBlocks (blocks: DeepPartial<BlockProgress>[]): Promise<{ blockProgress: BlockProgress, events: DeepPartial<Event>[] }[]> { async fetchEventsAndSaveBlocks (blocks: DeepPartial<BlockProgress>[]): Promise<{ blockProgress: BlockProgress, events: DeepPartial<Event>[] }[]> {
return this._baseIndexer.fetchEventsAndSaveBlocks(blocks, this.parseEventNameAndArgs.bind(this)) return this._baseIndexer.fetchEventsAndSaveBlocks(blocks, this.parseEventNameAndArgs.bind(this));
} }
async saveBlockAndFetchEvents (block: DeepPartial<BlockProgress>): Promise<[BlockProgress, DeepPartial<Event>[]]> { async saveBlockAndFetchEvents (block: DeepPartial<BlockProgress>): Promise<[BlockProgress, DeepPartial<Event>[]]> {

View File

@ -279,7 +279,7 @@ export class EthClient implements EthClientInterface {
let logs = logsByAddress.flat(); let logs = logsByAddress.flat();
// If no addresses provided to filter // If no addresses provided to filter
if (!logs.length) { if (!addresses.length) {
logs = await this._provider.getLogs({ logs = await this._provider.getLogs({
fromBlock, fromBlock,
toBlock toBlock

View File

@ -301,7 +301,7 @@ export class Indexer {
} }
// Fetch logs for block range of given blocks // Fetch logs for block range of given blocks
let logsPromise: Promise<any>; let logs: any;
const fromBlock = blocks[0].blockNumber; const fromBlock = blocks[0].blockNumber;
const toBlock = blocks[blocks.length - 1].blockNumber; const toBlock = blocks[blocks.length - 1].blockNumber;
@ -312,20 +312,43 @@ export class Indexer {
return watchedContract.address; return watchedContract.address;
}); });
logsPromise = this._ethClient.getLogsForBlockRange({ ({ logs } = await this._ethClient.getLogsForBlockRange({
fromBlock, fromBlock,
toBlock, toBlock,
addresses addresses
}); }));
} else { } else {
logsPromise = this._ethClient.getLogsForBlockRange({ fromBlock, toBlock }); ({ logs } = await this._ethClient.getLogsForBlockRange({ fromBlock, toBlock }));
} }
// Skip further processing if no relevant logs found in the entire block range
if (!logs.length) {
return new Map();
}
// Sort logs according to blockhash
const logsMap: Map<string, any> = new Map();
logs.forEach((log: any) => {
const { blockHash: logBlockHash } = log;
assert(typeof logBlockHash === 'string');
if (!logsMap.has(logBlockHash)) {
logsMap.set(logBlockHash, []);
}
logsMap.get(logBlockHash).push(log);
});
// Fetch transactions for given blocks // Fetch transactions for given blocks
const transactionsMap: Map<string, any> = new Map(); const transactionsMap: Map<string, any> = new Map();
const transactionPromises = blocks.map(async (block) => { const transactionPromises = blocks.map(async (block) => {
assert(block.blockHash); assert(block.blockHash);
// Skip fetching txs if no relevant logs found in this block
if (!logsMap.has(block.blockHash)) {
return;
}
const blockWithTransactions = await this._ethClient.getBlockWithTransactions({ blockHash: block.blockHash, blockNumber: block.blockNumber }); const blockWithTransactions = await this._ethClient.getBlockWithTransactions({ blockHash: block.blockHash, blockNumber: block.blockNumber });
const { const {
allEthHeaderCids: { allEthHeaderCids: {
@ -342,20 +365,7 @@ export class Indexer {
transactionsMap.set(block.blockHash, transactions); transactionsMap.set(block.blockHash, transactions);
}); });
const [{ logs }] = await Promise.all([logsPromise, ...transactionPromises]); await Promise.all(transactionPromises);
// Sort logs according to blockhash
const logsMap: Map<string, any> = new Map();
logs.forEach((log: any) => {
const { blockHash: logBlockHash } = log;
assert(typeof logBlockHash === 'string');
if (!logsMap.has(logBlockHash)) {
logsMap.set(logBlockHash, []);
}
logsMap.get(logBlockHash).push(log);
});
// Map db ready events according to blockhash // Map db ready events according to blockhash
const dbEventsMap: Map<string, DeepPartial<EventInterface>[]> = new Map(); const dbEventsMap: Map<string, DeepPartial<EventInterface>[]> = new Map();
@ -364,7 +374,7 @@ export class Indexer {
assert(blockHash); assert(blockHash);
const logs = logsMap.get(blockHash) || []; const logs = logsMap.get(blockHash) || [];
const transactions = transactionsMap.get(blockHash); const transactions = transactionsMap.get(blockHash) || [];
const dbEvents = this.createDbEventsFromLogsAndTxs(blockHash, logs, transactions, parseEventNameAndArgs); const dbEvents = this.createDbEventsFromLogsAndTxs(blockHash, logs, transactions, parseEventNameAndArgs);
dbEventsMap.set(blockHash, dbEvents); dbEventsMap.set(blockHash, dbEvents);