@subql/node-ethereum 0.3.1-0 → 0.3.1-2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/README.md +0 -2
  2. package/dist/.tsbuildinfo +1 -1
  3. package/dist/configure/SubqueryProject.js +15 -5
  4. package/dist/configure/SubqueryProject.js.map +1 -1
  5. package/dist/configure/configure.module.js +2 -2
  6. package/dist/configure/configure.module.js.map +1 -1
  7. package/dist/ethereum/api.ethereum.d.ts +1 -0
  8. package/dist/ethereum/api.ethereum.js +28 -0
  9. package/dist/ethereum/api.ethereum.js.map +1 -1
  10. package/dist/ethereum/api.service.ethereum.d.ts +4 -0
  11. package/dist/ethereum/api.service.ethereum.js +16 -1
  12. package/dist/ethereum/api.service.ethereum.js.map +1 -1
  13. package/dist/indexer/blockDispatcher/base-block-dispatcher.d.ts +1 -1
  14. package/dist/indexer/blockDispatcher/base-block-dispatcher.js +3 -1
  15. package/dist/indexer/blockDispatcher/base-block-dispatcher.js.map +1 -1
  16. package/dist/indexer/blockDispatcher/block-dispatcher.service.d.ts +1 -1
  17. package/dist/indexer/blockDispatcher/block-dispatcher.service.js +10 -5
  18. package/dist/indexer/blockDispatcher/block-dispatcher.service.js.map +1 -1
  19. package/dist/indexer/blockDispatcher/worker-block-dispatcher.service.d.ts +1 -1
  20. package/dist/indexer/blockDispatcher/worker-block-dispatcher.service.js +3 -3
  21. package/dist/indexer/blockDispatcher/worker-block-dispatcher.service.js.map +1 -1
  22. package/dist/indexer/dictionary.service.js +7 -2
  23. package/dist/indexer/dictionary.service.js.map +1 -1
  24. package/dist/indexer/ds-processor.service.d.ts +1 -1
  25. package/dist/indexer/ds-processor.service.js +4 -0
  26. package/dist/indexer/ds-processor.service.js.map +1 -1
  27. package/dist/indexer/dynamic-ds.service.js +4 -0
  28. package/dist/indexer/dynamic-ds.service.js.map +1 -1
  29. package/dist/indexer/fetch.module.js +12 -5
  30. package/dist/indexer/fetch.module.js.map +1 -1
  31. package/dist/indexer/fetch.service.d.ts +5 -1
  32. package/dist/indexer/fetch.service.js +71 -22
  33. package/dist/indexer/fetch.service.js.map +1 -1
  34. package/dist/indexer/indexer.manager.d.ts +1 -1
  35. package/dist/indexer/indexer.manager.js +4 -0
  36. package/dist/indexer/indexer.manager.js.map +1 -1
  37. package/dist/indexer/indexer.module.js +4 -6
  38. package/dist/indexer/indexer.module.js.map +1 -1
  39. package/dist/indexer/project.service.d.ts +1 -1
  40. package/dist/indexer/project.service.js +22 -6
  41. package/dist/indexer/project.service.js.map +1 -1
  42. package/dist/indexer/sandbox.service.js +4 -0
  43. package/dist/indexer/sandbox.service.js.map +1 -1
  44. package/dist/indexer/worker/worker.js +1 -1
  45. package/dist/indexer/worker/worker.js.map +1 -1
  46. package/dist/subcommands/forceClean.service.d.ts +3 -1
  47. package/dist/subcommands/forceClean.service.js +26 -6
  48. package/dist/subcommands/forceClean.service.js.map +1 -1
  49. package/dist/subcommands/reindex.module.js.map +1 -1
  50. package/dist/subcommands/reindex.service.js +6 -1
  51. package/dist/subcommands/reindex.service.js.map +1 -1
  52. package/dist/utils/project.d.ts +1 -0
  53. package/dist/utils/project.js +5 -1
  54. package/dist/utils/project.js.map +1 -1
  55. package/dist/yargs.d.ts +1 -7
  56. package/dist/yargs.js +1 -6
  57. package/dist/yargs.js.map +1 -1
  58. package/package.json +7 -7
@@ -1 +1 @@
1
- {"version":3,"file":"worker-block-dispatcher.service.js","sourceRoot":"","sources":["../../../src/indexer/blockDispatcher/worker-block-dispatcher.service.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2020-2021 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport assert from 'assert';\nimport path from 'path';\nimport { Injectable, OnApplicationShutdown } from '@nestjs/common';\nimport { EventEmitter2 } from '@nestjs/event-emitter';\nimport { Interval } from '@nestjs/schedule';\nimport {\n getLogger,\n NodeConfig,\n IndexerEvent,\n Worker,\n AutoQueue,\n} from '@subql/node-core';\nimport chalk from 'chalk';\nimport { last } from 'lodash';\nimport { ProjectService } from '../project.service';\nimport {\n FetchBlock,\n ProcessBlock,\n InitWorker,\n NumFetchedBlocks,\n NumFetchingBlocks,\n GetWorkerStatus,\n} from '../worker/worker';\nimport { BaseBlockDispatcher } from './base-block-dispatcher';\n\nconst logger = getLogger('WorkerBlockDispatcherService');\n\ntype IIndexerWorker = {\n processBlock: ProcessBlock;\n fetchBlock: FetchBlock;\n numFetchedBlocks: NumFetchedBlocks;\n numFetchingBlocks: NumFetchingBlocks;\n getStatus: GetWorkerStatus;\n};\n\ntype IInitIndexerWorker = IIndexerWorker & {\n initWorker: InitWorker;\n};\n\ntype IndexerWorker = IIndexerWorker & {\n terminate: () => Promise<number>;\n};\n\nasync function createIndexerWorker(): Promise<IndexerWorker> {\n const indexerWorker = Worker.create<IInitIndexerWorker>(\n path.resolve(__dirname, '../../../dist/indexer/worker/worker.js'),\n [\n 'initWorker',\n 'processBlock',\n 'fetchBlock',\n 'numFetchedBlocks',\n 'numFetchingBlocks',\n 'getStatus',\n ],\n );\n\n await indexerWorker.initWorker();\n\n return indexerWorker;\n}\n\n@Injectable()\nexport class WorkerBlockDispatcherService\n extends BaseBlockDispatcher<AutoQueue<void>>\n implements OnApplicationShutdown\n{\n private workers: IndexerWorker[];\n private numWorkers: number;\n\n private taskCounter = 0;\n private isShutdown = false;\n\n constructor(\n nodeConfig: NodeConfig,\n eventEmitter: EventEmitter2,\n projectService: ProjectService,\n ) {\n const numWorkers = nodeConfig.workers;\n super(\n nodeConfig,\n eventEmitter,\n projectService,\n new AutoQueue(numWorkers * nodeConfig.batchSize * 2),\n );\n this.numWorkers = numWorkers;\n }\n\n async init(\n onDynamicDsCreated: (height: number) => Promise<void>,\n ): Promise<void> {\n if (this.nodeConfig.unfinalizedBlocks) {\n throw new Error(\n 'Sorry, best block feature is not supported with workers yet.',\n );\n }\n\n this.workers = await Promise.all(\n new Array(this.numWorkers).fill(0).map(() => createIndexerWorker()),\n );\n\n this.onDynamicDsCreated = onDynamicDsCreated;\n\n const blockAmount = await this.projectService.getProcessedBlockCount();\n this.setProcessedBlockCount(blockAmount ?? 0);\n }\n\n async onApplicationShutdown(): Promise<void> {\n this.isShutdown = true;\n // Stop processing blocks\n this.queue.abort();\n\n // Stop all workers\n if (this.workers) {\n await Promise.all(this.workers.map((w) => w.terminate()));\n }\n }\n\n enqueueBlocks(heights: number[]): void {\n if (!heights.length) return;\n logger.info(\n `Enqueing blocks [${heights[0]}...${last(heights)}], total ${\n heights.length\n } blocks`,\n );\n\n // eslint-disable-next-line no-constant-condition\n if (true) {\n /*\n * Load balancing:\n * worker1: 1,2,3\n * worker2: 4,5,6\n */\n const workerIdx = this.getNextWorkerIndex();\n heights.map((height) => this.enqueueBlock(height, workerIdx));\n } else {\n /*\n * Load balancing:\n * worker1: 1,3,5\n * worker2: 2,4,6\n */\n heights.map((height) =>\n this.enqueueBlock(height, this.getNextWorkerIndex()),\n );\n }\n\n this.latestBufferedHeight = last(heights);\n }\n\n private enqueueBlock(height: number, workerIdx: number) {\n if (this.isShutdown) return;\n const worker = this.workers[workerIdx];\n\n assert(worker, `Worker ${workerIdx} not found`);\n\n // Used to compare before and after as a way to check if queue was flushed\n const bufferedHeight = this.latestBufferedHeight;\n const pendingBlock = worker.fetchBlock(height);\n\n const processBlock = async () => {\n try {\n const start = new Date();\n const result = await pendingBlock;\n const end = new Date();\n\n if (bufferedHeight > this.latestBufferedHeight) {\n logger.debug(`Queue was reset for new DS, discarding fetched blocks`);\n return;\n }\n\n const waitTime = end.getTime() - start.getTime();\n if (waitTime > 1000) {\n logger.info(\n `Waiting to fetch block ${height}: ${chalk.red(`${waitTime}ms`)}`,\n );\n } else if (waitTime > 200) {\n logger.info(\n `Waiting to fetch block ${height}: ${chalk.yellow(\n `${waitTime}ms`,\n )}`,\n );\n }\n\n // logger.info(\n // `worker ${workerIdx} processing block ${height}, fetched blocks: ${await worker.numFetchedBlocks()}, fetching blocks: ${await worker.numFetchingBlocks()}`,\n // );\n\n this.preProcessBlock(height);\n\n const { dynamicDsCreated, operationHash, reindexBlockHeight } =\n await worker.processBlock(height);\n\n await this.postProcessBlock(height, {\n dynamicDsCreated,\n operationHash: Buffer.from(operationHash, 'base64'),\n reindexBlockHeight,\n });\n } catch (e) {\n logger.error(\n e,\n `failed to index block at height ${height} ${\n e.handler ? `${e.handler}(${e.stack ?? ''})` : ''\n }`,\n );\n throw e;\n }\n };\n\n void this.queue.put(processBlock);\n }\n\n @Interval(15000)\n async sampleWorkerStatus(): Promise<void> {\n for (const worker of this.workers) {\n const status = await worker.getStatus();\n logger.info(JSON.stringify(status));\n }\n }\n\n // Getter doesn't seem to cary from abstract class\n get latestBufferedHeight(): number {\n return this._latestBufferedHeight;\n }\n\n set latestBufferedHeight(height: number) {\n super.latestBufferedHeight = height;\n // There is only a single queue with workers so we treat them as the same\n this.eventEmitter.emit(IndexerEvent.BlockQueueSize, {\n value: this.queueSize,\n });\n }\n\n private getNextWorkerIndex(): number {\n const index = this.taskCounter % this.numWorkers;\n\n this.taskCounter++;\n\n return index;\n }\n}\n"]}
1
+ {"version":3,"file":"worker-block-dispatcher.service.js","sourceRoot":"","sources":["../../../src/indexer/blockDispatcher/worker-block-dispatcher.service.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2020-2021 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport assert from 'assert';\nimport path from 'path';\nimport { Injectable, OnApplicationShutdown } from '@nestjs/common';\nimport { EventEmitter2 } from '@nestjs/event-emitter';\nimport { Interval } from '@nestjs/schedule';\nimport {\n getLogger,\n NodeConfig,\n IndexerEvent,\n Worker,\n AutoQueue,\n} from '@subql/node-core';\nimport chalk from 'chalk';\nimport { last } from 'lodash';\nimport { ProjectService } from '../project.service';\nimport {\n FetchBlock,\n ProcessBlock,\n InitWorker,\n NumFetchedBlocks,\n NumFetchingBlocks,\n GetWorkerStatus,\n} from '../worker/worker';\nimport { BaseBlockDispatcher } from './base-block-dispatcher';\n\nconst logger = getLogger('WorkerBlockDispatcherService');\n\ntype IIndexerWorker = {\n processBlock: ProcessBlock;\n fetchBlock: FetchBlock;\n numFetchedBlocks: NumFetchedBlocks;\n numFetchingBlocks: NumFetchingBlocks;\n getStatus: GetWorkerStatus;\n};\n\ntype IInitIndexerWorker = IIndexerWorker & {\n initWorker: InitWorker;\n};\n\ntype IndexerWorker = IIndexerWorker & {\n terminate: () => Promise<number>;\n};\n\nasync function createIndexerWorker(): Promise<IndexerWorker> {\n const indexerWorker = Worker.create<IInitIndexerWorker>(\n path.resolve(__dirname, '../../../dist/indexer/worker/worker.js'),\n [\n 'initWorker',\n 'processBlock',\n 'fetchBlock',\n 'numFetchedBlocks',\n 'numFetchingBlocks',\n 'getStatus',\n ],\n );\n\n await indexerWorker.initWorker();\n\n return indexerWorker;\n}\n\n@Injectable()\nexport class WorkerBlockDispatcherService\n extends BaseBlockDispatcher<AutoQueue<void>>\n implements OnApplicationShutdown\n{\n private workers: IndexerWorker[];\n private numWorkers: number;\n\n private taskCounter = 0;\n private isShutdown = false;\n\n constructor(\n nodeConfig: NodeConfig,\n eventEmitter: EventEmitter2,\n projectService: ProjectService,\n ) {\n const numWorkers = nodeConfig.workers;\n super(\n nodeConfig,\n eventEmitter,\n projectService,\n new AutoQueue(numWorkers * nodeConfig.batchSize * 2),\n );\n this.numWorkers = numWorkers;\n }\n\n async init(\n onDynamicDsCreated: (height: number) => Promise<void>,\n ): Promise<void> {\n if (this.nodeConfig.unfinalizedBlocks) {\n throw new Error(\n 'Sorry, best block feature is not supported with workers yet.',\n );\n }\n\n this.workers = await Promise.all(\n new Array(this.numWorkers).fill(0).map(() => createIndexerWorker()),\n );\n\n this.onDynamicDsCreated = onDynamicDsCreated;\n\n const blockAmount = await this.projectService.getProcessedBlockCount();\n this.setProcessedBlockCount(blockAmount ?? 0);\n }\n\n async onApplicationShutdown(): Promise<void> {\n this.isShutdown = true;\n // Stop processing blocks\n this.queue.abort();\n\n // Stop all workers\n if (this.workers) {\n await Promise.all(this.workers.map((w) => w.terminate()));\n }\n }\n\n enqueueBlocks(heights: number[], latestBufferHeight?: number): void {\n if (!heights.length) return;\n logger.info(\n `Enqueing blocks [${heights[0]}...${last(heights)}], total ${\n heights.length\n } blocks`,\n );\n\n // eslint-disable-next-line no-constant-condition\n if (true) {\n /*\n * Load balancing:\n * worker1: 1,2,3\n * worker2: 4,5,6\n */\n const workerIdx = this.getNextWorkerIndex();\n heights.map((height) => this.enqueueBlock(height, workerIdx));\n } else {\n /*\n * Load balancing:\n * worker1: 1,3,5\n * worker2: 2,4,6\n */\n heights.map((height) =>\n this.enqueueBlock(height, this.getNextWorkerIndex()),\n );\n }\n\n this.latestBufferedHeight = latestBufferHeight ?? last(heights);\n }\n\n private enqueueBlock(height: number, workerIdx: number) {\n if (this.isShutdown) return;\n const worker = this.workers[workerIdx];\n\n assert(worker, `Worker ${workerIdx} not found`);\n\n // Used to compare before and after as a way to check if queue was flushed\n const bufferedHeight = this.latestBufferedHeight;\n const pendingBlock = worker.fetchBlock(height);\n\n const processBlock = async () => {\n try {\n const start = new Date();\n const result = await pendingBlock;\n const end = new Date();\n\n if (bufferedHeight > this.latestBufferedHeight) {\n logger.debug(`Queue was reset for new DS, discarding fetched blocks`);\n return;\n }\n\n const waitTime = end.getTime() - start.getTime();\n if (waitTime > 1000) {\n logger.info(\n `Waiting to fetch block ${height}: ${chalk.red(`${waitTime}ms`)}`,\n );\n } else if (waitTime > 200) {\n logger.info(\n `Waiting to fetch block ${height}: ${chalk.yellow(\n `${waitTime}ms`,\n )}`,\n );\n }\n\n // logger.info(\n // `worker ${workerIdx} processing block ${height}, fetched blocks: ${await worker.numFetchedBlocks()}, fetching blocks: ${await worker.numFetchingBlocks()}`,\n // );\n\n this.preProcessBlock(height);\n\n const { dynamicDsCreated, operationHash, reindexBlockHeight } =\n await worker.processBlock(height);\n\n await this.postProcessBlock(height, {\n dynamicDsCreated,\n operationHash: Buffer.from(operationHash, 'base64'),\n reindexBlockHeight,\n });\n } catch (e) {\n logger.error(\n e,\n `failed to index block at height ${height} ${\n e.handler ? `${e.handler}(${e.stack ?? ''})` : ''\n }`,\n );\n process.exit(1);\n }\n };\n\n void this.queue.put(processBlock);\n }\n\n @Interval(15000)\n async sampleWorkerStatus(): Promise<void> {\n for (const worker of this.workers) {\n const status = await worker.getStatus();\n logger.info(JSON.stringify(status));\n }\n }\n\n // Getter doesn't seem to cary from abstract class\n get latestBufferedHeight(): number {\n return this._latestBufferedHeight;\n }\n\n set latestBufferedHeight(height: number) {\n super.latestBufferedHeight = height;\n // There is only a single queue with workers so we treat them as the same\n this.eventEmitter.emit(IndexerEvent.BlockQueueSize, {\n value: this.queueSize,\n });\n }\n\n private getNextWorkerIndex(): number {\n const index = this.taskCounter % this.numWorkers;\n\n this.taskCounter++;\n\n return index;\n }\n}\n"]}
@@ -10,6 +10,9 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
10
10
  var __metadata = (this && this.__metadata) || function (k, v) {
11
11
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
12
12
  };
13
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
14
+ return function (target, key) { decorator(target, key, paramIndex); }
15
+ };
13
16
  Object.defineProperty(exports, "__esModule", { value: true });
14
17
  exports.DictionaryService = void 0;
15
18
  const core_1 = require("@apollo/client/core");
@@ -19,7 +22,7 @@ const SubqueryProject_1 = require("../configure/SubqueryProject");
19
22
  const logger = (0, node_core_1.getLogger)('dictionary');
20
23
  let DictionaryService = class DictionaryService extends node_core_1.DictionaryService {
21
24
  constructor(project, nodeConfig) {
22
- super(project.network.dictionary, nodeConfig);
25
+ super(project.network.dictionary, project.network.chainId, nodeConfig);
23
26
  this.project = project;
24
27
  }
25
28
  async getEvmChainId() {
@@ -38,7 +41,9 @@ let DictionaryService = class DictionaryService extends node_core_1.DictionarySe
38
41
  };
39
42
  DictionaryService = __decorate([
40
43
  (0, common_1.Injectable)(),
41
- __metadata("design:paramtypes", [SubqueryProject_1.SubqueryProject, node_core_1.NodeConfig])
44
+ __param(0, (0, common_1.Inject)('ISubqueryProject')),
45
+ __metadata("design:paramtypes", [SubqueryProject_1.SubqueryProject,
46
+ node_core_1.NodeConfig])
42
47
  ], DictionaryService);
43
48
  exports.DictionaryService = DictionaryService;
44
49
  //# sourceMappingURL=dictionary.service.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"dictionary.service.js","sourceRoot":"","sources":["../../src/indexer/dictionary.service.ts"],"names":[],"mappings":";AAAA,gEAAgE;AAChE,sCAAsC;;;;;;;;;;;;AAEtC,8CAA0C;AAC1C,2CAAmE;AACnE,gDAK0B;AAC1B,kEAA+D;AAE/D,MAAM,MAAM,GAAG,IAAA,qBAAS,EAAC,YAAY,CAAC,CAAC;AAGhC,IAAM,iBAAiB,GAAvB,MAAM,iBACX,SAAQ,6BAAqB;IAG7B,YAAsB,OAAwB,EAAE,UAAsB;QACpE,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,UAAU,EAAE,UAAU,CAAC,CAAC;QAD1B,YAAO,GAAP,OAAO,CAAiB;IAE9C,CAAC;IAED,KAAK,CAAC,aAAa;QACjB,MAAM,KAAK,GAAG,4CAA4C,CAAC;QAE3D,IAAI;YACF,MAAM,IAAI,GAAG,MAAM,IAAA,mBAAO,EACxB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC;gBAChB,KAAK,EAAE,IAAA,UAAG,EAAC,KAAK,CAAC;aAClB,CAAC,EACF,IAAI,CAAC,UAAU,CAAC,iBAAiB,CAClC,CAAC;YACF,OAAO,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,KAAK,CAAC;SACnC;QAAC,OAAO,CAAC,EAAE;YACV,MAAM,CAAC,IAAI,CAAC,CAAC,EAAE,6CAA6C,CAAC,CAAC;YAC9D,OAAO,SAAS,CAAC;SAClB;IACH,CAAC;CACF,CAAA;AAxBY,iBAAiB;IAD7B,IAAA,mBAAU,GAAE;qCAKoB,iCAAe,EAAc,sBAAU;GAJ3D,iBAAiB,CAwB7B;AAxBY,8CAAiB","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport { gql } from '@apollo/client/core';\nimport { Injectable, OnApplicationShutdown } from '@nestjs/common';\nimport {\n NodeConfig,\n DictionaryService as CoreDictionaryService,\n timeout,\n getLogger,\n} from '@subql/node-core';\nimport { SubqueryProject } from '../configure/SubqueryProject';\n\nconst logger = getLogger('dictionary');\n\n@Injectable()\nexport class DictionaryService\n extends CoreDictionaryService\n implements OnApplicationShutdown\n{\n constructor(protected project: SubqueryProject, nodeConfig: NodeConfig) {\n super(project.network.dictionary, nodeConfig);\n }\n\n async getEvmChainId(): Promise<string> {\n const query = `query{chainAlias(id: \"evmChainId\"){value}}`;\n\n try {\n const resp = await timeout(\n this.client.query({\n query: gql(query),\n }),\n this.nodeConfig.dictionaryTimeout,\n );\n return resp.data.chainAlias.value;\n } catch (e) {\n logger.warn(e, `failed to fetch evm chainId from dictionary`);\n return undefined;\n }\n }\n}\n"]}
1
+ {"version":3,"file":"dictionary.service.js","sourceRoot":"","sources":["../../src/indexer/dictionary.service.ts"],"names":[],"mappings":";AAAA,gEAAgE;AAChE,sCAAsC;;;;;;;;;;;;;;;AAEtC,8CAA0C;AAC1C,2CAA2E;AAC3E,gDAK0B;AAC1B,kEAA+D;AAE/D,MAAM,MAAM,GAAG,IAAA,qBAAS,EAAC,YAAY,CAAC,CAAC;AAGhC,IAAM,iBAAiB,GAAvB,MAAM,iBACX,SAAQ,6BAAqB;IAG7B,YACwC,OAAwB,EAC9D,UAAsB;QAEtB,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,UAAU,EAAE,OAAO,CAAC,OAAO,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC;QAHjC,YAAO,GAAP,OAAO,CAAiB;IAIhE,CAAC;IAED,KAAK,CAAC,aAAa;QACjB,MAAM,KAAK,GAAG,4CAA4C,CAAC;QAE3D,IAAI;YACF,MAAM,IAAI,GAAG,MAAM,IAAA,mBAAO,EACxB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC;gBAChB,KAAK,EAAE,IAAA,UAAG,EAAC,KAAK,CAAC;aAClB,CAAC,EACF,IAAI,CAAC,UAAU,CAAC,iBAAiB,CAClC,CAAC;YACF,OAAO,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,KAAK,CAAC;SACnC;QAAC,OAAO,CAAC,EAAE;YACV,MAAM,CAAC,IAAI,CAAC,CAAC,EAAE,6CAA6C,CAAC,CAAC;YAC9D,OAAO,SAAS,CAAC;SAClB;IACH,CAAC;CACF,CAAA;AA3BY,iBAAiB;IAD7B,IAAA,mBAAU,GAAE;IAMR,WAAA,IAAA,eAAM,EAAC,kBAAkB,CAAC,CAAA;qCAAoB,iCAAe;QAClD,sBAAU;GANb,iBAAiB,CA2B7B;AA3BY,8CAAiB","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport { gql } from '@apollo/client/core';\nimport { Inject, Injectable, OnApplicationShutdown } from '@nestjs/common';\nimport {\n NodeConfig,\n DictionaryService as CoreDictionaryService,\n timeout,\n getLogger,\n} from '@subql/node-core';\nimport { SubqueryProject } from '../configure/SubqueryProject';\n\nconst logger = getLogger('dictionary');\n\n@Injectable()\nexport class DictionaryService\n extends CoreDictionaryService\n implements OnApplicationShutdown\n{\n constructor(\n @Inject('ISubqueryProject') protected project: SubqueryProject,\n nodeConfig: NodeConfig,\n ) {\n super(project.network.dictionary, project.network.chainId, nodeConfig);\n }\n\n async getEvmChainId(): Promise<string> {\n const query = `query{chainAlias(id: \"evmChainId\"){value}}`;\n\n try {\n const resp = await timeout(\n this.client.query({\n query: gql(query),\n }),\n this.nodeConfig.dictionaryTimeout,\n );\n return resp.data.chainAlias.value;\n } catch (e) {\n logger.warn(e, `failed to fetch evm chainId from dictionary`);\n return undefined;\n }\n }\n}\n"]}
@@ -15,7 +15,7 @@ export declare class DsPluginSandbox extends Sandbox {
15
15
  getDsPlugin<D extends string>(): SubqlDatasourceProcessor<D, unknown>;
16
16
  }
17
17
  export declare class DsProcessorService {
18
- private project;
18
+ private readonly project;
19
19
  private readonly nodeConfig;
20
20
  private processorCache;
21
21
  constructor(project: SubqueryProject, nodeConfig: NodeConfig);
@@ -10,6 +10,9 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
10
10
  var __metadata = (this && this.__metadata) || function (k, v) {
11
11
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
12
12
  };
13
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
14
+ return function (target, key) { decorator(target, key, paramIndex); }
15
+ };
13
16
  var __importDefault = (this && this.__importDefault) || function (mod) {
14
17
  return (mod && mod.__esModule) ? mod : { "default": mod };
15
18
  };
@@ -126,6 +129,7 @@ let DsProcessorService = class DsProcessorService {
126
129
  };
127
130
  DsProcessorService = __decorate([
128
131
  (0, common_1.Injectable)(),
132
+ __param(0, (0, common_1.Inject)('ISubqueryProject')),
129
133
  __metadata("design:paramtypes", [SubqueryProject_1.SubqueryProject,
130
134
  node_core_1.NodeConfig])
131
135
  ], DsProcessorService);
@@ -1 +1 @@
1
- {"version":3,"file":"ds-processor.service.js","sourceRoot":"","sources":["../../src/indexer/ds-processor.service.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport fs from 'fs';\nimport path from 'path';\nimport { Injectable } from '@nestjs/common';\nimport {\n EthereumHandlerKind,\n isCustomDs,\n SubqlEthereumCustomDataSource,\n SubqlEthereumDataSource,\n SubqlDatasourceProcessor,\n} from '@subql/common-ethereum';\nimport { getLogger, NodeConfig, Sandbox } from '@subql/node-core';\nimport {\n SecondLayerHandlerProcessor_0_0_0,\n SecondLayerHandlerProcessor_1_0_0,\n SubqlCustomDatasource,\n} from '@subql/types-ethereum';\n\nimport { VMScript } from 'vm2';\nimport { SubqueryProject } from '../configure/SubqueryProject';\n\nexport interface DsPluginSandboxOption {\n root: string;\n entry: string;\n script: string;\n}\n\nconst logger = getLogger('ds-sandbox');\n\nexport function isSecondLayerHandlerProcessor_0_0_0<\n K extends EthereumHandlerKind,\n F,\n E,\n DS extends SubqlCustomDatasource = SubqlEthereumCustomDataSource,\n>(\n processor:\n | SecondLayerHandlerProcessor_0_0_0<K, F, E, DS>\n | SecondLayerHandlerProcessor_1_0_0<K, F, E, DS>,\n): processor is SecondLayerHandlerProcessor_0_0_0<K, F, E, DS> {\n // Exisiting datasource processors had no concept of specVersion, therefore undefined is equivalent to 0.0.0\n return processor.specVersion === undefined;\n}\n\nexport function isSecondLayerHandlerProcessor_1_0_0<\n K extends EthereumHandlerKind,\n F,\n E,\n DS extends SubqlEthereumCustomDataSource = SubqlEthereumCustomDataSource,\n>(\n processor:\n | SecondLayerHandlerProcessor_0_0_0<K, F, E, DS>\n | SecondLayerHandlerProcessor_1_0_0<K, F, E, DS>,\n): processor is SecondLayerHandlerProcessor_1_0_0<K, F, E, DS> {\n return processor.specVersion === '1.0.0';\n}\n\nexport function asSecondLayerHandlerProcessor_1_0_0<\n K extends EthereumHandlerKind,\n F,\n E,\n DS extends SubqlEthereumCustomDataSource = SubqlEthereumCustomDataSource,\n>(\n processor:\n | SecondLayerHandlerProcessor_0_0_0<K, F, E, DS>\n | SecondLayerHandlerProcessor_1_0_0<K, F, E, DS>,\n): SecondLayerHandlerProcessor_1_0_0<K, F, E, DS> {\n if (isSecondLayerHandlerProcessor_1_0_0(processor)) {\n return processor;\n }\n\n if (!isSecondLayerHandlerProcessor_0_0_0(processor)) {\n throw new Error('Unsupported ds processor version');\n }\n\n return {\n ...processor,\n specVersion: '1.0.0',\n filterProcessor: (params) =>\n processor.filterProcessor(params.filter, params.input, params.ds),\n transformer: (params) =>\n processor\n .transformer(params.input, params.ds, params.api, params.assets)\n .then((res) => [res]),\n };\n}\n\nexport class DsPluginSandbox extends Sandbox {\n constructor(option: DsPluginSandboxOption, nodeConfig: NodeConfig) {\n super(\n option,\n new VMScript(\n `module.exports = require('${option.entry}').default;`,\n path.join(option.root, 'ds_sandbox'),\n ),\n nodeConfig,\n );\n this.freeze(logger, 'logger');\n }\n\n getDsPlugin<D extends string>(): SubqlDatasourceProcessor<D, unknown> {\n return this.run(this.script);\n }\n}\n\n@Injectable()\nexport class DsProcessorService {\n private processorCache: {\n [entry: string]: SubqlDatasourceProcessor<string, unknown>;\n } = {};\n constructor(\n private project: SubqueryProject,\n private readonly nodeConfig: NodeConfig,\n ) {}\n\n async validateCustomDs(\n datasources: SubqlEthereumCustomDataSource[],\n ): Promise<void> {\n for (const ds of datasources) {\n const processor = this.getDsProcessor(ds);\n /* Standard validation applicable to all custom ds and processors */\n if (ds.kind !== processor.kind) {\n throw new Error(\n `ds kind (${ds.kind}) doesnt match processor (${processor.kind})`,\n );\n }\n\n for (const handler of ds.mapping.handlers) {\n if (!(handler.kind in processor.handlerProcessors)) {\n throw new Error(\n `ds kind ${handler.kind} not one of ${Object.keys(\n processor.handlerProcessors,\n ).join(', ')}`,\n );\n }\n }\n\n ds.mapping.handlers.map((handler) =>\n processor.handlerProcessors[handler.kind].filterValidator(\n handler.filter,\n ),\n );\n\n /* Additional processor specific validation */\n processor.validate(ds, await this.getAssets(ds));\n }\n }\n\n async validateProjectCustomDatasources(): Promise<void> {\n await this.validateCustomDs(\n (this.project.dataSources as SubqlEthereumDataSource[]).filter(\n isCustomDs,\n ),\n );\n }\n\n getDsProcessor<D extends string>(\n ds: SubqlEthereumCustomDataSource<string>,\n ): SubqlDatasourceProcessor<D, unknown> {\n if (!isCustomDs(ds)) {\n throw new Error(`data source is not a custom data source`);\n }\n if (!this.processorCache[ds.processor.file]) {\n const sandbox = new DsPluginSandbox(\n {\n root: this.project.root,\n entry: ds.processor.file,\n script:\n null /* TODO get working with Readers, same as with sandbox */,\n },\n this.nodeConfig,\n );\n try {\n this.processorCache[ds.processor.file] = sandbox.getDsPlugin<D>();\n } catch (e) {\n logger.error(`not supported ds @${ds.kind}`);\n throw e;\n }\n }\n return this.processorCache[\n ds.processor.file\n ] as unknown as SubqlDatasourceProcessor<D, unknown>;\n }\n\n // eslint-disable-next-line @typescript-eslint/require-await\n async getAssets(\n ds: SubqlEthereumCustomDataSource,\n ): Promise<Record<string, string>> {\n if (!isCustomDs(ds)) {\n throw new Error(`data source is not a custom data source`);\n }\n\n if (!ds.assets) {\n return {};\n }\n\n const res: Record<string, string> = {};\n\n for (const [name, { file }] of ds.assets) {\n // TODO update with https://github.com/subquery/subql/pull/511\n try {\n res[name] = fs.readFileSync(file, {\n encoding: 'utf8',\n });\n } catch (e) {\n logger.error(`Failed to load datasource asset ${file}`);\n throw e;\n }\n }\n\n return res;\n }\n}\n"]}
1
+ {"version":3,"file":"ds-processor.service.js","sourceRoot":"","sources":["../../src/indexer/ds-processor.service.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport fs from 'fs';\nimport path from 'path';\nimport { Inject, Injectable } from '@nestjs/common';\nimport {\n EthereumHandlerKind,\n isCustomDs,\n SubqlEthereumCustomDataSource,\n SubqlEthereumDataSource,\n SubqlDatasourceProcessor,\n} from '@subql/common-ethereum';\nimport { getLogger, NodeConfig, Sandbox } from '@subql/node-core';\nimport {\n SecondLayerHandlerProcessor_0_0_0,\n SecondLayerHandlerProcessor_1_0_0,\n SubqlCustomDatasource,\n} from '@subql/types-ethereum';\n\nimport { VMScript } from 'vm2';\nimport { SubqueryProject } from '../configure/SubqueryProject';\n\nexport interface DsPluginSandboxOption {\n root: string;\n entry: string;\n script: string;\n}\n\nconst logger = getLogger('ds-sandbox');\n\nexport function isSecondLayerHandlerProcessor_0_0_0<\n K extends EthereumHandlerKind,\n F,\n E,\n DS extends SubqlCustomDatasource = SubqlEthereumCustomDataSource,\n>(\n processor:\n | SecondLayerHandlerProcessor_0_0_0<K, F, E, DS>\n | SecondLayerHandlerProcessor_1_0_0<K, F, E, DS>,\n): processor is SecondLayerHandlerProcessor_0_0_0<K, F, E, DS> {\n // Exisiting datasource processors had no concept of specVersion, therefore undefined is equivalent to 0.0.0\n return processor.specVersion === undefined;\n}\n\nexport function isSecondLayerHandlerProcessor_1_0_0<\n K extends EthereumHandlerKind,\n F,\n E,\n DS extends SubqlEthereumCustomDataSource = SubqlEthereumCustomDataSource,\n>(\n processor:\n | SecondLayerHandlerProcessor_0_0_0<K, F, E, DS>\n | SecondLayerHandlerProcessor_1_0_0<K, F, E, DS>,\n): processor is SecondLayerHandlerProcessor_1_0_0<K, F, E, DS> {\n return processor.specVersion === '1.0.0';\n}\n\nexport function asSecondLayerHandlerProcessor_1_0_0<\n K extends EthereumHandlerKind,\n F,\n E,\n DS extends SubqlEthereumCustomDataSource = SubqlEthereumCustomDataSource,\n>(\n processor:\n | SecondLayerHandlerProcessor_0_0_0<K, F, E, DS>\n | SecondLayerHandlerProcessor_1_0_0<K, F, E, DS>,\n): SecondLayerHandlerProcessor_1_0_0<K, F, E, DS> {\n if (isSecondLayerHandlerProcessor_1_0_0(processor)) {\n return processor;\n }\n\n if (!isSecondLayerHandlerProcessor_0_0_0(processor)) {\n throw new Error('Unsupported ds processor version');\n }\n\n return {\n ...processor,\n specVersion: '1.0.0',\n filterProcessor: (params) =>\n processor.filterProcessor(params.filter, params.input, params.ds),\n transformer: (params) =>\n processor\n .transformer(params.input, params.ds, params.api, params.assets)\n .then((res) => [res]),\n };\n}\n\nexport class DsPluginSandbox extends Sandbox {\n constructor(option: DsPluginSandboxOption, nodeConfig: NodeConfig) {\n super(\n option,\n new VMScript(\n `module.exports = require('${option.entry}').default;`,\n path.join(option.root, 'ds_sandbox'),\n ),\n nodeConfig,\n );\n this.freeze(logger, 'logger');\n }\n\n getDsPlugin<D extends string>(): SubqlDatasourceProcessor<D, unknown> {\n return this.run(this.script);\n }\n}\n\n@Injectable()\nexport class DsProcessorService {\n private processorCache: {\n [entry: string]: SubqlDatasourceProcessor<string, unknown>;\n } = {};\n constructor(\n @Inject('ISubqueryProject') private readonly project: SubqueryProject,\n private readonly nodeConfig: NodeConfig,\n ) {}\n\n async validateCustomDs(\n datasources: SubqlEthereumCustomDataSource[],\n ): Promise<void> {\n for (const ds of datasources) {\n const processor = this.getDsProcessor(ds);\n /* Standard validation applicable to all custom ds and processors */\n if (ds.kind !== processor.kind) {\n throw new Error(\n `ds kind (${ds.kind}) doesnt match processor (${processor.kind})`,\n );\n }\n\n for (const handler of ds.mapping.handlers) {\n if (!(handler.kind in processor.handlerProcessors)) {\n throw new Error(\n `ds kind ${handler.kind} not one of ${Object.keys(\n processor.handlerProcessors,\n ).join(', ')}`,\n );\n }\n }\n\n ds.mapping.handlers.map((handler) =>\n processor.handlerProcessors[handler.kind].filterValidator(\n handler.filter,\n ),\n );\n\n /* Additional processor specific validation */\n processor.validate(ds, await this.getAssets(ds));\n }\n }\n\n async validateProjectCustomDatasources(): Promise<void> {\n await this.validateCustomDs(\n (this.project.dataSources as SubqlEthereumDataSource[]).filter(\n isCustomDs,\n ),\n );\n }\n\n getDsProcessor<D extends string>(\n ds: SubqlEthereumCustomDataSource<string>,\n ): SubqlDatasourceProcessor<D, unknown> {\n if (!isCustomDs(ds)) {\n throw new Error(`data source is not a custom data source`);\n }\n if (!this.processorCache[ds.processor.file]) {\n const sandbox = new DsPluginSandbox(\n {\n root: this.project.root,\n entry: ds.processor.file,\n script:\n null /* TODO get working with Readers, same as with sandbox */,\n },\n this.nodeConfig,\n );\n try {\n this.processorCache[ds.processor.file] = sandbox.getDsPlugin<D>();\n } catch (e) {\n logger.error(`not supported ds @${ds.kind}`);\n throw e;\n }\n }\n return this.processorCache[\n ds.processor.file\n ] as unknown as SubqlDatasourceProcessor<D, unknown>;\n }\n\n // eslint-disable-next-line @typescript-eslint/require-await\n async getAssets(\n ds: SubqlEthereumCustomDataSource,\n ): Promise<Record<string, string>> {\n if (!isCustomDs(ds)) {\n throw new Error(`data source is not a custom data source`);\n }\n\n if (!ds.assets) {\n return {};\n }\n\n const res: Record<string, string> = {};\n\n for (const [name, { file }] of ds.assets) {\n // TODO update with https://github.com/subquery/subql/pull/511\n try {\n res[name] = fs.readFileSync(file, {\n encoding: 'utf8',\n });\n } catch (e) {\n logger.error(`Failed to load datasource asset ${file}`);\n throw e;\n }\n }\n\n return res;\n }\n}\n"]}
@@ -10,6 +10,9 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
10
10
  var __metadata = (this && this.__metadata) || function (k, v) {
11
11
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
12
12
  };
13
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
14
+ return function (target, key) { decorator(target, key, paramIndex); }
15
+ };
13
16
  var __importDefault = (this && this.__importDefault) || function (mod) {
14
17
  return (mod && mod.__esModule) ? mod : { "default": mod };
15
18
  };
@@ -124,6 +127,7 @@ let DynamicDsService = class DynamicDsService {
124
127
  };
125
128
  DynamicDsService = __decorate([
126
129
  (0, common_1.Injectable)(),
130
+ __param(1, (0, common_1.Inject)('ISubqueryProject')),
127
131
  __metadata("design:paramtypes", [ds_processor_service_1.DsProcessorService,
128
132
  SubqueryProject_1.SubqueryProject])
129
133
  ], DynamicDsService);
@@ -1 +1 @@
1
- {"version":3,"file":"dynamic-ds.service.js","sourceRoot":"","sources":["../../src/indexer/dynamic-ds.service.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport assert from 'assert';\nimport { Injectable } from '@nestjs/common';\nimport { isCustomDs, isRuntimeDs } from '@subql/common-ethereum';\nimport { getLogger, MetadataRepo } from '@subql/node-core';\nimport { cloneDeep, isEqual, unionWith } from 'lodash';\nimport { Transaction } from 'sequelize/types';\nimport { SubqlProjectDs, SubqueryProject } from '../configure/SubqueryProject';\nimport { DsProcessorService } from './ds-processor.service';\n\nconst logger = getLogger('dynamic-ds');\n\nconst METADATA_KEY = 'dynamicDatasources';\nconst TEMP_DS_PREFIX = 'ds_';\n\ninterface DatasourceParams {\n templateName: string;\n args?: Record<string, unknown>;\n startBlock: number;\n}\n\n@Injectable()\nexport class DynamicDsService {\n private metaDataRepo: MetadataRepo;\n private tempDsRecords: Record<string, string>;\n\n constructor(\n private readonly dsProcessorService: DsProcessorService,\n private readonly project: SubqueryProject,\n ) {}\n\n init(metaDataRepo: MetadataRepo): void {\n this.metaDataRepo = metaDataRepo;\n }\n\n private _datasources: SubqlProjectDs[];\n\n async resetDynamicDatasource(targetHeight: number, tx: Transaction) {\n const dynamicDs = await this.getDynamicDatasourceParams();\n if (dynamicDs.length !== 0) {\n const filteredDs = dynamicDs.filter(\n (ds) => ds.startBlock <= targetHeight,\n );\n const dsRecords = JSON.stringify(filteredDs);\n await this.metaDataRepo.upsert(\n { key: METADATA_KEY, value: dsRecords },\n { transaction: tx },\n );\n }\n }\n\n async createDynamicDatasource(\n params: DatasourceParams,\n tx: Transaction,\n ): Promise<SubqlProjectDs> {\n try {\n const ds = await this.getDatasource(params);\n\n await this.saveDynamicDatasourceParams(params, tx);\n\n logger.info(\n `Created new dynamic datasource from template: \"${params.templateName}\"`,\n );\n\n if (!this._datasources) this._datasources = [];\n this._datasources.push(ds);\n\n return ds;\n } catch (e) {\n logger.error(e.message);\n process.exit(1);\n }\n }\n\n async getDynamicDatasources(): Promise<SubqlProjectDs[]> {\n if (!this._datasources) {\n try {\n const params = await this.getDynamicDatasourceParams();\n\n this._datasources = await Promise.all(\n params.map((params) => this.getDatasource(params)),\n );\n } catch (e) {\n logger.error(`Unable to get dynamic datasources:\\n${e.message}`);\n process.exit(1);\n }\n }\n\n return this._datasources;\n }\n\n deleteTempDsRecords(blockHeight: number) {\n delete this.tempDsRecords[TEMP_DS_PREFIX + blockHeight];\n }\n\n private async getDynamicDatasourceParams(\n blockHeight?: number,\n ): Promise<DatasourceParams[]> {\n assert(this.metaDataRepo, `Model _metadata does not exist`);\n const record = await this.metaDataRepo.findByPk(METADATA_KEY);\n\n let results: DatasourceParams[] = [];\n\n const metaResults: DatasourceParams[] = JSON.parse(\n (record?.value as string) ?? '[]',\n );\n if (metaResults.length) {\n results = [...metaResults];\n }\n\n if (blockHeight !== undefined) {\n const tempResults: DatasourceParams[] = JSON.parse(\n this.tempDsRecords?.[TEMP_DS_PREFIX + blockHeight] ?? '[]',\n );\n if (tempResults.length) {\n results = unionWith(results, tempResults, isEqual);\n }\n }\n\n return results;\n }\n\n private async saveDynamicDatasourceParams(\n dsParams: DatasourceParams,\n tx: Transaction,\n ): Promise<void> {\n const existing = await this.getDynamicDatasourceParams(dsParams.startBlock);\n\n assert(this.metaDataRepo, `Model _metadata does not exist`);\n const dsRecords = JSON.stringify([...existing, dsParams]);\n await this.metaDataRepo\n .upsert({ key: METADATA_KEY, value: dsRecords }, { transaction: tx })\n .then(() => {\n this.tempDsRecords = {\n ...this.tempDsRecords,\n [TEMP_DS_PREFIX + dsParams.startBlock]: dsRecords,\n };\n });\n }\n\n private async getDatasource(\n params: DatasourceParams,\n ): Promise<SubqlProjectDs> {\n const template = cloneDeep(\n this.project.templates.find((t) => t.name === params.templateName),\n );\n\n if (!template) {\n throw new Error(\n `Unable to find matching template in project for name: \"${params.templateName}\"`,\n );\n }\n\n logger.info(\n `Initialised dynamic datasource from template: \"${params.templateName}\"`,\n );\n\n const dsObj = {\n ...template,\n startBlock: params.startBlock,\n } as SubqlProjectDs;\n delete dsObj.name;\n try {\n if (isCustomDs(dsObj)) {\n dsObj.processor.options = {\n ...dsObj.processor.options,\n ...params.args,\n };\n await this.dsProcessorService.validateCustomDs([dsObj]);\n } else if (isRuntimeDs(dsObj)) {\n // XXX add any modifications to the ds here\n }\n\n return dsObj;\n } catch (e) {\n throw new Error(`Unable to create dynamic datasource.\\n ${e.message}`);\n }\n }\n}\n"]}
1
+ {"version":3,"file":"dynamic-ds.service.js","sourceRoot":"","sources":["../../src/indexer/dynamic-ds.service.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport assert from 'assert';\nimport { Inject, Injectable } from '@nestjs/common';\nimport { isCustomDs, isRuntimeDs } from '@subql/common-ethereum';\nimport { getLogger, MetadataRepo } from '@subql/node-core';\nimport { cloneDeep, isEqual, unionWith } from 'lodash';\nimport { Transaction } from 'sequelize/types';\nimport { SubqlProjectDs, SubqueryProject } from '../configure/SubqueryProject';\nimport { DsProcessorService } from './ds-processor.service';\n\nconst logger = getLogger('dynamic-ds');\n\nconst METADATA_KEY = 'dynamicDatasources';\nconst TEMP_DS_PREFIX = 'ds_';\n\ninterface DatasourceParams {\n templateName: string;\n args?: Record<string, unknown>;\n startBlock: number;\n}\n\n@Injectable()\nexport class DynamicDsService {\n private metaDataRepo: MetadataRepo;\n private tempDsRecords: Record<string, string>;\n\n constructor(\n private readonly dsProcessorService: DsProcessorService,\n @Inject('ISubqueryProject') private readonly project: SubqueryProject,\n ) {}\n\n init(metaDataRepo: MetadataRepo): void {\n this.metaDataRepo = metaDataRepo;\n }\n\n private _datasources: SubqlProjectDs[];\n\n async resetDynamicDatasource(targetHeight: number, tx: Transaction) {\n const dynamicDs = await this.getDynamicDatasourceParams();\n if (dynamicDs.length !== 0) {\n const filteredDs = dynamicDs.filter(\n (ds) => ds.startBlock <= targetHeight,\n );\n const dsRecords = JSON.stringify(filteredDs);\n await this.metaDataRepo.upsert(\n { key: METADATA_KEY, value: dsRecords },\n { transaction: tx },\n );\n }\n }\n\n async createDynamicDatasource(\n params: DatasourceParams,\n tx: Transaction,\n ): Promise<SubqlProjectDs> {\n try {\n const ds = await this.getDatasource(params);\n\n await this.saveDynamicDatasourceParams(params, tx);\n\n logger.info(\n `Created new dynamic datasource from template: \"${params.templateName}\"`,\n );\n\n if (!this._datasources) this._datasources = [];\n this._datasources.push(ds);\n\n return ds;\n } catch (e) {\n logger.error(e.message);\n process.exit(1);\n }\n }\n\n async getDynamicDatasources(): Promise<SubqlProjectDs[]> {\n if (!this._datasources) {\n try {\n const params = await this.getDynamicDatasourceParams();\n\n this._datasources = await Promise.all(\n params.map((params) => this.getDatasource(params)),\n );\n } catch (e) {\n logger.error(`Unable to get dynamic datasources:\\n${e.message}`);\n process.exit(1);\n }\n }\n\n return this._datasources;\n }\n\n deleteTempDsRecords(blockHeight: number) {\n delete this.tempDsRecords[TEMP_DS_PREFIX + blockHeight];\n }\n\n private async getDynamicDatasourceParams(\n blockHeight?: number,\n ): Promise<DatasourceParams[]> {\n assert(this.metaDataRepo, `Model _metadata does not exist`);\n const record = await this.metaDataRepo.findByPk(METADATA_KEY);\n\n let results: DatasourceParams[] = [];\n\n const metaResults: DatasourceParams[] = JSON.parse(\n (record?.value as string) ?? '[]',\n );\n if (metaResults.length) {\n results = [...metaResults];\n }\n\n if (blockHeight !== undefined) {\n const tempResults: DatasourceParams[] = JSON.parse(\n this.tempDsRecords?.[TEMP_DS_PREFIX + blockHeight] ?? '[]',\n );\n if (tempResults.length) {\n results = unionWith(results, tempResults, isEqual);\n }\n }\n\n return results;\n }\n\n private async saveDynamicDatasourceParams(\n dsParams: DatasourceParams,\n tx: Transaction,\n ): Promise<void> {\n const existing = await this.getDynamicDatasourceParams(dsParams.startBlock);\n\n assert(this.metaDataRepo, `Model _metadata does not exist`);\n const dsRecords = JSON.stringify([...existing, dsParams]);\n await this.metaDataRepo\n .upsert({ key: METADATA_KEY, value: dsRecords }, { transaction: tx })\n .then(() => {\n this.tempDsRecords = {\n ...this.tempDsRecords,\n [TEMP_DS_PREFIX + dsParams.startBlock]: dsRecords,\n };\n });\n }\n\n private async getDatasource(\n params: DatasourceParams,\n ): Promise<SubqlProjectDs> {\n const template = cloneDeep(\n this.project.templates.find((t) => t.name === params.templateName),\n );\n\n if (!template) {\n throw new Error(\n `Unable to find matching template in project for name: \"${params.templateName}\"`,\n );\n }\n\n logger.info(\n `Initialised dynamic datasource from template: \"${params.templateName}\"`,\n );\n\n const dsObj = {\n ...template,\n startBlock: params.startBlock,\n } as SubqlProjectDs;\n delete dsObj.name;\n try {\n if (isCustomDs(dsObj)) {\n dsObj.processor.options = {\n ...dsObj.processor.options,\n ...params.args,\n };\n await this.dsProcessorService.validateCustomDs([dsObj]);\n } else if (isRuntimeDs(dsObj)) {\n // XXX add any modifications to the ds here\n }\n\n return dsObj;\n } catch (e) {\n throw new Error(`Unable to create dynamic datasource.\\n ${e.message}`);\n }\n }\n}\n"]}
@@ -12,7 +12,6 @@ exports.FetchModule = void 0;
12
12
  const common_1 = require("@nestjs/common");
13
13
  const event_emitter_1 = require("@nestjs/event-emitter");
14
14
  const node_core_1 = require("@subql/node-core");
15
- const SubqueryProject_1 = require("../configure/SubqueryProject");
16
15
  const api_service_ethereum_1 = require("../ethereum/api.service.ethereum");
17
16
  const blockDispatcher_1 = require("./blockDispatcher");
18
17
  const dictionary_service_1 = require("./dictionary.service");
@@ -31,12 +30,12 @@ FetchModule = __decorate([
31
30
  node_core_1.StoreService,
32
31
  {
33
32
  provide: node_core_1.ApiService,
34
- useFactory: async (project) => {
35
- const apiService = new api_service_ethereum_1.EthereumApiService(project);
33
+ useFactory: async (project, eventEmitter) => {
34
+ const apiService = new api_service_ethereum_1.EthereumApiService(project, eventEmitter);
36
35
  await apiService.init();
37
36
  return apiService;
38
37
  },
39
- inject: [SubqueryProject_1.SubqueryProject],
38
+ inject: ['ISubqueryProject', event_emitter_1.EventEmitter2],
40
39
  },
41
40
  indexer_manager_1.IndexerManager,
42
41
  {
@@ -54,7 +53,15 @@ FetchModule = __decorate([
54
53
  },
55
54
  fetch_service_1.FetchService,
56
55
  node_core_1.BenchmarkService,
57
- dictionary_service_1.DictionaryService,
56
+ {
57
+ provide: dictionary_service_1.DictionaryService,
58
+ useFactory: async (project, nodeConfig) => {
59
+ const dictionaryService = new dictionary_service_1.DictionaryService(project, nodeConfig);
60
+ await dictionaryService.init();
61
+ return dictionaryService;
62
+ },
63
+ inject: ['ISubqueryProject', node_core_1.NodeConfig],
64
+ },
58
65
  sandbox_service_1.SandboxService,
59
66
  ds_processor_service_1.DsProcessorService,
60
67
  dynamic_ds_service_1.DynamicDsService,
@@ -1 +1 @@
1
- {"version":3,"file":"fetch.module.js","sourceRoot":"","sources":["../../src/indexer/fetch.module.ts"],"names":[],"mappings":";AAAA,gEAAgE;AAChE,sCAAsC;;;;;;;;;AAEtC,2CAAwC;AACxC,yDAAsD;AACtD,gDAO0B;AAC1B,kEAA+D;AAC/D,2EAAsE;AACtE,uDAG2B;AAC3B,6DAAyD;AACzD,iEAA4D;AAC5D,6DAAwD;AACxD,mDAA+C;AAC/C,uDAAmD;AACnD,uDAAmD;AACnD,uDAAmD;AACnD,2EAAuE;AA2DhE,IAAM,WAAW,GAAjB,MAAM,WAAW;CAAG,CAAA;AAAd,WAAW;IAzDvB,IAAA,eAAM,EAAC;QACN,SAAS,EAAE;YACT,wBAAY;YACZ;gBACE,OAAO,EAAE,sBAAU;gBACnB,UAAU,EAAE,KAAK,EAAE,OAAwB,EAAE,EAAE;oBAC7C,MAAM,UAAU,GAAG,IAAI,yCAAkB,CAAC,OAAO,CAAC,CAAC;oBAEnD,MAAM,UAAU,CAAC,IAAI,EAAE,CAAC;oBACxB,OAAO,UAAU,CAAC;gBACpB,CAAC;gBACD,MAAM,EAAE,CAAC,iCAAe,CAAC;aAC1B;YACD,gCAAc;YACd;gBACE,OAAO,EAAE,kBAAkB;gBAC3B,UAAU,EAAE,CACV,UAAsB,EACtB,YAA2B,EAC3B,cAA8B,EAC9B,UAAsB,EACtB,cAA8B,EAC9B,EAAE,CACF,UAAU,CAAC,OAAO,KAAK,SAAS;oBAC9B,CAAC,CAAC,IAAI,8CAA4B,CAC9B,UAAU,EACV,YAAY,EACZ,cAAc,CACf;oBACH,CAAC,CAAC,IAAI,wCAAsB,CACxB,UAAU,EACV,UAAU,EACV,cAAc,EACd,YAAY,EACZ,cAAc,CACf;gBACP,MAAM,EAAE;oBACN,sBAAU;oBACV,6BAAa;oBACb,gCAAc;oBACd,sBAAU;oBACV,gCAAc;iBACf;aACF;YACD,4BAAY;YACZ,4BAAgB;YAChB,sCAAiB;YACjB,gCAAc;YACd,yCAAkB;YAClB,qCAAgB;YAChB,sBAAU;YACV,sBAAU;YACV,gCAAc;YACd,oDAAwB;SACzB;QACD,OAAO,EAAE,CAAC,wBAAY,EAAE,sBAAU,CAAC;KACpC,CAAC;GACW,WAAW,CAAG;AAAd,kCAAW","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport { Module } from '@nestjs/common';\nimport { EventEmitter2 } from '@nestjs/event-emitter';\nimport {\n BenchmarkService,\n MmrService,\n StoreService,\n PoiService,\n ApiService,\n NodeConfig,\n} from '@subql/node-core';\nimport { SubqueryProject } from '../configure/SubqueryProject';\nimport { EthereumApiService } from '../ethereum/api.service.ethereum';\nimport {\n BlockDispatcherService,\n WorkerBlockDispatcherService,\n} from './blockDispatcher';\nimport { DictionaryService } from './dictionary.service';\nimport { DsProcessorService } from './ds-processor.service';\nimport { DynamicDsService } from './dynamic-ds.service';\nimport { FetchService } from './fetch.service';\nimport { IndexerManager } from './indexer.manager';\nimport { ProjectService } from './project.service';\nimport { SandboxService } from './sandbox.service';\nimport { UnfinalizedBlocksService } from './unfinalizedBlocks.service';\n\n@Module({\n providers: [\n StoreService,\n {\n provide: ApiService,\n useFactory: async (project: SubqueryProject) => {\n const apiService = new EthereumApiService(project);\n\n await apiService.init();\n return apiService;\n },\n inject: [SubqueryProject],\n },\n IndexerManager,\n {\n provide: 'IBlockDispatcher',\n useFactory: (\n nodeConfig: NodeConfig,\n eventEmitter: EventEmitter2,\n projectService: ProjectService,\n apiService: ApiService,\n indexerManager: IndexerManager,\n ) =>\n nodeConfig.workers !== undefined\n ? new WorkerBlockDispatcherService(\n nodeConfig,\n eventEmitter,\n projectService,\n )\n : new BlockDispatcherService(\n apiService,\n nodeConfig,\n indexerManager,\n eventEmitter,\n projectService,\n ),\n inject: [\n NodeConfig,\n EventEmitter2,\n ProjectService,\n ApiService,\n IndexerManager,\n ],\n },\n FetchService,\n BenchmarkService,\n DictionaryService,\n SandboxService,\n DsProcessorService,\n DynamicDsService,\n PoiService,\n MmrService,\n ProjectService,\n UnfinalizedBlocksService,\n ],\n exports: [StoreService, MmrService],\n})\nexport class FetchModule {}\n"]}
1
+ {"version":3,"file":"fetch.module.js","sourceRoot":"","sources":["../../src/indexer/fetch.module.ts"],"names":[],"mappings":";AAAA,gEAAgE;AAChE,sCAAsC;;;;;;;;;AAEtC,2CAAwC;AACxC,yDAAsD;AACtD,gDAO0B;AAE1B,2EAAsE;AACtE,uDAG2B;AAC3B,6DAAyD;AACzD,iEAA4D;AAC5D,6DAAwD;AACxD,mDAA+C;AAC/C,uDAAmD;AACnD,uDAAmD;AACnD,uDAAmD;AACnD,2EAAuE;AAqEhE,IAAM,WAAW,GAAjB,MAAM,WAAW;CAAG,CAAA;AAAd,WAAW;IAnEvB,IAAA,eAAM,EAAC;QACN,SAAS,EAAE;YACT,wBAAY;YACZ;gBACE,OAAO,EAAE,sBAAU;gBACnB,UAAU,EAAE,KAAK,EACf,OAAwB,EACxB,YAA2B,EAC3B,EAAE;oBACF,MAAM,UAAU,GAAG,IAAI,yCAAkB,CAAC,OAAO,EAAE,YAAY,CAAC,CAAC;oBACjE,MAAM,UAAU,CAAC,IAAI,EAAE,CAAC;oBACxB,OAAO,UAAU,CAAC;gBACpB,CAAC;gBACD,MAAM,EAAE,CAAC,kBAAkB,EAAE,6BAAa,CAAC;aAC5C;YACD,gCAAc;YACd;gBACE,OAAO,EAAE,kBAAkB;gBAC3B,UAAU,EAAE,CACV,UAAsB,EACtB,YAA2B,EAC3B,cAA8B,EAC9B,UAAsB,EACtB,cAA8B,EAC9B,EAAE,CACF,UAAU,CAAC,OAAO,KAAK,SAAS;oBAC9B,CAAC,CAAC,IAAI,8CAA4B,CAC9B,UAAU,EACV,YAAY,EACZ,cAAc,CACf;oBACH,CAAC,CAAC,IAAI,wCAAsB,CACxB,UAAU,EACV,UAAU,EACV,cAAc,EACd,YAAY,EACZ,cAAc,CACf;gBACP,MAAM,EAAE;oBACN,sBAAU;oBACV,6BAAa;oBACb,gCAAc;oBACd,sBAAU;oBACV,gCAAc;iBACf;aACF;YACD,4BAAY;YACZ,4BAAgB;YAChB;gBACE,OAAO,EAAE,sCAAiB;gBAC1B,UAAU,EAAE,KAAK,EAAE,OAAwB,EAAE,UAAsB,EAAE,EAAE;oBACrE,MAAM,iBAAiB,GAAG,IAAI,sCAAiB,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC;oBACrE,MAAM,iBAAiB,CAAC,IAAI,EAAE,CAAC;oBAC/B,OAAO,iBAAiB,CAAC;gBAC3B,CAAC;gBACD,MAAM,EAAE,CAAC,kBAAkB,EAAE,sBAAU,CAAC;aACzC;YACD,gCAAc;YACd,yCAAkB;YAClB,qCAAgB;YAChB,sBAAU;YACV,sBAAU;YACV,gCAAc;YACd,oDAAwB;SACzB;QACD,OAAO,EAAE,CAAC,wBAAY,EAAE,sBAAU,CAAC;KACpC,CAAC;GACW,WAAW,CAAG;AAAd,kCAAW","sourcesContent":["// Copyright 2020-2022 OnFinality Limited authors & contributors\n// SPDX-License-Identifier: Apache-2.0\n\nimport { Module } from '@nestjs/common';\nimport { EventEmitter2 } from '@nestjs/event-emitter';\nimport {\n BenchmarkService,\n MmrService,\n StoreService,\n PoiService,\n ApiService,\n NodeConfig,\n} from '@subql/node-core';\nimport { SubqueryProject } from '../configure/SubqueryProject';\nimport { EthereumApiService } from '../ethereum/api.service.ethereum';\nimport {\n BlockDispatcherService,\n WorkerBlockDispatcherService,\n} from './blockDispatcher';\nimport { DictionaryService } from './dictionary.service';\nimport { DsProcessorService } from './ds-processor.service';\nimport { DynamicDsService } from './dynamic-ds.service';\nimport { FetchService } from './fetch.service';\nimport { IndexerManager } from './indexer.manager';\nimport { ProjectService } from './project.service';\nimport { SandboxService } from './sandbox.service';\nimport { UnfinalizedBlocksService } from './unfinalizedBlocks.service';\n\n@Module({\n providers: [\n StoreService,\n {\n provide: ApiService,\n useFactory: async (\n project: SubqueryProject,\n eventEmitter: EventEmitter2,\n ) => {\n const apiService = new EthereumApiService(project, eventEmitter);\n await apiService.init();\n return apiService;\n },\n inject: ['ISubqueryProject', EventEmitter2],\n },\n IndexerManager,\n {\n provide: 'IBlockDispatcher',\n useFactory: (\n nodeConfig: NodeConfig,\n eventEmitter: EventEmitter2,\n projectService: ProjectService,\n apiService: ApiService,\n indexerManager: IndexerManager,\n ) =>\n nodeConfig.workers !== undefined\n ? new WorkerBlockDispatcherService(\n nodeConfig,\n eventEmitter,\n projectService,\n )\n : new BlockDispatcherService(\n apiService,\n nodeConfig,\n indexerManager,\n eventEmitter,\n projectService,\n ),\n inject: [\n NodeConfig,\n EventEmitter2,\n ProjectService,\n ApiService,\n IndexerManager,\n ],\n },\n FetchService,\n BenchmarkService,\n {\n provide: DictionaryService,\n useFactory: async (project: SubqueryProject, nodeConfig: NodeConfig) => {\n const dictionaryService = new DictionaryService(project, nodeConfig);\n await dictionaryService.init();\n return dictionaryService;\n },\n inject: ['ISubqueryProject', NodeConfig],\n },\n SandboxService,\n DsProcessorService,\n DynamicDsService,\n PoiService,\n MmrService,\n ProjectService,\n UnfinalizedBlocksService,\n ],\n exports: [StoreService, MmrService],\n})\nexport class FetchModule {}\n"]}
@@ -21,11 +21,11 @@ export declare class FetchService implements OnApplicationShutdown {
21
21
  private latestBestHeight;
22
22
  private latestFinalizedHeight;
23
23
  private isShutdown;
24
- private dictionaryQueryEntries?;
25
24
  private batchSizeScale;
26
25
  private templateDynamicDatasouces;
27
26
  private dictionaryGenesisMatches;
28
27
  private evmChainId;
28
+ private bypassBlocks;
29
29
  constructor(apiService: ApiService, nodeConfig: NodeConfig, project: SubqueryProject, blockDispatcher: IBlockDispatcher, dictionaryService: DictionaryService, dynamicDsService: DynamicDsService, unfinalizedBlocksService: UnfinalizedBlocksService, eventEmitter: EventEmitter2, schedulerRegistry: SchedulerRegistry);
30
30
  onApplicationShutdown(): void;
31
31
  get api(): ApiWrapper;
@@ -34,6 +34,8 @@ export declare class FetchService implements OnApplicationShutdown {
34
34
  updateDictionary(): void;
35
35
  private get useDictionary();
36
36
  init(startHeight: number): Promise<void>;
37
+ getUseDictionary(): boolean;
38
+ getLatestFinalizedHeight(): number;
37
39
  checkBatchScale(): void;
38
40
  getFinalizedBlockHead(): Promise<void>;
39
41
  getBestBlockHead(): Promise<void>;
@@ -42,6 +44,8 @@ export declare class FetchService implements OnApplicationShutdown {
42
44
  getModuloBlocks(startHeight: number, endHeight: number): number[];
43
45
  getEnqueuedModuloBlocks(startBlockHeight: number): number[];
44
46
  fillNextBlockBuffer(initBlockHeight: number): Promise<void>;
47
+ private getLatestBufferHeight;
48
+ private filteredBlockBatch;
45
49
  private nextEndBlockHeight;
46
50
  private dictionaryValidation;
47
51
  resetForNewDs(blockHeight: number): Promise<void>;
@@ -94,6 +94,7 @@ let FetchService = class FetchService {
94
94
  this.schedulerRegistry = schedulerRegistry;
95
95
  this.isShutdown = false;
96
96
  this.dictionaryGenesisMatches = true;
97
+ this.bypassBlocks = [];
97
98
  this.batchSizeScale = 1;
98
99
  }
99
100
  onApplicationShutdown() {
@@ -164,6 +165,10 @@ let FetchService = class FetchService {
164
165
  !!this.dictionaryService.getDictionaryQueryEntries((_a = this.blockDispatcher.latestBufferedHeight) !== null && _a !== void 0 ? _a : Math.min(...this.project.dataSources.map((ds) => ds.startBlock))).length);
165
166
  }
166
167
  async init(startHeight) {
168
+ var _a;
169
+ if (((_a = this.project.network) === null || _a === void 0 ? void 0 : _a.bypassBlocks) !== undefined) {
170
+ this.bypassBlocks = (0, node_core_1.transformBypassBlocks)(this.project.network.bypassBlocks).filter((blk) => blk >= startHeight);
171
+ }
167
172
  if (this.api) {
168
173
  const CHAIN_INTERVAL = (0, utils_ethereum_1.calcInterval)(this.api) * INTERVAL_PERCENT;
169
174
  BLOCK_TIME_VARIANCE = Math.min(BLOCK_TIME_VARIANCE, CHAIN_INTERVAL);
@@ -179,9 +184,22 @@ let FetchService = class FetchService {
179
184
  }
180
185
  await this.getFinalizedBlockHead();
181
186
  await this.getBestBlockHead();
187
+ // Call metadata here, other network should align with this
188
+ // For substrate, we might use the specVersion metadata in future if we have same error handling as in node-core
189
+ const metadata = await this.dictionaryService.getMetadata();
190
+ const validChecker = this.dictionaryValidation(metadata);
191
+ if (validChecker) {
192
+ this.dictionaryService.setDictionaryStartHeight(metadata._metadata.startHeight);
193
+ }
182
194
  await this.blockDispatcher.init(this.resetForNewDs.bind(this));
183
195
  void this.startLoop(startHeight);
184
196
  }
197
+ getUseDictionary() {
198
+ return this.useDictionary;
199
+ }
200
+ getLatestFinalizedHeight() {
201
+ return this.latestFinalizedHeight;
202
+ }
185
203
  checkBatchScale() {
186
204
  if (this.nodeConfig['scale-batch-size']) {
187
205
  const scale = (0, node_core_1.checkMemoryUsage)(this.batchSizeScale, this.nodeConfig);
@@ -281,6 +299,9 @@ let FetchService = class FetchService {
281
299
  ? this.blockDispatcher.latestBufferedHeight + 1
282
300
  : initBlockHeight;
283
301
  };
302
+ if (this.dictionaryService.startHeight > getStartBlockHeight()) {
303
+ logger.warn(`Dictionary start height ${this.dictionaryService.startHeight} is beyond indexing height ${getStartBlockHeight()}, skipping dictionary for now`);
304
+ }
284
305
  while (!this.isShutdown) {
285
306
  startBlockHeight = getStartBlockHeight();
286
307
  scaledBatchSize = Math.max(Math.round(this.batchSizeScale * this.nodeConfig.batchSize), Math.min(MINIMUM_BATCH_SIZE, this.nodeConfig.batchSize * 3));
@@ -292,7 +313,8 @@ let FetchService = class FetchService {
292
313
  await (0, node_core_1.delay)(1);
293
314
  continue;
294
315
  }
295
- if (this.useDictionary) {
316
+ if (this.useDictionary &&
317
+ startBlockHeight >= this.dictionaryService.startHeight) {
296
318
  const queryEndBlock = startBlockHeight + DICTIONARY_MAX_QUERY_SIZE;
297
319
  const moduloBlocks = this.getModuloBlocks(startBlockHeight, queryEndBlock);
298
320
  try {
@@ -309,12 +331,13 @@ let FetchService = class FetchService {
309
331
  .sort((a, b) => a - b);
310
332
  if (batchBlocks.length === 0) {
311
333
  // There we're no blocks in this query range, we can set a new height we're up to
312
- this.blockDispatcher.latestBufferedHeight = Math.min(queryEndBlock - 1, dictionary._metadata.lastProcessedHeight);
334
+ this.blockDispatcher.enqueueBlocks([], Math.min(queryEndBlock - 1, dictionary._metadata.lastProcessedHeight));
313
335
  }
314
336
  else {
315
337
  const maxBlockSize = Math.min(batchBlocks.length, this.blockDispatcher.freeSize);
316
- batchBlocks = batchBlocks.slice(0, maxBlockSize);
317
- this.blockDispatcher.enqueueBlocks(batchBlocks);
338
+ const enqueuingBlocks = batchBlocks.slice(0, maxBlockSize);
339
+ const cleanedBatchBlocks = this.filteredBlockBatch(enqueuingBlocks);
340
+ this.blockDispatcher.enqueueBlocks(cleanedBatchBlocks, this.getLatestBufferHeight(cleanedBatchBlocks, enqueuingBlocks));
318
341
  }
319
342
  continue; // skip nextBlockRange() way
320
343
  }
@@ -327,13 +350,32 @@ let FetchService = class FetchService {
327
350
  }
328
351
  const endHeight = this.nextEndBlockHeight(startBlockHeight, scaledBatchSize);
329
352
  if (handlers.length && this.getModulos().length === handlers.length) {
330
- this.blockDispatcher.enqueueBlocks(this.getEnqueuedModuloBlocks(startBlockHeight));
353
+ const enqueuingBlocks = this.getEnqueuedModuloBlocks(startBlockHeight);
354
+ const cleanedBatchBlocks = this.filteredBlockBatch(enqueuingBlocks);
355
+ this.blockDispatcher.enqueueBlocks(cleanedBatchBlocks, this.getLatestBufferHeight(cleanedBatchBlocks, enqueuingBlocks));
331
356
  }
332
357
  else {
333
- this.blockDispatcher.enqueueBlocks((0, lodash_1.range)(startBlockHeight, endHeight + 1));
358
+ const enqueuingBlocks = (0, lodash_1.range)(startBlockHeight, endHeight + 1);
359
+ const cleanedBatchBlocks = this.filteredBlockBatch(enqueuingBlocks);
360
+ this.blockDispatcher.enqueueBlocks(cleanedBatchBlocks, this.getLatestBufferHeight(cleanedBatchBlocks, enqueuingBlocks));
334
361
  }
335
362
  }
336
363
  }
364
+ getLatestBufferHeight(cleanedBatchBlocks, rawBatchBlocks) {
365
+ return Math.max(...cleanedBatchBlocks, ...rawBatchBlocks);
366
+ }
367
+ filteredBlockBatch(currentBatchBlocks) {
368
+ if (!this.bypassBlocks.length || !currentBatchBlocks) {
369
+ return currentBatchBlocks;
370
+ }
371
+ const cleanedBatch = (0, node_core_1.cleanedBatchBlocks)(this.bypassBlocks, currentBatchBlocks);
372
+ const pollutedBlocks = this.bypassBlocks.filter((b) => b < Math.max(...currentBatchBlocks));
373
+ if (pollutedBlocks.length) {
374
+ logger.info(`Bypassing blocks: ${pollutedBlocks}`);
375
+ }
376
+ this.bypassBlocks = (0, lodash_1.without)(this.bypassBlocks, ...pollutedBlocks);
377
+ return cleanedBatch;
378
+ }
337
379
  nextEndBlockHeight(startBlockHeight, scaledBatchSize) {
338
380
  let endBlockHeight = startBlockHeight + scaledBatchSize - 1;
339
381
  if (endBlockHeight > this.latestFinalizedHeight) {
@@ -348,23 +390,29 @@ let FetchService = class FetchService {
348
390
  }
349
391
  return endBlockHeight;
350
392
  }
351
- dictionaryValidation({ _metadata: metaData }, startBlockHeight) {
352
- if (metaData.genesisHash !== this.api.getGenesisHash() &&
353
- this.evmChainId !== this.api.getChainId().toString()) {
354
- logger.error('The dictionary that you have specified does not match the chain you are indexing, it will be ignored. Please update your project manifest to reference the correct dictionary');
355
- this.dictionaryGenesisMatches = false;
356
- this.eventEmitter.emit(node_core_1.IndexerEvent.UsingDictionary, {
357
- value: Number(this.useDictionary),
358
- });
359
- this.eventEmitter.emit(node_core_1.IndexerEvent.SkipDictionary);
360
- return false;
361
- }
362
- if (metaData.lastProcessedHeight < startBlockHeight) {
363
- logger.warn(`Dictionary indexed block is behind current indexing block height`);
364
- this.eventEmitter.emit(node_core_1.IndexerEvent.SkipDictionary);
365
- return false;
393
+ dictionaryValidation(dictionary, startBlockHeight) {
394
+ if (dictionary !== undefined) {
395
+ const { _metadata: metaData } = dictionary;
396
+ if (metaData.genesisHash !== this.api.getGenesisHash() &&
397
+ this.evmChainId !== this.api.getChainId().toString()) {
398
+ logger.error('The dictionary that you have specified does not match the chain you are indexing, it will be ignored. Please update your project manifest to reference the correct dictionary');
399
+ this.dictionaryGenesisMatches = false;
400
+ this.eventEmitter.emit(node_core_1.IndexerEvent.UsingDictionary, {
401
+ value: Number(this.useDictionary),
402
+ });
403
+ this.eventEmitter.emit(node_core_1.IndexerEvent.SkipDictionary);
404
+ return false;
405
+ }
406
+ if (startBlockHeight !== undefined) {
407
+ if (metaData.lastProcessedHeight < startBlockHeight) {
408
+ logger.warn(`Dictionary indexed block is behind current indexing block height`);
409
+ this.eventEmitter.emit(node_core_1.IndexerEvent.SkipDictionary);
410
+ return false;
411
+ }
412
+ }
413
+ return true;
366
414
  }
367
- return true;
415
+ return false;
368
416
  }
369
417
  async resetForNewDs(blockHeight) {
370
418
  await this.syncDynamicDatascourcesFromMeta();
@@ -398,6 +446,7 @@ __decorate([
398
446
  ], FetchService.prototype, "getBestBlockHead", null);
399
447
  FetchService = __decorate([
400
448
  (0, common_1.Injectable)(),
449
+ __param(2, (0, common_1.Inject)('ISubqueryProject')),
401
450
  __param(3, (0, common_1.Inject)('IBlockDispatcher')),
402
451
  __metadata("design:paramtypes", [node_core_1.ApiService,
403
452
  node_core_1.NodeConfig,