envio 3.3.0-alpha.1 → 3.3.0-alpha.10
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.
- package/evm.schema.json +10 -0
- package/index.d.ts +45 -25
- package/package.json +7 -7
- package/src/Address.res +5 -2
- package/src/Address.res.mjs +3 -1
- package/src/Api.res +1 -1
- package/src/Api.res.mjs +1 -1
- package/src/Batch.res +0 -6
- package/src/Batch.res.mjs +1 -12
- package/src/BatchProcessing.res +7 -12
- package/src/BatchProcessing.res.mjs +8 -7
- package/src/Bin.res +3 -0
- package/src/Bin.res.mjs +4 -0
- package/src/ChainFetching.res +43 -9
- package/src/ChainFetching.res.mjs +34 -15
- package/src/ChainMetadata.res +1 -11
- package/src/ChainMetadata.res.mjs +1 -10
- package/src/ChainState.res +605 -151
- package/src/ChainState.res.mjs +427 -104
- package/src/ChainState.resi +72 -4
- package/src/Config.res +61 -33
- package/src/Config.res.mjs +50 -10
- package/src/ContractRegisterContext.res +2 -12
- package/src/ContractRegisterContext.res.mjs +3 -5
- package/src/Core.res +14 -3
- package/src/CrossChainState.res +113 -89
- package/src/CrossChainState.res.mjs +64 -60
- package/src/CrossChainState.resi +1 -1
- package/src/Ecosystem.res +5 -6
- package/src/Ecosystem.res.mjs +3 -3
- package/src/Envio.res +17 -11
- package/src/EnvioGlobal.res +53 -0
- package/src/EnvioGlobal.res.mjs +31 -0
- package/src/EventConfigBuilder.res +177 -88
- package/src/EventConfigBuilder.res.mjs +99 -42
- package/src/EventProcessing.res +74 -28
- package/src/EventProcessing.res.mjs +55 -29
- package/src/ExitOnCaughtUp.res +10 -2
- package/src/ExitOnCaughtUp.res.mjs +10 -1
- package/src/FetchState.res +544 -356
- package/src/FetchState.res.mjs +412 -471
- package/src/HandlerLoader.res +8 -104
- package/src/HandlerLoader.res.mjs +2 -81
- package/src/HandlerRegister.res +518 -144
- package/src/HandlerRegister.res.mjs +285 -133
- package/src/HandlerRegister.resi +24 -8
- package/src/IndexerState.res +10 -3
- package/src/IndexerState.res.mjs +11 -4
- package/src/IndexerState.resi +2 -1
- package/src/IndexingAddresses.res +108 -0
- package/src/IndexingAddresses.res.mjs +101 -0
- package/src/IndexingAddresses.resi +34 -0
- package/src/Internal.res +155 -46
- package/src/Internal.res.mjs +30 -2
- package/src/LoadLayer.res +5 -5
- package/src/LoadLayer.res.mjs +6 -6
- package/src/LogSelection.res +102 -165
- package/src/LogSelection.res.mjs +101 -116
- package/src/Main.res +71 -236
- package/src/Main.res.mjs +60 -145
- package/src/Metrics.res +74 -0
- package/src/Metrics.res.mjs +75 -0
- package/src/PgStorage.res +4 -4
- package/src/PgStorage.res.mjs +5 -5
- package/src/Prometheus.res +10 -63
- package/src/Prometheus.res.mjs +124 -171
- package/src/PruneStaleHistory.res +2 -2
- package/src/PruneStaleHistory.res.mjs +3 -3
- package/src/RawEvent.res +7 -2
- package/src/RawEvent.res.mjs +4 -4
- package/src/Rollback.res +3 -3
- package/src/Rollback.res.mjs +4 -4
- package/src/RollbackCommit.res +4 -1
- package/src/RollbackCommit.res.mjs +3 -2
- package/src/SimulateDeadInputTracker.res +85 -0
- package/src/SimulateDeadInputTracker.res.mjs +73 -0
- package/src/SimulateDeadInputTracker.resi +12 -0
- package/src/SimulateItems.res +91 -23
- package/src/SimulateItems.res.mjs +55 -32
- package/src/TestIndexer.res +54 -40
- package/src/TestIndexer.res.mjs +37 -30
- package/src/bindings/Performance.res +7 -0
- package/src/bindings/Performance.res.mjs +21 -0
- package/src/bindings/Performance.resi +7 -0
- package/src/bindings/Viem.res +0 -41
- package/src/bindings/Viem.res.mjs +1 -43
- package/src/sources/BlockStore.res +46 -0
- package/src/sources/BlockStore.res.mjs +24 -0
- package/src/sources/EventRouter.res +36 -33
- package/src/sources/EventRouter.res.mjs +13 -14
- package/src/sources/Evm.res +83 -72
- package/src/sources/Evm.res.mjs +53 -69
- package/src/sources/EvmChain.res +18 -20
- package/src/sources/EvmChain.res.mjs +15 -15
- package/src/sources/EvmRpcClient.res +74 -5
- package/src/sources/EvmRpcClient.res.mjs +13 -4
- package/src/sources/FieldMask.res +39 -0
- package/src/sources/FieldMask.res.mjs +42 -0
- package/src/sources/Fuel.res +9 -6
- package/src/sources/Fuel.res.mjs +5 -10
- package/src/sources/HyperFuelSource.res +46 -50
- package/src/sources/HyperFuelSource.res.mjs +64 -54
- package/src/sources/HyperSync.res +39 -7
- package/src/sources/HyperSync.res.mjs +57 -37
- package/src/sources/HyperSync.resi +12 -2
- package/src/sources/HyperSyncClient.res +22 -111
- package/src/sources/HyperSyncClient.res.mjs +2 -30
- package/src/sources/HyperSyncHeightStream.res +1 -8
- package/src/sources/HyperSyncHeightStream.res.mjs +0 -2
- package/src/sources/HyperSyncSource.res +94 -107
- package/src/sources/HyperSyncSource.res.mjs +82 -86
- package/src/sources/Rpc.res +15 -47
- package/src/sources/Rpc.res.mjs +25 -56
- package/src/sources/RpcSource.res +320 -467
- package/src/sources/RpcSource.res.mjs +268 -385
- package/src/sources/RpcWebSocketHeightStream.res +0 -5
- package/src/sources/RpcWebSocketHeightStream.res.mjs +0 -2
- package/src/sources/SimulateSource.res +10 -4
- package/src/sources/SimulateSource.res.mjs +16 -6
- package/src/sources/Source.res +34 -6
- package/src/sources/SourceManager.res +77 -19
- package/src/sources/SourceManager.res.mjs +63 -21
- package/src/sources/SourceManager.resi +10 -0
- package/src/sources/Svm.res +31 -16
- package/src/sources/Svm.res.mjs +36 -13
- package/src/sources/SvmHyperSyncClient.res +5 -32
- package/src/sources/SvmHyperSyncSource.res +159 -134
- package/src/sources/SvmHyperSyncSource.res.mjs +164 -129
- package/src/sources/TransactionStore.res +49 -0
- package/src/sources/TransactionStore.res.mjs +30 -0
- package/src/tui/Tui.res +13 -16
- package/src/tui/Tui.res.mjs +12 -14
- package/svm.schema.json +49 -37
- package/src/bindings/Hrtime.res +0 -58
- package/src/bindings/Hrtime.res.mjs +0 -90
- package/src/bindings/Hrtime.resi +0 -30
|
@@ -7,26 +7,23 @@ type selectionConfig = {
|
|
|
7
7
|
fieldSelection: HyperSyncClient.QueryTypes.fieldSelection,
|
|
8
8
|
}
|
|
9
9
|
|
|
10
|
-
let getSelectionConfig = (selection: FetchState.selection
|
|
10
|
+
let getSelectionConfig = (selection: FetchState.selection) => {
|
|
11
11
|
let capitalizedBlockFields = Utils.Set.make()
|
|
12
12
|
let capitalizedTransactionFields = Utils.Set.make()
|
|
13
13
|
|
|
14
|
-
let
|
|
15
|
-
let
|
|
16
|
-
let dynamicWildcardEventFiltersByContract = Dict.make()
|
|
14
|
+
let topicSelectionsByContract = Dict.make()
|
|
15
|
+
let wildcardTopicSelectionsByContract = Dict.make()
|
|
17
16
|
let noAddressesTopicSelections = []
|
|
18
17
|
let contractNames = Utils.Set.make()
|
|
19
18
|
|
|
20
|
-
selection.
|
|
21
|
-
->(Utils.magic: array<Internal.
|
|
22
|
-
->Array.forEach(
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
selectedBlockFields,
|
|
27
|
-
|
|
28
|
-
isWildcard,
|
|
29
|
-
}) => {
|
|
19
|
+
selection.onEventRegistrations
|
|
20
|
+
->(Utils.magic: array<Internal.onEventRegistration> => array<Internal.evmOnEventRegistration>)
|
|
21
|
+
->Array.forEach(reg => {
|
|
22
|
+
let eventConfig =
|
|
23
|
+
reg.eventConfig->(Utils.magic: Internal.eventConfig => Internal.evmEventConfig)
|
|
24
|
+
let contractName = eventConfig.contractName
|
|
25
|
+
let {selectedBlockFields, selectedTransactionFields} = eventConfig
|
|
26
|
+
let {dependsOnAddresses, resolvedWhere, isWildcard} = reg
|
|
30
27
|
selectedBlockFields
|
|
31
28
|
->Utils.Set.toArray
|
|
32
29
|
->Array.forEach(name =>
|
|
@@ -36,30 +33,26 @@ let getSelectionConfig = (selection: FetchState.selection, ~chain) => {
|
|
|
36
33
|
)
|
|
37
34
|
selectedTransactionFields
|
|
38
35
|
->Utils.Set.toArray
|
|
39
|
-
->Array.forEach(name =>
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
36
|
+
->Array.forEach(name => {
|
|
37
|
+
// transactionIndex is read off the log (the store key), so it never needs
|
|
38
|
+
// to be requested as a transaction column — and requesting it alone would
|
|
39
|
+
// pull the whole transaction table for nothing.
|
|
40
|
+
let fieldName = (name :> string)
|
|
41
|
+
if fieldName != "transactionIndex" {
|
|
42
|
+
capitalizedTransactionFields->Utils.Set.add(fieldName->Utils.String.capitalize)->ignore
|
|
43
|
+
}
|
|
44
|
+
})
|
|
44
45
|
|
|
45
|
-
let eventFilters = getEventFiltersOrThrow(chain)
|
|
46
46
|
if dependsOnAddresses {
|
|
47
47
|
let _ = contractNames->Utils.Set.add(contractName)
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
(
|
|
53
|
-
isWildcard ? dynamicWildcardEventFiltersByContract : dynamicEventFiltersByContract
|
|
54
|
-
)->Utils.Dict.push(contractName, fn)
|
|
55
|
-
}
|
|
48
|
+
|
|
49
|
+
(
|
|
50
|
+
isWildcard ? wildcardTopicSelectionsByContract : topicSelectionsByContract
|
|
51
|
+
)->Utils.Dict.pushMany(contractName, resolvedWhere.topicSelections)
|
|
56
52
|
} else {
|
|
57
53
|
noAddressesTopicSelections
|
|
58
54
|
->Array.pushMany(
|
|
59
|
-
|
|
60
|
-
| Static(s) => s
|
|
61
|
-
| Dynamic(fn) => fn([])
|
|
62
|
-
},
|
|
55
|
+
resolvedWhere.topicSelections->LogSelection.materializeTopicSelections(~addresses=[]),
|
|
63
56
|
)
|
|
64
57
|
->ignore
|
|
65
58
|
}
|
|
@@ -90,27 +83,26 @@ let getSelectionConfig = (selection: FetchState.selection, ~chain) => {
|
|
|
90
83
|
| None
|
|
91
84
|
| Some([]) => ()
|
|
92
85
|
| Some(addresses) =>
|
|
93
|
-
switch
|
|
86
|
+
switch topicSelectionsByContract->Utils.Dict.dangerouslyGetNonOption(contractName) {
|
|
94
87
|
| None => ()
|
|
95
88
|
| Some(topicSelections) =>
|
|
96
|
-
logSelections->Array.push(LogSelection.make(~addresses, ~topicSelections))
|
|
97
|
-
}
|
|
98
|
-
switch dynamicEventFiltersByContract->Utils.Dict.dangerouslyGetNonOption(contractName) {
|
|
99
|
-
| None => ()
|
|
100
|
-
| Some(fns) =>
|
|
101
89
|
logSelections->Array.push(
|
|
102
|
-
LogSelection.make(
|
|
90
|
+
LogSelection.make(
|
|
91
|
+
~addresses,
|
|
92
|
+
~topicSelections=topicSelections->LogSelection.materializeTopicSelections(~addresses),
|
|
93
|
+
),
|
|
103
94
|
)
|
|
104
95
|
}
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
96
|
+
// Wildcard events that filter an indexed param by registered addresses:
|
|
97
|
+
// the addresses fold into the topics, so the query itself stays
|
|
98
|
+
// address-unbound.
|
|
99
|
+
switch wildcardTopicSelectionsByContract->Utils.Dict.dangerouslyGetNonOption(contractName) {
|
|
108
100
|
| None => ()
|
|
109
|
-
| Some(
|
|
101
|
+
| Some(topicSelections) =>
|
|
110
102
|
logSelections->Array.push(
|
|
111
103
|
LogSelection.make(
|
|
112
104
|
~addresses=[],
|
|
113
|
-
~topicSelections=
|
|
105
|
+
~topicSelections=topicSelections->LogSelection.materializeTopicSelections(~addresses),
|
|
114
106
|
),
|
|
115
107
|
)
|
|
116
108
|
}
|
|
@@ -125,8 +117,7 @@ let getSelectionConfig = (selection: FetchState.selection, ~chain) => {
|
|
|
125
117
|
}
|
|
126
118
|
}
|
|
127
119
|
|
|
128
|
-
let memoGetSelectionConfig = (
|
|
129
|
-
Utils.WeakMap.memoize(selection => selection->getSelectionConfig(~chain))
|
|
120
|
+
let memoGetSelectionConfig = () => Utils.WeakMap.memoize(getSelectionConfig)
|
|
130
121
|
|
|
131
122
|
// Surfaced by HyperSyncClient.getHeight (Rust) when HyperSync rejects the API
|
|
132
123
|
// token. The corrupted-token test feeds the real server error through this
|
|
@@ -137,7 +128,7 @@ type options = {
|
|
|
137
128
|
chain: ChainMap.Chain.t,
|
|
138
129
|
endpointUrl: string,
|
|
139
130
|
allEventParams: array<HyperSyncClient.Decoder.eventParamsInput>,
|
|
140
|
-
eventRouter: EventRouter.t<Internal.
|
|
131
|
+
eventRouter: EventRouter.t<Internal.evmOnEventRegistration>,
|
|
141
132
|
apiToken: option<string>,
|
|
142
133
|
clientTimeoutMillis: int,
|
|
143
134
|
lowercaseAddresses: bool,
|
|
@@ -162,7 +153,7 @@ let make = (
|
|
|
162
153
|
): t => {
|
|
163
154
|
let name = "HyperSync"
|
|
164
155
|
|
|
165
|
-
let getSelectionConfig = memoGetSelectionConfig(
|
|
156
|
+
let getSelectionConfig = memoGetSelectionConfig()
|
|
166
157
|
|
|
167
158
|
let apiToken = switch apiToken {
|
|
168
159
|
| Some(token) => token
|
|
@@ -194,27 +185,24 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
194
185
|
let makeEventBatchQueueItem = (
|
|
195
186
|
item: HyperSyncClient.EventItems.item,
|
|
196
187
|
~params: Internal.eventParams,
|
|
197
|
-
~
|
|
188
|
+
~onEventRegistration: Internal.evmOnEventRegistration,
|
|
198
189
|
): Internal.item => {
|
|
199
|
-
let {
|
|
190
|
+
let {transactionIndex, logIndex, srcAddress} = item
|
|
200
191
|
let chainId = chain->ChainMap.Chain.toChainId
|
|
201
192
|
|
|
202
193
|
Internal.Event({
|
|
203
|
-
|
|
204
|
-
timestamp: block.timestamp->Option.getUnsafe,
|
|
194
|
+
onEventRegistration: (onEventRegistration :> Internal.onEventRegistration),
|
|
205
195
|
chain,
|
|
206
|
-
blockNumber:
|
|
207
|
-
blockHash: block.hash->Option.getUnsafe,
|
|
196
|
+
blockNumber: item.blockNumber,
|
|
208
197
|
logIndex,
|
|
198
|
+
transactionIndex,
|
|
199
|
+
// `block` and `transaction` are omitted; they're materialised from the
|
|
200
|
+
// per-chain stores onto the payload at batch prep.
|
|
209
201
|
payload: {
|
|
210
|
-
contractName: eventConfig.contractName,
|
|
211
|
-
eventName: eventConfig.name,
|
|
202
|
+
contractName: onEventRegistration.eventConfig.contractName,
|
|
203
|
+
eventName: onEventRegistration.eventConfig.name,
|
|
212
204
|
chainId,
|
|
213
205
|
params,
|
|
214
|
-
transaction: transaction->(
|
|
215
|
-
Utils.magic: HyperSyncClient.ResponseTypes.transaction => Internal.eventTransaction
|
|
216
|
-
),
|
|
217
|
-
block: block->(Utils.magic: HyperSyncClient.ResponseTypes.block => Internal.eventBlock),
|
|
218
206
|
srcAddress,
|
|
219
207
|
logIndex,
|
|
220
208
|
}->Evm.fromPayload,
|
|
@@ -225,14 +213,15 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
225
213
|
~fromBlock,
|
|
226
214
|
~toBlock,
|
|
227
215
|
~addressesByContractName,
|
|
228
|
-
~
|
|
216
|
+
~contractNameByAddress,
|
|
229
217
|
~knownHeight,
|
|
230
218
|
~partitionId as _,
|
|
231
219
|
~selection,
|
|
220
|
+
~itemsTarget,
|
|
232
221
|
~retry,
|
|
233
222
|
~logger,
|
|
234
223
|
) => {
|
|
235
|
-
let totalTimeRef =
|
|
224
|
+
let totalTimeRef = Performance.now()
|
|
236
225
|
|
|
237
226
|
let selectionConfig = selection->getSelectionConfig
|
|
238
227
|
|
|
@@ -241,20 +230,16 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
241
230
|
exn->ErrorHandling.mkLogAndRaise(~logger, ~msg="Failed getting log selection for the query")
|
|
242
231
|
}
|
|
243
232
|
|
|
244
|
-
let startFetchingBatchTimeRef =
|
|
233
|
+
let startFetchingBatchTimeRef = Performance.now()
|
|
245
234
|
|
|
246
235
|
//fetch batch
|
|
247
|
-
Prometheus.SourceRequestCount.increment(
|
|
248
|
-
~sourceName=name,
|
|
249
|
-
~chainId=chain->ChainMap.Chain.toChainId,
|
|
250
|
-
~method="getLogs",
|
|
251
|
-
)
|
|
252
236
|
let pageUnsafe = try await HyperSync.GetLogs.query(
|
|
253
237
|
~client,
|
|
254
238
|
~fromBlock,
|
|
255
239
|
~toBlock,
|
|
256
240
|
~logSelections,
|
|
257
241
|
~fieldSelection=selectionConfig.fieldSelection,
|
|
242
|
+
~maxNumLogs=itemsTarget,
|
|
258
243
|
) catch {
|
|
259
244
|
| HyperSync.GetLogs.Error(error) =>
|
|
260
245
|
throw(
|
|
@@ -301,7 +286,8 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
301
286
|
)
|
|
302
287
|
}
|
|
303
288
|
|
|
304
|
-
let pageFetchTime = startFetchingBatchTimeRef->
|
|
289
|
+
let pageFetchTime = startFetchingBatchTimeRef->Performance.secondsSince
|
|
290
|
+
let requestStats = [{Source.method: "getLogs", seconds: pageFetchTime}]
|
|
305
291
|
|
|
306
292
|
//set height and next from block
|
|
307
293
|
let knownHeight = pageUnsafe.archiveHeight
|
|
@@ -311,23 +297,30 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
311
297
|
//In the query
|
|
312
298
|
let heighestBlockQueried = pageUnsafe.nextBlock - 1
|
|
313
299
|
|
|
314
|
-
let parsingTimeRef =
|
|
300
|
+
let parsingTimeRef = Performance.now()
|
|
315
301
|
|
|
316
302
|
//Parse page items into queue items
|
|
317
303
|
let parsedQueueItems = []
|
|
318
304
|
|
|
305
|
+
// Block headers are returned once per number; items reference them by blockNumber.
|
|
306
|
+
let blocksByNumber = Utils.Map.make()
|
|
307
|
+
pageUnsafe.blocks->Array.forEach(block => {
|
|
308
|
+
blocksByNumber->Utils.Map.set(block.number, block)->ignore
|
|
309
|
+
})
|
|
310
|
+
let getBlock = blockNumber => blocksByNumber->Utils.Map.unsafeGet(blockNumber)
|
|
311
|
+
|
|
319
312
|
let handleDecodeFailure = (
|
|
320
|
-
~
|
|
313
|
+
~onEventRegistration: Internal.evmOnEventRegistration,
|
|
321
314
|
~logIndex,
|
|
322
315
|
~blockNumber,
|
|
323
316
|
~chainId,
|
|
324
317
|
~exn,
|
|
325
318
|
) => {
|
|
326
|
-
if !
|
|
319
|
+
if !onEventRegistration.isWildcard {
|
|
327
320
|
//Wildcard events can be parsed as undefined if the number of topics
|
|
328
321
|
//don't match the event with the given topic0
|
|
329
322
|
//Non wildcard events should be expected to be parsed
|
|
330
|
-
let msg = `Event ${eventConfig.name} was unexpectedly parsed as undefined`
|
|
323
|
+
let msg = `Event ${onEventRegistration.eventConfig.name} was unexpectedly parsed as undefined`
|
|
331
324
|
let logger = Logging.createChildFrom(
|
|
332
325
|
~logger,
|
|
333
326
|
~params={
|
|
@@ -349,24 +342,25 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
349
342
|
~sighash=item.topic0->EvmTypes.Hex.toString,
|
|
350
343
|
~topicCount=item.topicCount,
|
|
351
344
|
),
|
|
352
|
-
~
|
|
345
|
+
~contractNameByAddress,
|
|
353
346
|
~contractAddress=item.srcAddress,
|
|
354
|
-
~blockNumber=item.block.number->Option.getUnsafe,
|
|
355
347
|
)
|
|
356
348
|
|
|
357
349
|
switch maybeEventConfig {
|
|
358
350
|
| None => () //ignore events that aren't registered
|
|
359
|
-
| Some(
|
|
351
|
+
| Some(onEventRegistration) =>
|
|
360
352
|
switch item.params
|
|
361
353
|
->Nullable.toOption
|
|
362
|
-
->Option.flatMap(Dict.get(_, eventConfig.contractName)) {
|
|
354
|
+
->Option.flatMap(Dict.get(_, onEventRegistration.eventConfig.contractName)) {
|
|
363
355
|
| Some(params) =>
|
|
364
|
-
parsedQueueItems
|
|
356
|
+
parsedQueueItems
|
|
357
|
+
->Array.push(makeEventBatchQueueItem(item, ~params, ~onEventRegistration))
|
|
358
|
+
->ignore
|
|
365
359
|
| None =>
|
|
366
360
|
handleDecodeFailure(
|
|
367
|
-
~
|
|
361
|
+
~onEventRegistration,
|
|
368
362
|
~logIndex=item.logIndex,
|
|
369
|
-
~blockNumber=item.
|
|
363
|
+
~blockNumber=item.blockNumber,
|
|
370
364
|
~chainId,
|
|
371
365
|
~exn=UndefinedValue,
|
|
372
366
|
)
|
|
@@ -374,19 +368,17 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
374
368
|
}
|
|
375
369
|
})
|
|
376
370
|
|
|
377
|
-
let parsingTimeElapsed = parsingTimeRef->
|
|
371
|
+
let parsingTimeElapsed = parsingTimeRef->Performance.secondsSince
|
|
378
372
|
|
|
379
373
|
// Collect (blockNumber, blockHash) pairs we already have from the response —
|
|
380
|
-
// one per
|
|
374
|
+
// one per returned block plus, when present, the rollbackGuard's head block
|
|
381
375
|
// and the parent of the range's first block. Duplicates are allowed; reorg
|
|
382
376
|
// detection notices same-block-number-different-hash collisions itself.
|
|
383
377
|
let blockHashes = []
|
|
384
|
-
pageUnsafe.
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
| _ => ()
|
|
389
|
-
}
|
|
378
|
+
pageUnsafe.blocks->Array.forEach(block => {
|
|
379
|
+
blockHashes
|
|
380
|
+
->Array.push({ReorgDetection.blockNumber: block.number, blockHash: block.hash})
|
|
381
|
+
->ignore
|
|
390
382
|
})
|
|
391
383
|
switch pageUnsafe.rollbackGuard {
|
|
392
384
|
| None => ()
|
|
@@ -409,13 +401,13 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
409
401
|
| Some({timestamp}) => timestamp
|
|
410
402
|
| None =>
|
|
411
403
|
switch pageUnsafe.items->Array.get(pageUnsafe.items->Array.length - 1) {
|
|
412
|
-
| Some(
|
|
413
|
-
|
|
404
|
+
| Some(item) if item.blockNumber == heighestBlockQueried =>
|
|
405
|
+
getBlock(item.blockNumber).timestamp
|
|
414
406
|
| _ => 0
|
|
415
407
|
}
|
|
416
408
|
}
|
|
417
409
|
|
|
418
|
-
let totalTimeElapsed = totalTimeRef->
|
|
410
|
+
let totalTimeElapsed = totalTimeRef->Performance.secondsSince
|
|
419
411
|
|
|
420
412
|
let stats = {
|
|
421
413
|
totalTimeElapsed,
|
|
@@ -426,11 +418,14 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
426
418
|
{
|
|
427
419
|
latestFetchedBlockTimestamp,
|
|
428
420
|
parsedQueueItems,
|
|
421
|
+
transactionStore: Some(pageUnsafe.transactionStore),
|
|
422
|
+
blockStore: Some(pageUnsafe.blockStore),
|
|
429
423
|
latestFetchedBlockNumber: heighestBlockQueried,
|
|
430
424
|
stats,
|
|
431
425
|
knownHeight,
|
|
432
426
|
blockHashes,
|
|
433
427
|
fromBlockQueried: fromBlock,
|
|
428
|
+
requestStats,
|
|
434
429
|
}
|
|
435
430
|
}
|
|
436
431
|
|
|
@@ -441,7 +436,10 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
441
436
|
~sourceName=name,
|
|
442
437
|
~chainId=chain->ChainMap.Chain.toChainId,
|
|
443
438
|
~logger,
|
|
444
|
-
)->Promise.thenResolve(
|
|
439
|
+
)->Promise.thenResolve(((queryRes, requestStats)) => {
|
|
440
|
+
Source.result: queryRes->HyperSync.mapExn,
|
|
441
|
+
requestStats,
|
|
442
|
+
})
|
|
445
443
|
|
|
446
444
|
{
|
|
447
445
|
name,
|
|
@@ -451,8 +449,8 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
451
449
|
poweredByHyperSync: true,
|
|
452
450
|
getBlockHashes,
|
|
453
451
|
getHeightOrThrow: async () => {
|
|
454
|
-
let timerRef =
|
|
455
|
-
let
|
|
452
|
+
let timerRef = Performance.now()
|
|
453
|
+
let height = try {
|
|
456
454
|
await client.getHeight()
|
|
457
455
|
} catch {
|
|
458
456
|
| JsExn(e) =>
|
|
@@ -465,19 +463,8 @@ Learn more or get a free Envio API token at: https://envio.dev/app/api-tokens`)
|
|
|
465
463
|
| _ => throw(JsExn(e))
|
|
466
464
|
}
|
|
467
465
|
}
|
|
468
|
-
let seconds = timerRef->
|
|
469
|
-
|
|
470
|
-
~sourceName=name,
|
|
471
|
-
~chainId=chain->ChainMap.Chain.toChainId,
|
|
472
|
-
~method="getHeight",
|
|
473
|
-
)
|
|
474
|
-
Prometheus.SourceRequestCount.addSeconds(
|
|
475
|
-
~sourceName=name,
|
|
476
|
-
~chainId=chain->ChainMap.Chain.toChainId,
|
|
477
|
-
~method="getHeight",
|
|
478
|
-
~seconds,
|
|
479
|
-
)
|
|
480
|
-
result
|
|
466
|
+
let seconds = timerRef->Performance.secondsSince
|
|
467
|
+
{height, requestStats: [{method: "getHeight", seconds}]}
|
|
481
468
|
},
|
|
482
469
|
getItemsOrThrow,
|
|
483
470
|
createHeightSubscription: (~onHeight) =>
|