UNPKG

@wormhole-foundation/sdk-connect

Version:

The core package for the Connect SDK, used in conjunction with 1 or more of the chain packages

122 lines 4.82 kB
import { amount, circle, contracts } from "@wormhole-foundation/sdk-base"; import { CircleBridge, isSameToken } from "@wormhole-foundation/sdk-definitions"; import { signSendWait } from "../../common.js"; import { CircleTransfer } from "../../protocols/cctp/cctpTransfer.js"; import { TransferState, isAttested } from "../../types.js"; import { Wormhole } from "../../wormhole.js"; import { ManualRoute } from "../route.js"; export class CCTPRoute extends ManualRoute { static meta = { name: "ManualCCTP", provider: "Circle", }; static supportedNetworks() { return ["Mainnet", "Testnet"]; } // get the list of chains this route supports static supportedChains(network) { if (contracts.circleContractChains.has(network)) { return contracts.circleContractChains.get(network); } return []; } // get the list of destination tokens that may be received on the destination chain static async supportedDestinationTokens(sourceToken, fromChain, toChain) { // Ensure the source token is USDC const sourceChainUsdcContract = circle.usdcContract.get(fromChain.network, fromChain.chain); if (!sourceChainUsdcContract) return []; if (!isSameToken(sourceToken, Wormhole.tokenId(fromChain.chain, sourceChainUsdcContract))) { return []; } const { network, chain } = toChain; if (!circle.usdcContract.has(network, chain)) return []; return [Wormhole.chainAddress(chain, circle.usdcContract.get(network, chain))]; } getDefaultOptions() { return { payload: undefined, }; } async validate(request, params) { const amount = request.parseAmount(params.amount); const validatedParams = { normalizedParams: { amount, }, options: params.options ?? this.getDefaultOptions(), ...params, }; return { valid: true, params: validatedParams }; } async quote(request, params) { try { return request.displayQuote(await CircleTransfer.quoteTransfer(request.fromChain, request.toChain, { automatic: false, amount: amount.units(params.normalizedParams.amount), ...params.options, }), params); } catch (e) { return { success: false, error: e, }; } } async initiate(request, signer, quote, to) { const { params } = quote; const transfer = await CircleTransfer.destinationOverrides(request.fromChain, request.toChain, this.toTransferDetails(params, Wormhole.chainAddress(signer.chain(), signer.address()), to)); const txids = await CircleTransfer.transfer(request.fromChain, transfer, signer); const msg = await CircleTransfer.getTransferMessage(request.fromChain, txids[txids.length - 1].txid); return { from: transfer.from.chain, to: transfer.to.chain, state: TransferState.SourceFinalized, originTxs: txids, attestation: { id: msg.id, attestation: { message: msg.message } }, }; } async complete(signer, receipt) { if (!isAttested(receipt)) throw new Error("The source must be finalized in order to complete the transfer"); const { id, attestation: att } = receipt.attestation; if (CircleBridge.isCircleAttestation(att)) { const { message, attestation } = att; if (!attestation) throw new Error(`No Circle attestation for ${id}`); const toChain = this.wh.getChain(receipt.to); const cb = await toChain.getCircleBridge(); const sender = Wormhole.parseAddress(signer.chain(), signer.address()); const xfer = cb.redeem(sender, message, attestation); const dstTxids = await signSendWait(toChain, xfer, signer); return { ...receipt, state: TransferState.DestinationInitiated, destinationTxs: dstTxids, }; } else { // return receipt; } } async resume(txid) { const xfer = await CircleTransfer.from(this.wh, txid, 10 * 1000); return CircleTransfer.getReceipt(xfer); } async *track(receipt, timeout) { yield* CircleTransfer.track(this.wh, receipt, timeout); } toTransferDetails(params, from, to) { return { from, to, amount: amount.units(params.normalizedParams.amount), automatic: false, ...params.options, }; } } //# sourceMappingURL=manual.js.map