@across-protocol/sdk 4.1.32 → 4.1.33
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/dist/cjs/arch/evm/index.d.ts +1 -0
- package/dist/cjs/arch/evm/index.js +5 -0
- package/dist/cjs/arch/evm/index.js.map +1 -0
- package/dist/cjs/arch/index.d.ts +2 -0
- package/dist/cjs/arch/index.js +7 -0
- package/dist/cjs/arch/index.js.map +1 -0
- package/dist/cjs/arch/svm/index.d.ts +1 -0
- package/dist/cjs/arch/svm/index.js +5 -0
- package/dist/cjs/arch/svm/index.js.map +1 -0
- package/dist/cjs/clients/BundleDataClient/BundleDataClient.js +24 -3
- package/dist/cjs/clients/BundleDataClient/BundleDataClient.js.map +1 -1
- package/dist/cjs/clients/BundleDataClient/utils/SuperstructUtils.d.ts +2 -2
- package/dist/cjs/clients/SpokePoolClient/EVMSpokePoolClient.d.ts +19 -0
- package/dist/cjs/clients/SpokePoolClient/EVMSpokePoolClient.js +170 -0
- package/dist/cjs/clients/SpokePoolClient/EVMSpokePoolClient.js.map +1 -0
- package/dist/cjs/clients/{SpokePoolClient.d.ts → SpokePoolClient/SpokePoolClient.d.ts} +17 -22
- package/dist/cjs/clients/{SpokePoolClient.js → SpokePoolClient/SpokePoolClient.js} +24 -174
- package/dist/cjs/clients/SpokePoolClient/SpokePoolClient.js.map +1 -0
- package/dist/cjs/clients/SpokePoolClient/index.d.ts +5 -0
- package/dist/cjs/clients/SpokePoolClient/index.js +13 -0
- package/dist/cjs/clients/SpokePoolClient/index.js.map +1 -0
- package/dist/cjs/clients/index.d.ts +1 -1
- package/dist/cjs/clients/index.js +2 -1
- package/dist/cjs/clients/index.js.map +1 -1
- package/dist/cjs/clients/mocks/MockSpokePoolClient.d.ts +2 -2
- package/dist/cjs/clients/mocks/MockSpokePoolClient.js +1 -1
- package/dist/cjs/clients/mocks/MockSpokePoolClient.js.map +1 -1
- package/dist/cjs/utils/BundleUtils.js +7 -7
- package/dist/cjs/utils/BundleUtils.js.map +1 -1
- package/dist/esm/arch/evm/index.d.ts +1 -0
- package/dist/esm/arch/evm/index.js +2 -0
- package/dist/esm/arch/evm/index.js.map +1 -0
- package/dist/esm/arch/index.d.ts +2 -0
- package/dist/esm/arch/index.js +5 -0
- package/dist/esm/arch/index.js.map +1 -0
- package/dist/esm/arch/svm/index.d.ts +1 -0
- package/dist/esm/arch/svm/index.js +2 -0
- package/dist/esm/arch/svm/index.js.map +1 -0
- package/dist/esm/clients/BundleDataClient/BundleDataClient.js +30 -3
- package/dist/esm/clients/BundleDataClient/BundleDataClient.js.map +1 -1
- package/dist/esm/clients/BundleDataClient/utils/SuperstructUtils.d.ts +2 -2
- package/dist/esm/clients/SpokePoolClient/EVMSpokePoolClient.d.ts +22 -0
- package/dist/esm/clients/SpokePoolClient/EVMSpokePoolClient.js +174 -0
- package/dist/esm/clients/SpokePoolClient/EVMSpokePoolClient.js.map +1 -0
- package/dist/{types/clients → esm/clients/SpokePoolClient}/SpokePoolClient.d.ts +58 -57
- package/dist/esm/clients/{SpokePoolClient.js → SpokePoolClient/SpokePoolClient.js} +22 -212
- package/dist/esm/clients/SpokePoolClient/SpokePoolClient.js.map +1 -0
- package/dist/esm/clients/SpokePoolClient/index.d.ts +10 -0
- package/dist/esm/clients/SpokePoolClient/index.js +12 -0
- package/dist/esm/clients/SpokePoolClient/index.js.map +1 -0
- package/dist/esm/clients/index.d.ts +1 -1
- package/dist/esm/clients/index.js +1 -1
- package/dist/esm/clients/index.js.map +1 -1
- package/dist/esm/clients/mocks/MockSpokePoolClient.d.ts +2 -2
- package/dist/esm/clients/mocks/MockSpokePoolClient.js +2 -2
- package/dist/esm/clients/mocks/MockSpokePoolClient.js.map +1 -1
- package/dist/esm/utils/BundleUtils.js +7 -7
- package/dist/esm/utils/BundleUtils.js.map +1 -1
- package/dist/esm/utils/abi/typechain/Multicall3.d.ts +1 -4
- package/dist/esm/utils/abi/typechain/factories/Multicall3__factory.js.map +1 -1
- package/dist/types/arch/evm/index.d.ts +2 -0
- package/dist/types/arch/evm/index.d.ts.map +1 -0
- package/dist/types/arch/index.d.ts +3 -0
- package/dist/types/arch/index.d.ts.map +1 -0
- package/dist/types/arch/svm/index.d.ts +2 -0
- package/dist/types/arch/svm/index.d.ts.map +1 -0
- package/dist/types/clients/BundleDataClient/BundleDataClient.d.ts.map +1 -1
- package/dist/types/clients/BundleDataClient/utils/SuperstructUtils.d.ts +2 -2
- package/dist/types/clients/SpokePoolClient/EVMSpokePoolClient.d.ts +23 -0
- package/dist/types/clients/SpokePoolClient/EVMSpokePoolClient.d.ts.map +1 -0
- package/dist/{esm/clients → types/clients/SpokePoolClient}/SpokePoolClient.d.ts +59 -56
- package/dist/types/clients/SpokePoolClient/SpokePoolClient.d.ts.map +1 -0
- package/dist/types/clients/SpokePoolClient/index.d.ts +11 -0
- package/dist/types/clients/SpokePoolClient/index.d.ts.map +1 -0
- package/dist/types/clients/index.d.ts +1 -1
- package/dist/types/clients/index.d.ts.map +1 -1
- package/dist/types/clients/mocks/MockSpokePoolClient.d.ts +2 -2
- package/dist/types/clients/mocks/MockSpokePoolClient.d.ts.map +1 -1
- package/dist/types/utils/abi/typechain/Multicall3.d.ts +1 -4
- package/dist/types/utils/abi/typechain/Multicall3.d.ts.map +1 -1
- package/dist/types/utils/abi/typechain/common.d.ts.map +1 -1
- package/dist/types/utils/abi/typechain/factories/Multicall3__factory.d.ts.map +1 -1
- package/package.json +4 -3
- package/src/arch/evm/index.ts +1 -0
- package/src/arch/index.ts +2 -0
- package/src/arch/svm/index.ts +1 -0
- package/src/clients/BundleDataClient/BundleDataClient.ts +29 -1
- package/src/clients/SpokePoolClient/EVMSpokePoolClient.ts +206 -0
- package/src/clients/{SpokePoolClient.ts → SpokePoolClient/SpokePoolClient.ts} +87 -237
- package/src/clients/SpokePoolClient/index.ts +14 -0
- package/src/clients/index.ts +1 -1
- package/src/clients/mocks/MockSpokePoolClient.ts +2 -2
- package/src/utils/BundleUtils.ts +6 -6
- package/dist/cjs/clients/SpokePoolClient.js.map +0 -1
- package/dist/esm/clients/SpokePoolClient.js.map +0 -1
- package/dist/types/clients/SpokePoolClient.d.ts.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Multicall3__factory.d.ts","sourceRoot":"","sources":["../../../../../../src/utils/abi/typechain/factories/Multicall3__factory.ts"],"names":[],"mappings":"AAIA,OAAO,EAAY,MAAM,EAAS,MAAM,QAAQ,CAAC;AACjD,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,0BAA0B,CAAC;AACzD,OAAO,KAAK,EAAE,UAAU,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AA2brE,qBAAa,mBAAmB;IAC9B,MAAM,CAAC,QAAQ,CAAC,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAAQ;IAC3B,MAAM,CAAC,eAAe,IAAI,mBAAmB;IAG7C,MAAM,CAAC,OAAO,
|
|
1
|
+
{"version":3,"file":"Multicall3__factory.d.ts","sourceRoot":"","sources":["../../../../../../src/utils/abi/typechain/factories/Multicall3__factory.ts"],"names":[],"mappings":"AAIA,OAAO,EAAY,MAAM,EAAS,MAAM,QAAQ,CAAC;AACjD,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,0BAA0B,CAAC;AACzD,OAAO,KAAK,EAAE,UAAU,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AA2brE,qBAAa,mBAAmB;IAC9B,MAAM,CAAC,QAAQ,CAAC,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAAQ;IAC3B,MAAM,CAAC,eAAe,IAAI,mBAAmB;IAG7C,MAAM,CAAC,OAAO,CAAC,OAAO,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,GAAG,QAAQ,GAAG,UAAU;CAGjF"}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@across-protocol/sdk",
|
|
3
3
|
"author": "UMA Team",
|
|
4
|
-
"version": "4.1.
|
|
4
|
+
"version": "4.1.33",
|
|
5
5
|
"license": "AGPL-3.0",
|
|
6
6
|
"homepage": "https://docs.across.to/reference/sdk",
|
|
7
7
|
"files": [
|
|
@@ -16,8 +16,8 @@
|
|
|
16
16
|
"build-bigint-buffer": "node scripts/build-bigint-buffer.js",
|
|
17
17
|
"postinstall": "node scripts/build-bigint-buffer.js",
|
|
18
18
|
"start": "yarn typechain && nodemon -e ts,tsx,json,js,jsx --watch ./src --ignore ./dist --exec 'yarn dev'",
|
|
19
|
-
"build": "yarn run clean && yarn typechain && yarn
|
|
20
|
-
"dev": "yarn run build:cjs
|
|
19
|
+
"build": "yarn run clean && yarn typechain && yarn dev",
|
|
20
|
+
"dev": "concurrently --kill-others-on-fail --names 'cjs,esm,types' --prefix-colors 'blue,magenta,green' 'yarn run build:cjs' 'yarn run build:esm' 'yarn run build:types'",
|
|
21
21
|
"build:cjs": "tsc --project tsconfig.build.json --module commonjs --outDir ./dist/cjs --removeComments --verbatimModuleSyntax false && echo > ./dist/cjs/package.json '{\"type\":\"commonjs\"}'",
|
|
22
22
|
"build:esm": "tsc --project tsconfig.build.json --module es2015 --outDir ./dist/esm && echo > ./dist/esm/package.json '{\"type\":\"module\",\"sideEffects\":false}'",
|
|
23
23
|
"build:types": "tsc --project tsconfig.build.json --module esnext --declarationDir ./dist/types --emitDeclarationOnly --declaration --declarationMap",
|
|
@@ -71,6 +71,7 @@
|
|
|
71
71
|
"arlocal": "^1.1.65",
|
|
72
72
|
"chai": "^4.3.8",
|
|
73
73
|
"chai-exclude": "^2.1.0",
|
|
74
|
+
"concurrently": "^9.1.2",
|
|
74
75
|
"dotenv": "^16.0.0",
|
|
75
76
|
"eslint": "^8.49.0",
|
|
76
77
|
"eslint-config-prettier": "^9.0.0",
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const platform = "evm"; // Placeholder for actual exports.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const platform = "svm"; // Placeholder for actual exports.
|
|
@@ -58,6 +58,7 @@ import {
|
|
|
58
58
|
verifyFillRepayment,
|
|
59
59
|
} from "./utils";
|
|
60
60
|
import { UNDEFINED_MESSAGE_HASH } from "../../constants";
|
|
61
|
+
import { isEVMSpokePoolClient } from "../SpokePoolClient";
|
|
61
62
|
|
|
62
63
|
// max(uint256) - 1
|
|
63
64
|
export const INFINITE_FILL_DEADLINE = bnUint32Max;
|
|
@@ -388,9 +389,15 @@ export class BundleDataClient {
|
|
|
388
389
|
await forEachAsync(fillsToCount, async (_fill) => {
|
|
389
390
|
const matchingDeposit = this.spokePoolClients[_fill.originChainId].getDeposit(_fill.depositId);
|
|
390
391
|
assert(isDefined(matchingDeposit), "Deposit not found for fill.");
|
|
392
|
+
|
|
393
|
+
const spokeClient = this.spokePoolClients[_fill.destinationChainId];
|
|
394
|
+
if (!isEVMSpokePoolClient(spokeClient)) {
|
|
395
|
+
// FIXME: Handle non-EVM chains.
|
|
396
|
+
throw new Error("Destination chain is not an EVM chain.");
|
|
397
|
+
}
|
|
391
398
|
const fill = await verifyFillRepayment(
|
|
392
399
|
_fill,
|
|
393
|
-
|
|
400
|
+
spokeClient.spokePool.provider,
|
|
394
401
|
matchingDeposit,
|
|
395
402
|
this.clients.hubPoolClient
|
|
396
403
|
);
|
|
@@ -890,6 +897,10 @@ export class BundleDataClient {
|
|
|
890
897
|
assert(isDefined(deposits) && deposits.length > 0, "Deposit should exist in relay hash dictionary.");
|
|
891
898
|
v3RelayHashes[relayDataHash].fill = fill;
|
|
892
899
|
if (fill.blockNumber >= destinationChainBlockRange[0]) {
|
|
900
|
+
if (!isEVMSpokePoolClient(destinationClient)) {
|
|
901
|
+
// FIXME: Handle non-EVM chains.
|
|
902
|
+
throw new Error("Destination chain is not an EVM chain.");
|
|
903
|
+
}
|
|
893
904
|
const fillToRefund = await verifyFillRepayment(
|
|
894
905
|
fill,
|
|
895
906
|
destinationClient.spokePool.provider,
|
|
@@ -989,6 +1000,11 @@ export class BundleDataClient {
|
|
|
989
1000
|
}
|
|
990
1001
|
v3RelayHashes[relayDataHash].deposits = [matchedDeposit];
|
|
991
1002
|
|
|
1003
|
+
if (!isEVMSpokePoolClient(destinationClient)) {
|
|
1004
|
+
// FIXME: Handle non-EVM chains.
|
|
1005
|
+
throw new Error("Destination chain is not an EVM chain.");
|
|
1006
|
+
}
|
|
1007
|
+
|
|
992
1008
|
const fillToRefund = await verifyFillRepayment(
|
|
993
1009
|
fill,
|
|
994
1010
|
destinationClient.spokePool.provider,
|
|
@@ -1163,6 +1179,10 @@ export class BundleDataClient {
|
|
|
1163
1179
|
// include this pre fill if the fill is in an older bundle.
|
|
1164
1180
|
if (fill) {
|
|
1165
1181
|
if (fill.blockNumber < destinationChainBlockRange[0]) {
|
|
1182
|
+
if (!isEVMSpokePoolClient(destinationClient)) {
|
|
1183
|
+
// FIXME: Handle non-EVM chains.
|
|
1184
|
+
throw new Error("Destination chain is not an EVM chain.");
|
|
1185
|
+
}
|
|
1166
1186
|
const fillToRefund = await verifyFillRepayment(
|
|
1167
1187
|
fill,
|
|
1168
1188
|
destinationClient.spokePool.provider,
|
|
@@ -1215,6 +1235,10 @@ export class BundleDataClient {
|
|
|
1215
1235
|
const prefill = await this.findMatchingFillEvent(deposit, destinationClient);
|
|
1216
1236
|
assert(isDefined(prefill), `findFillEvent# Cannot find prefill: ${relayDataHash}`);
|
|
1217
1237
|
assert(getRelayEventKey(prefill) === relayDataHash, "Relay hashes should match.");
|
|
1238
|
+
if (!isEVMSpokePoolClient(destinationClient)) {
|
|
1239
|
+
// FIXME: Handle non-EVM chains.
|
|
1240
|
+
throw new Error("Destination chain is not an EVM chain.");
|
|
1241
|
+
}
|
|
1218
1242
|
const verifiedFill = await verifyFillRepayment(
|
|
1219
1243
|
prefill,
|
|
1220
1244
|
destinationClient.spokePool.provider,
|
|
@@ -1511,6 +1535,10 @@ export class BundleDataClient {
|
|
|
1511
1535
|
deposit: DepositWithBlock,
|
|
1512
1536
|
spokePoolClient: SpokePoolClient
|
|
1513
1537
|
): Promise<FillWithBlock | undefined> {
|
|
1538
|
+
if (!isEVMSpokePoolClient(spokePoolClient)) {
|
|
1539
|
+
// FIXME: Handle non-EVM chains.
|
|
1540
|
+
throw new Error("Destination chain is not an EVM chain.");
|
|
1541
|
+
}
|
|
1514
1542
|
return await findFillEvent(
|
|
1515
1543
|
spokePoolClient.spokePool,
|
|
1516
1544
|
deposit,
|
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
import { Contract, EventFilter } from "ethers";
|
|
2
|
+
import { BigNumber, DepositSearchResult, getNetworkName, InvalidFill, MakeOptional, toBN } from "../../utils";
|
|
3
|
+
import {
|
|
4
|
+
EventSearchConfig,
|
|
5
|
+
paginatedEventQuery,
|
|
6
|
+
sortEventsAscendingInPlace,
|
|
7
|
+
spreadEventWithBlockNumber,
|
|
8
|
+
} from "../../utils/EventUtils";
|
|
9
|
+
import { isUpdateFailureReason } from "../BaseAbstractClient";
|
|
10
|
+
import { knownEventNames, SpokePoolClient, SpokePoolUpdate } from "./SpokePoolClient";
|
|
11
|
+
import winston from "winston";
|
|
12
|
+
import { HubPoolClient } from "../HubPoolClient";
|
|
13
|
+
import {
|
|
14
|
+
findDepositBlock,
|
|
15
|
+
getMaxFillDeadlineInRange as getMaxFillDeadline,
|
|
16
|
+
getTimeAt as _getTimeAt,
|
|
17
|
+
relayFillStatus,
|
|
18
|
+
isZeroAddress,
|
|
19
|
+
getTimestampForBlock as _getTimestampForBlock,
|
|
20
|
+
} from "../../utils/SpokeUtils";
|
|
21
|
+
import { DepositWithBlock, FillStatus, RelayData } from "../../interfaces";
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* An EVM-specific SpokePoolClient.
|
|
25
|
+
*/
|
|
26
|
+
export class EVMSpokePoolClient extends SpokePoolClient {
|
|
27
|
+
constructor(
|
|
28
|
+
logger: winston.Logger,
|
|
29
|
+
public readonly spokePool: Contract,
|
|
30
|
+
hubPoolClient: HubPoolClient | null,
|
|
31
|
+
chainId: number,
|
|
32
|
+
deploymentBlock: number,
|
|
33
|
+
eventSearchConfig: MakeOptional<EventSearchConfig, "toBlock"> = { fromBlock: 0, maxBlockLookBack: 0 }
|
|
34
|
+
) {
|
|
35
|
+
super(logger, hubPoolClient, chainId, deploymentBlock, eventSearchConfig);
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
public override relayFillStatus(
|
|
39
|
+
relayData: RelayData,
|
|
40
|
+
blockTag?: number | "latest",
|
|
41
|
+
destinationChainId?: number
|
|
42
|
+
): Promise<FillStatus> {
|
|
43
|
+
return relayFillStatus(this.spokePool, relayData, blockTag, destinationChainId);
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
public override getMaxFillDeadlineInRange(startBlock: number, endBlock: number): Promise<number> {
|
|
47
|
+
return getMaxFillDeadline(this.spokePool, startBlock, endBlock);
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
private _availableEventsOnSpoke(eventNames: string[] = knownEventNames): { [eventName: string]: EventFilter } {
|
|
51
|
+
return Object.fromEntries(
|
|
52
|
+
this.spokePool.interface.fragments
|
|
53
|
+
.filter(({ name, type }) => type === "event" && eventNames.includes(name))
|
|
54
|
+
.map(({ name }) => [name, this.spokePool.filters[name]()])
|
|
55
|
+
);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
public override _queryableEventNames(): string[] {
|
|
59
|
+
return Object.keys(this._availableEventsOnSpoke(knownEventNames));
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
protected override async _update(eventsToQuery: string[]): Promise<SpokePoolUpdate> {
|
|
63
|
+
const searchConfig = await this.updateSearchConfig(this.spokePool.provider);
|
|
64
|
+
if (isUpdateFailureReason(searchConfig)) {
|
|
65
|
+
const reason = searchConfig;
|
|
66
|
+
return { success: false, reason };
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
const eventSearchConfigs = eventsToQuery.map((eventName) => {
|
|
70
|
+
if (!this._queryableEventNames().includes(eventName)) {
|
|
71
|
+
throw new Error(`SpokePoolClient: Cannot query unrecognised SpokePool event name: ${eventName}`);
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
const _searchConfig = { ...searchConfig }; // shallow copy
|
|
75
|
+
|
|
76
|
+
// By default, an event's query range is controlled by the `eventSearchConfig` passed in during instantiation.
|
|
77
|
+
// However, certain events have special overriding requirements to their search ranges:
|
|
78
|
+
// - EnabledDepositRoute: The full history is always required, so override the requested fromBlock.
|
|
79
|
+
if (eventName === "EnabledDepositRoute" && !this.isUpdated) {
|
|
80
|
+
_searchConfig.fromBlock = this.deploymentBlock;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
return {
|
|
84
|
+
filter: this._availableEventsOnSpoke()[eventName],
|
|
85
|
+
searchConfig: _searchConfig,
|
|
86
|
+
};
|
|
87
|
+
});
|
|
88
|
+
|
|
89
|
+
const { spokePool } = this;
|
|
90
|
+
this.log("debug", `Updating SpokePool client for chain ${this.chainId}`, {
|
|
91
|
+
eventsToQuery,
|
|
92
|
+
searchConfig,
|
|
93
|
+
spokePool: spokePool.address,
|
|
94
|
+
});
|
|
95
|
+
|
|
96
|
+
const timerStart = Date.now();
|
|
97
|
+
const multicallFunctions = ["getCurrentTime"];
|
|
98
|
+
const [multicallOutput, ...events] = await Promise.all([
|
|
99
|
+
spokePool.callStatic.multicall(
|
|
100
|
+
multicallFunctions.map((f) => spokePool.interface.encodeFunctionData(f)),
|
|
101
|
+
{ blockTag: searchConfig.toBlock }
|
|
102
|
+
),
|
|
103
|
+
...eventSearchConfigs.map((config) => paginatedEventQuery(this.spokePool, config.filter, config.searchConfig)),
|
|
104
|
+
]);
|
|
105
|
+
this.log("debug", `Time to query new events from RPC for ${this.chainId}: ${Date.now() - timerStart} ms`);
|
|
106
|
+
|
|
107
|
+
const [currentTime] = multicallFunctions.map(
|
|
108
|
+
(fn, idx) => spokePool.interface.decodeFunctionResult(fn, multicallOutput[idx])[0]
|
|
109
|
+
);
|
|
110
|
+
|
|
111
|
+
if (!BigNumber.isBigNumber(currentTime) || currentTime.lt(this.currentTime)) {
|
|
112
|
+
const errMsg = BigNumber.isBigNumber(currentTime)
|
|
113
|
+
? `currentTime: ${currentTime} < ${toBN(this.currentTime)}`
|
|
114
|
+
: `currentTime is not a BigNumber: ${JSON.stringify(currentTime)}`;
|
|
115
|
+
throw new Error(`SpokePoolClient::update: ${errMsg}`);
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
// Sort all events to ensure they are stored in a consistent order.
|
|
119
|
+
events.forEach((events) => sortEventsAscendingInPlace(events));
|
|
120
|
+
|
|
121
|
+
return {
|
|
122
|
+
success: true,
|
|
123
|
+
currentTime: currentTime.toNumber(), // uint32
|
|
124
|
+
searchEndBlock: searchConfig.toBlock,
|
|
125
|
+
events,
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
public override getTimeAt(blockNumber: number): Promise<number> {
|
|
130
|
+
return _getTimeAt(this.spokePool, blockNumber);
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
public override async findDeposit(depositId: BigNumber): Promise<DepositSearchResult> {
|
|
134
|
+
let deposit = this.getDeposit(depositId);
|
|
135
|
+
if (deposit) {
|
|
136
|
+
return { found: true, deposit };
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
// No deposit found; revert to searching for it.
|
|
140
|
+
const upperBound = this.latestBlockSearched || undefined; // Don't permit block 0 as the high block.
|
|
141
|
+
const fromBlock = await findDepositBlock(this.spokePool, depositId, this.deploymentBlock, upperBound);
|
|
142
|
+
const chain = getNetworkName(this.chainId);
|
|
143
|
+
if (!fromBlock) {
|
|
144
|
+
const reason =
|
|
145
|
+
`Unable to find ${chain} depositId ${depositId}` +
|
|
146
|
+
` within blocks [${this.deploymentBlock}, ${upperBound ?? "latest"}].`;
|
|
147
|
+
return { found: false, code: InvalidFill.DepositIdNotFound, reason };
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
const toBlock = fromBlock;
|
|
151
|
+
const tStart = Date.now();
|
|
152
|
+
// Check both V3FundsDeposited and FundsDeposited events to look for a specified depositId.
|
|
153
|
+
const { maxBlockLookBack } = this.eventSearchConfig;
|
|
154
|
+
const query = (
|
|
155
|
+
await Promise.all([
|
|
156
|
+
paginatedEventQuery(
|
|
157
|
+
this.spokePool,
|
|
158
|
+
this.spokePool.filters.V3FundsDeposited(null, null, null, null, null, depositId),
|
|
159
|
+
{ fromBlock, toBlock, maxBlockLookBack }
|
|
160
|
+
),
|
|
161
|
+
paginatedEventQuery(
|
|
162
|
+
this.spokePool,
|
|
163
|
+
this.spokePool.filters.FundsDeposited(null, null, null, null, null, depositId),
|
|
164
|
+
{ fromBlock, toBlock, maxBlockLookBack }
|
|
165
|
+
),
|
|
166
|
+
])
|
|
167
|
+
).flat();
|
|
168
|
+
const tStop = Date.now();
|
|
169
|
+
|
|
170
|
+
const event = query.find(({ args }) => args["depositId"].eq(depositId));
|
|
171
|
+
if (event === undefined) {
|
|
172
|
+
return {
|
|
173
|
+
found: false,
|
|
174
|
+
code: InvalidFill.DepositIdNotFound,
|
|
175
|
+
reason: `${chain} depositId ${depositId} not found at block ${fromBlock}.`,
|
|
176
|
+
};
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
deposit = {
|
|
180
|
+
...spreadEventWithBlockNumber(event),
|
|
181
|
+
originChainId: this.chainId,
|
|
182
|
+
quoteBlockNumber: await this.getBlockNumber(Number(event.args["quoteTimestamp"])),
|
|
183
|
+
fromLiteChain: true, // To be updated immediately afterwards.
|
|
184
|
+
toLiteChain: true, // To be updated immediately afterwards.
|
|
185
|
+
} as DepositWithBlock;
|
|
186
|
+
|
|
187
|
+
if (isZeroAddress(deposit.outputToken)) {
|
|
188
|
+
deposit.outputToken = this.getDestinationTokenForDeposit(deposit);
|
|
189
|
+
}
|
|
190
|
+
deposit.fromLiteChain = this.isOriginLiteChain(deposit);
|
|
191
|
+
deposit.toLiteChain = this.isDestinationLiteChain(deposit);
|
|
192
|
+
|
|
193
|
+
this.logger.debug({
|
|
194
|
+
at: "SpokePoolClient#findDeposit",
|
|
195
|
+
message: "Located V3 deposit outside of SpokePoolClient's search range",
|
|
196
|
+
deposit,
|
|
197
|
+
elapsedMs: tStop - tStart,
|
|
198
|
+
});
|
|
199
|
+
|
|
200
|
+
return { found: true, deposit };
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
public override getTimestampForBlock(blockNumber: number): Promise<number> {
|
|
204
|
+
return _getTimestampForBlock(this.spokePool.provider, blockNumber);
|
|
205
|
+
}
|
|
206
|
+
}
|