From fd6ea3ee9ef6f39d0d96281f4234e370fae6ffa0 Mon Sep 17 00:00:00 2001 From: Kelvin Fichter <kelvin@optimism.io> Date: Mon, 7 Feb 2022 12:33:26 -0500 Subject: [PATCH] feat(sdk): allow withdrawals or deposits to target This commit updates the SDK to add support for withdrawing or depositing to a target address (as opposed to simply depositing or withdrawing to yourself). --- .changeset/big-windows-shout.md | 5 ++ packages/sdk/src/adapters/eth-bridge.ts | 55 ++++++++++++----- packages/sdk/src/adapters/standard-bridge.ts | 59 ++++++++++++++----- packages/sdk/src/cross-chain-messenger.ts | 12 ++++ packages/sdk/src/interfaces/bridge-adapter.ts | 12 ++++ .../src/interfaces/cross-chain-messenger.ts | 24 ++++++++ 6 files changed, 137 insertions(+), 30 deletions(-) create mode 100644 .changeset/big-windows-shout.md diff --git a/.changeset/big-windows-shout.md b/.changeset/big-windows-shout.md new file mode 100644 index 000000000..d6b5b4250 --- /dev/null +++ b/.changeset/big-windows-shout.md @@ -0,0 +1,5 @@ +--- +'@eth-optimism/sdk': patch +--- + +Adds support for depositing or withdrawing to a target address diff --git a/packages/sdk/src/adapters/eth-bridge.ts b/packages/sdk/src/adapters/eth-bridge.ts index ad1360da0..429f85b38 100644 --- a/packages/sdk/src/adapters/eth-bridge.ts +++ b/packages/sdk/src/adapters/eth-bridge.ts @@ -100,6 +100,7 @@ export class ETHBridgeAdapter extends StandardBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -108,14 +109,26 @@ export class ETHBridgeAdapter extends StandardBridgeAdapter { throw new Error(`token pair not supported by bridge`) } - return this.l1Bridge.populateTransaction.depositETH( - opts?.l2GasLimit || 200_000, // Default to 200k gas limit. - '0x', // No data. - { - ...omit(opts?.overrides || {}, 'value'), - value: amount, - } - ) + if (opts?.recipient === undefined) { + return this.l1Bridge.populateTransaction.depositETH( + opts?.l2GasLimit || 200_000, // Default to 200k gas limit. + '0x', // No data. + { + ...omit(opts?.overrides || {}, 'value'), + value: amount, + } + ) + } else { + return this.l1Bridge.populateTransaction.depositETHTo( + toAddress(opts.recipient), + opts?.l2GasLimit || 200_000, // Default to 200k gas limit. + '0x', // No data. + { + ...omit(opts?.overrides || {}, 'value'), + value: amount, + } + ) + } }, withdraw: async ( @@ -123,6 +136,7 @@ export class ETHBridgeAdapter extends StandardBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> => { @@ -130,13 +144,24 @@ export class ETHBridgeAdapter extends StandardBridgeAdapter { throw new Error(`token pair not supported by bridge`) } - return this.l2Bridge.populateTransaction.withdraw( - toAddress(l2Token), - amount, - 0, // L1 gas not required. - '0x', // No data. - opts?.overrides || {} - ) + if (opts?.recipient === undefined) { + return this.l2Bridge.populateTransaction.withdraw( + toAddress(l2Token), + amount, + 0, // L1 gas not required. + '0x', // No data. + opts?.overrides || {} + ) + } else { + return this.l2Bridge.populateTransaction.withdrawTo( + toAddress(l2Token), + toAddress(opts.recipient), + amount, + 0, // L1 gas not required. + '0x', // No data. + opts?.overrides || {} + ) + } }, } } diff --git a/packages/sdk/src/adapters/standard-bridge.ts b/packages/sdk/src/adapters/standard-bridge.ts index f2bcbf025..7acd2f847 100644 --- a/packages/sdk/src/adapters/standard-bridge.ts +++ b/packages/sdk/src/adapters/standard-bridge.ts @@ -208,6 +208,7 @@ export class StandardBridgeAdapter implements IBridgeAdapter { amount: NumberLike, signer: Signer, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -223,6 +224,7 @@ export class StandardBridgeAdapter implements IBridgeAdapter { amount: NumberLike, signer: Signer, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionResponse> { @@ -237,6 +239,7 @@ export class StandardBridgeAdapter implements IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -245,14 +248,26 @@ export class StandardBridgeAdapter implements IBridgeAdapter { throw new Error(`token pair not supported by bridge`) } - return this.l1Bridge.populateTransaction.depositERC20( - toAddress(l1Token), - toAddress(l2Token), - amount, - opts?.l2GasLimit || 200_000, // Default to 200k gas limit. - '0x', // No data. - opts?.overrides || {} - ) + if (opts?.recipient === undefined) { + return this.l1Bridge.populateTransaction.depositERC20( + toAddress(l1Token), + toAddress(l2Token), + amount, + opts?.l2GasLimit || 200_000, // Default to 200k gas limit. + '0x', // No data. + opts?.overrides || {} + ) + } else { + return this.l1Bridge.populateTransaction.depositERC20To( + toAddress(l1Token), + toAddress(l2Token), + toAddress(opts.recipient), + amount, + opts?.l2GasLimit || 200_000, // Default to 200k gas limit. + '0x', // No data. + opts?.overrides || {} + ) + } }, withdraw: async ( @@ -260,6 +275,7 @@ export class StandardBridgeAdapter implements IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> => { @@ -267,13 +283,24 @@ export class StandardBridgeAdapter implements IBridgeAdapter { throw new Error(`token pair not supported by bridge`) } - return this.l2Bridge.populateTransaction.withdraw( - toAddress(l2Token), - amount, - 0, // L1 gas not required. - '0x', // No data. - opts?.overrides || {} - ) + if (opts?.recipient === undefined) { + return this.l2Bridge.populateTransaction.withdraw( + toAddress(l2Token), + amount, + 0, // L1 gas not required. + '0x', // No data. + opts?.overrides || {} + ) + } else { + return this.l2Bridge.populateTransaction.withdrawTo( + toAddress(l2Token), + toAddress(opts.recipient), + amount, + 0, // L1 gas not required. + '0x', // No data. + opts?.overrides || {} + ) + } }, } @@ -283,6 +310,7 @@ export class StandardBridgeAdapter implements IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -297,6 +325,7 @@ export class StandardBridgeAdapter implements IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<BigNumber> => { diff --git a/packages/sdk/src/cross-chain-messenger.ts b/packages/sdk/src/cross-chain-messenger.ts index e1d4b9103..6217dd199 100644 --- a/packages/sdk/src/cross-chain-messenger.ts +++ b/packages/sdk/src/cross-chain-messenger.ts @@ -815,6 +815,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { public async depositETH( amount: NumberLike, opts?: { + recipient?: AddressLike signer?: Signer l2GasLimit?: NumberLike overrides?: Overrides @@ -828,6 +829,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { public async withdrawETH( amount: NumberLike, opts?: { + recipient?: AddressLike signer?: Signer overrides?: Overrides } @@ -842,6 +844,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike signer?: Signer l2GasLimit?: NumberLike overrides?: Overrides @@ -862,6 +865,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike signer?: Signer overrides?: Overrides } @@ -949,6 +953,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { depositETH: async ( amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -964,6 +969,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { withdrawETH: async ( amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> => { @@ -980,6 +986,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -993,6 +1000,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> => { @@ -1047,6 +1055,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { depositETH: async ( amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -1059,6 +1068,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { withdrawETH: async ( amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<BigNumber> => { @@ -1072,6 +1082,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -1091,6 +1102,7 @@ export class CrossChainMessenger implements ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<BigNumber> => { diff --git a/packages/sdk/src/interfaces/bridge-adapter.ts b/packages/sdk/src/interfaces/bridge-adapter.ts index f027197dd..cb1c848fa 100644 --- a/packages/sdk/src/interfaces/bridge-adapter.ts +++ b/packages/sdk/src/interfaces/bridge-adapter.ts @@ -109,6 +109,7 @@ export interface IBridgeAdapter { * @param amount Amount of the token to deposit. * @param signer Signer used to sign and send the transaction. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Transaction response for the deposit transaction. @@ -119,6 +120,7 @@ export interface IBridgeAdapter { amount: NumberLike, signer: Signer, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -132,6 +134,7 @@ export interface IBridgeAdapter { * @param amount Amount of the token to withdraw. * @param signer Signer used to sign and send the transaction. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Transaction response for the withdraw transaction. */ @@ -141,6 +144,7 @@ export interface IBridgeAdapter { amount: NumberLike, signer: Signer, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionResponse> @@ -157,6 +161,7 @@ export interface IBridgeAdapter { * @param l2Token The L2 token address. * @param amount Amount of the token to deposit. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Transaction that can be signed and executed to deposit the tokens. @@ -166,6 +171,7 @@ export interface IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -178,6 +184,7 @@ export interface IBridgeAdapter { * @param l2Token The L2 token address. * @param amount Amount of the token to withdraw. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Transaction that can be signed and executed to withdraw the tokens. */ @@ -186,6 +193,7 @@ export interface IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> @@ -203,6 +211,7 @@ export interface IBridgeAdapter { * @param l2Token The L2 token address. * @param amount Amount of the token to deposit. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Gas estimate for the transaction. @@ -212,6 +221,7 @@ export interface IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -224,6 +234,7 @@ export interface IBridgeAdapter { * @param l2Token The L2 token address. * @param amount Amount of the token to withdraw. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Gas estimate for the transaction. */ @@ -232,6 +243,7 @@ export interface IBridgeAdapter { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<BigNumber> diff --git a/packages/sdk/src/interfaces/cross-chain-messenger.ts b/packages/sdk/src/interfaces/cross-chain-messenger.ts index af73739d6..ba91e3d6c 100644 --- a/packages/sdk/src/interfaces/cross-chain-messenger.ts +++ b/packages/sdk/src/interfaces/cross-chain-messenger.ts @@ -397,6 +397,7 @@ export interface ICrossChainMessenger { * @param amount Amount of ETH to deposit (in wei). * @param opts Additional options. * @param opts.signer Optional signer to use to send the transaction. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Transaction response for the deposit transaction. @@ -405,6 +406,7 @@ export interface ICrossChainMessenger { amount: NumberLike, opts?: { signer?: Signer + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -416,6 +418,7 @@ export interface ICrossChainMessenger { * @param amount Amount of ETH to withdraw. * @param opts Additional options. * @param opts.signer Optional signer to use to send the transaction. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Transaction response for the withdraw transaction. */ @@ -423,6 +426,7 @@ export interface ICrossChainMessenger { amount: NumberLike, opts?: { signer?: Signer + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionResponse> @@ -435,6 +439,7 @@ export interface ICrossChainMessenger { * @param amount Amount to deposit. * @param opts Additional options. * @param opts.signer Optional signer to use to send the transaction. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Transaction response for the deposit transaction. @@ -445,6 +450,7 @@ export interface ICrossChainMessenger { amount: NumberLike, opts?: { signer?: Signer + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -458,6 +464,7 @@ export interface ICrossChainMessenger { * @param amount Amount to withdraw. * @param opts Additional options. * @param opts.signer Optional signer to use to send the transaction. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Transaction response for the withdraw transaction. */ @@ -467,6 +474,7 @@ export interface ICrossChainMessenger { amount: NumberLike, opts?: { signer?: Signer + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionResponse> @@ -534,6 +542,7 @@ export interface ICrossChainMessenger { * * @param amount Amount of ETH to deposit. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Transaction that can be signed and executed to deposit the ETH. @@ -541,6 +550,7 @@ export interface ICrossChainMessenger { depositETH( amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -551,12 +561,14 @@ export interface ICrossChainMessenger { * * @param amount Amount of ETH to withdraw. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Transaction that can be signed and executed to withdraw the ETH. */ withdrawETH( amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> @@ -568,6 +580,7 @@ export interface ICrossChainMessenger { * @param l2Token Address of the L2 token. * @param amount Amount to deposit. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Transaction that can be signed and executed to deposit the tokens. @@ -577,6 +590,7 @@ export interface ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -589,6 +603,7 @@ export interface ICrossChainMessenger { * @param l2Token Address of the L2 token. * @param amount Amount to withdraw. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Transaction that can be signed and executed to withdraw the tokens. */ @@ -597,6 +612,7 @@ export interface ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<TransactionRequest> @@ -661,6 +677,7 @@ export interface ICrossChainMessenger { * * @param amount Amount of ETH to deposit. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Gas estimate for the transaction. @@ -668,6 +685,7 @@ export interface ICrossChainMessenger { depositETH( amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -678,12 +696,14 @@ export interface ICrossChainMessenger { * * @param amount Amount of ETH to withdraw. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Gas estimate for the transaction. */ withdrawETH( amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<BigNumber> @@ -695,6 +715,7 @@ export interface ICrossChainMessenger { * @param l2Token Address of the L2 token. * @param amount Amount to deposit. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L2. Defaults to sender. * @param opts.l2GasLimit Optional gas limit to use for the transaction on L2. * @param opts.overrides Optional transaction overrides. * @returns Gas estimate for the transaction. @@ -704,6 +725,7 @@ export interface ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike l2GasLimit?: NumberLike overrides?: Overrides } @@ -716,6 +738,7 @@ export interface ICrossChainMessenger { * @param l2Token Address of the L2 token. * @param amount Amount to withdraw. * @param opts Additional options. + * @param opts.recipient Optional address to receive the funds on L1. Defaults to sender. * @param opts.overrides Optional transaction overrides. * @returns Gas estimate for the transaction. */ @@ -724,6 +747,7 @@ export interface ICrossChainMessenger { l2Token: AddressLike, amount: NumberLike, opts?: { + recipient?: AddressLike overrides?: Overrides } ): Promise<BigNumber> -- 2.23.0