Skip to content

Commit

Permalink
sdk: Added resume transfer methods to routes (#487)
Browse files Browse the repository at this point in the history
* sdk: Added resume transfer methods to routes

* bump wormhole sdk to 0.9.0

* add eta to quote

* bump wormhole sdk to 0.9.1

* fix test
  • Loading branch information
kev1n-peters authored Aug 7, 2024
1 parent a6fcaea commit aa72f14
Show file tree
Hide file tree
Showing 11 changed files with 449 additions and 554 deletions.
16 changes: 8 additions & 8 deletions evm/ts/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -44,19 +44,19 @@
"test": "jest --config ./jest.config.ts"
},
"dependencies": {
"@wormhole-foundation/sdk-base": "^0.8",
"@wormhole-foundation/sdk-definitions": "^0.8",
"@wormhole-foundation/sdk-base": "^0.9.1",
"@wormhole-foundation/sdk-definitions": "^0.9.1",
"@wormhole-foundation/sdk-definitions-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-evm": "^0.8",
"@wormhole-foundation/sdk-evm-core": "^0.8",
"@wormhole-foundation/sdk-evm": "^0.9.1",
"@wormhole-foundation/sdk-evm-core": "^0.9.1",
"ethers": "^6.5.1"
},
"peerDependencies": {
"@wormhole-foundation/sdk-definitions-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-base": "^0.8",
"@wormhole-foundation/sdk-definitions": "^0.8",
"@wormhole-foundation/sdk-evm": "^0.8",
"@wormhole-foundation/sdk-evm-core": "^0.8"
"@wormhole-foundation/sdk-base": "^0.9.1",
"@wormhole-foundation/sdk-definitions": "^0.9.1",
"@wormhole-foundation/sdk-evm": "^0.9.1",
"@wormhole-foundation/sdk-evm-core": "^0.9.1"
},
"devDependencies": {
"@typechain/ethers-v6": "^0.5.1",
Expand Down
750 changes: 221 additions & 529 deletions package-lock.json

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
"version": "tsx setSdkVersion.ts"
},
"devDependencies": {
"@wormhole-foundation/sdk": "^0.8",
"@wormhole-foundation/sdk": "^0.9.1",
"@solana/spl-token": "0.3.9",
"@solana/web3.js": "1.91.7",
"@types/jest": "^29.5.12",
Expand Down
8 changes: 4 additions & 4 deletions sdk/definitions/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -49,12 +49,12 @@
"test": "jest --config ./jest.config.ts"
},
"dependencies": {
"@wormhole-foundation/sdk-base": "^0.8",
"@wormhole-foundation/sdk-definitions": "^0.8"
"@wormhole-foundation/sdk-base": "^0.9.1",
"@wormhole-foundation/sdk-definitions": "^0.9.1"
},
"peerDependencies": {
"@wormhole-foundation/sdk-base": "^0.8",
"@wormhole-foundation/sdk-definitions": "^0.8"
"@wormhole-foundation/sdk-base": "^0.9.1",
"@wormhole-foundation/sdk-definitions": "^0.9.1"
},
"type": "module"
}
2 changes: 1 addition & 1 deletion sdk/examples/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@
"tsx": "^4.7.2"
},
"dependencies": {
"@wormhole-foundation/sdk": "^0.8",
"@wormhole-foundation/sdk": "^0.9.1",
"@wormhole-foundation/sdk-definitions-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-evm-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-solana-ntt": "0.1.0-beta.0",
Expand Down
2 changes: 2 additions & 0 deletions sdk/route/__tests__/route.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,7 @@ describe("Manual Route Tests", function () {
"params",
"sourceToken",
"destinationToken",
"eta",
]);
});
});
Expand Down Expand Up @@ -249,6 +250,7 @@ describe("Automatic Route Tests", function () {
"destinationToken",
"relayFee",
"destinationNativeGas",
"eta",
]);
});
});
6 changes: 3 additions & 3 deletions sdk/route/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -48,10 +48,10 @@
"@wormhole-foundation/sdk-definitions-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-solana-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-evm-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-connect": "^0.8"
"@wormhole-foundation/sdk-connect": "^0.9.1"
},
"peerDependencies": {
"@wormhole-foundation/sdk-connect": "^0.8",
"@wormhole-foundation/sdk-connect": "^0.9.1",
"@wormhole-foundation/sdk-definitions-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-solana-ntt": "0.1.0-beta.0",
"@wormhole-foundation/sdk-evm-ntt": "0.1.0-beta.0"
Expand All @@ -69,4 +69,4 @@
}
}
}
}
}
85 changes: 85 additions & 0 deletions sdk/route/src/automatic.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,14 @@ import {
RedeemedTransferReceipt,
Signer,
TokenId,
TransactionId,
TransferState,
Wormhole,
WormholeMessageId,
amount,
canonicalAddress,
chainToPlatform,
finality,
isAttested,
isDestinationQueued,
isRedeemed,
Expand Down Expand Up @@ -179,6 +182,7 @@ export class NttAutomaticRoute<N extends Network>
params.normalizedParams.options.gasDropoff ?? 0n,
toChain.config.nativeTokenDecimals
),
eta: finality.estimateFinalityTime(request.fromChain.chain),
};
const dstNtt = await toChain.getProtocol("Ntt", {
ntt: params.normalizedParams.destinationContracts,
Expand Down Expand Up @@ -235,6 +239,87 @@ export class NttAutomaticRoute<N extends Network>
};
}

async resume(tx: TransactionId): Promise<R> {
const vaa = await this.wh.getVaa(
tx.txid,
"Ntt:WormholeTransferStandardRelayer"
);
if (!vaa) throw new Error("No VAA found for transaction: " + tx.txid);

const msgId: WormholeMessageId = {
chain: vaa.emitterChain,
emitter: vaa.emitterAddress,
sequence: vaa.sequence,
};

const { payload } = vaa.payload;
const { recipientChain, trimmedAmount } =
payload["nttManagerPayload"].payload;

const token = canonicalAddress({
chain: vaa.emitterChain,
address: payload["nttManagerPayload"].payload.sourceToken,
});
const manager = canonicalAddress({
chain: vaa.emitterChain,
address: payload["sourceNttManager"],
});
const whTransceiver =
vaa.emitterChain === "Solana"
? manager
: canonicalAddress({
chain: vaa.emitterChain,
address: vaa.emitterAddress,
});

const dstInfo = NttRoute.resolveDestinationNttContracts(
this.staticConfig,
{
chain: vaa.emitterChain,
address: payload["sourceNttManager"],
},
recipientChain
);

const amt = amount.fromBaseUnits(
trimmedAmount.amount,
trimmedAmount.decimals
);

return {
from: vaa.emitterChain,
to: recipientChain,
state: TransferState.Attested,
originTxs: [tx],
attestation: {
id: msgId,
attestation: vaa,
},
params: {
amount: amount.display(amt),
options: { automatic: true },
normalizedParams: {
amount: amt,
options: { queue: false, automatic: true },
sourceContracts: {
token,
manager,
transceiver: {
wormhole: whTransceiver,
},
},
destinationContracts: {
token: dstInfo.token,
manager: dstInfo.manager,
transceiver: {
wormhole: dstInfo.transceiver.wormhole,
},
},
},
},
};
}

// Even though this is an automatic route, the transfer may need to be
// manually finalized if it was queued
async finalize(signer: Signer, receipt: R): Promise<R> {
Expand Down
81 changes: 81 additions & 0 deletions sdk/route/src/manual.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,17 +9,20 @@ import {
RedeemedTransferReceipt,
Signer,
TokenId,
TransactionId,
TransferState,
Wormhole,
WormholeMessageId,
amount,
canonicalAddress,
isAttested,
isDestinationQueued,
isRedeemed,
isSourceFinalized,
isSourceInitiated,
routes,
signSendWait,
finality,
} from "@wormhole-foundation/sdk-connect";
import "@wormhole-foundation/sdk-definitions-ntt";
import { NttRoute } from "./types.js";
Expand Down Expand Up @@ -145,6 +148,7 @@ export class NttManualRoute<N extends Network>
token: request.destination.id,
amount: amount.parse(params.amount, request.destination.decimals),
},
eta: finality.estimateFinalityTime(request.fromChain.chain),
};
const { fromChain, toChain } = request;
const dstNtt = await toChain.getProtocol("Ntt", {
Expand Down Expand Up @@ -224,6 +228,83 @@ export class NttManualRoute<N extends Network>
};
}

async resume(tx: TransactionId): Promise<R> {
const vaa = await this.wh.getVaa(tx.txid, "Ntt:WormholeTransfer");
if (!vaa) throw new Error("No VAA found for transaction: " + tx.txid);

const msgId: WormholeMessageId = {
chain: vaa.emitterChain,
emitter: vaa.emitterAddress,
sequence: vaa.sequence,
};

const { recipientChain, trimmedAmount } =
vaa.payload["nttManagerPayload"].payload;

const token = canonicalAddress({
chain: vaa.emitterChain,
address: vaa.payload["nttManagerPayload"].payload.sourceToken,
});
const manager = canonicalAddress({
chain: vaa.emitterChain,
address: vaa.payload["sourceNttManager"],
});
const whTransceiver =
vaa.emitterChain === "Solana"
? manager
: canonicalAddress({
chain: vaa.emitterChain,
address: vaa.emitterAddress,
});

const dstInfo = NttRoute.resolveDestinationNttContracts(
this.staticConfig,
{
chain: vaa.emitterChain,
address: vaa.payload["sourceNttManager"],
},
recipientChain
);

const amt = amount.fromBaseUnits(
trimmedAmount.amount,
trimmedAmount.decimals
);

return {
from: vaa.emitterChain,
to: recipientChain,
state: TransferState.Attested,
originTxs: [tx],
attestation: {
id: msgId,
attestation: vaa,
},
params: {
amount: amount.display(amt),
options: { automatic: false },
normalizedParams: {
amount: amt,
options: { queue: false },
sourceContracts: {
token,
manager,
transceiver: {
wormhole: whTransceiver,
},
},
destinationContracts: {
token: dstInfo.token,
manager: dstInfo.manager,
transceiver: {
wormhole: dstInfo.transceiver.wormhole,
},
},
},
},
};
}

async finalize(signer: Signer, receipt: R): Promise<R> {
if (!isDestinationQueued(receipt)) {
throw new Error(
Expand Down
35 changes: 35 additions & 0 deletions sdk/route/src/types.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import {
Chain,
ChainAddress,
ChainContext,
Network,
TokenId,
Expand Down Expand Up @@ -168,6 +169,40 @@ export namespace NttRoute {
throw new Error("Cannot find Ntt contracts in config for: " + address);
}

export function resolveDestinationNttContracts<C extends Chain>(
config: Config,
srcManager: ChainAddress<C>,
dstChain: Chain
): Ntt.Contracts {
const cfg = Object.values(config.tokens);
const address = canonicalAddress(srcManager);
for (const tokens of cfg) {
const found = tokens.find(
(tc) =>
tc.manager.toLowerCase() === address.toLowerCase() &&
tc.chain === srcManager.chain
);
if (found) {
const remote = tokens.find((tc) => tc.chain === dstChain);
if (!remote) {
throw new Error(
`Cannot find destination Ntt contracts in config for: ${address}`
);
}
return {
token: remote.token,
manager: remote.manager,
transceiver: {
wormhole: remote.transceiver.find((v) => v.type === "wormhole")!
.address,
},
quoter: remote.quoter,
};
}
}
throw new Error("Cannot find Ntt contracts in config for: " + address);
}

// returns true if the amount is greater than 95% of the capacity
// useful for warning about the possibility of a transfer being queued
export function isCapacityThresholdExceeded(
Expand Down
16 changes: 8 additions & 8 deletions solana/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -54,16 +54,16 @@
"@solana/spl-token": "0.4.0",
"@solana/web3.js": "1.91.7",
"bn.js": "5.2.1",
"@wormhole-foundation/sdk-base": "^0.8",
"@wormhole-foundation/sdk-definitions": "^0.8",
"@wormhole-foundation/sdk-solana": "^0.8",
"@wormhole-foundation/sdk-solana-core": "^0.8"
"@wormhole-foundation/sdk-base": "^0.9.1",
"@wormhole-foundation/sdk-definitions": "^0.9.1",
"@wormhole-foundation/sdk-solana": "^0.9.1",
"@wormhole-foundation/sdk-solana-core": "^0.9.1"
},
"peerDependencies": {
"@wormhole-foundation/sdk-base": "^0.8",
"@wormhole-foundation/sdk-definitions": "^0.8",
"@wormhole-foundation/sdk-solana": "^0.8",
"@wormhole-foundation/sdk-solana-core": "^0.8",
"@wormhole-foundation/sdk-base": "^0.9.1",
"@wormhole-foundation/sdk-definitions": "^0.9.1",
"@wormhole-foundation/sdk-solana": "^0.9.1",
"@wormhole-foundation/sdk-solana-core": "^0.9.1",
"@wormhole-foundation/sdk-definitions-ntt": "0.1.0-beta.0"
},
"type": "module",
Expand Down

0 comments on commit aa72f14

Please sign in to comment.