initiateWithdrawal
Initiates a withdrawal on an L2 to the L1.
Internally performs a contract write to the initiateWithdrawal
function on the Optimism L2ToL1MessagePasser predeploy contract.
Usage
import { base } from 'viem/chains'
import { account, walletClientL2 } from './config'
const hash = await walletClientL2.initiateWithdrawal({
account,
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
import { base } from 'viem/chains'
import { account, walletClientL2 } from './config'
const hash = await walletClientL2.initiateWithdrawal({
account,
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
import { createWalletClient, custom } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet } from 'viem/chains'
import { walletActionsL2 } from 'viem/op-stack'
export const walletClientL2 = createWalletClient({
chain: mainnet,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
// JSON-RPC Account
export const [account] = await walletClientL2.getAddresses()
// Local Account
export const account = privateKeyToAccount(...)
import { createWalletClient, custom } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet } from 'viem/chains'
import { walletActionsL2 } from 'viem/op-stack'
export const walletClientL2 = createWalletClient({
chain: mainnet,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
// JSON-RPC Account
export const [account] = await walletClientL2.getAddresses()
// Local Account
export const account = privateKeyToAccount(...)
WARNING
You must build the parameters on the L1 before calling this function. If the gas is too low, transaction execution will fail on the L1.
Building Parameters
The buildInitiateWithdrawal
Action builds & prepares the initiate withdrawal transaction parameters.
We can use the resulting args
to initiate the withdrawal transaction on the L2.
import { account, publicClientL1, walletClientL2 } from './config'
const args = await publicClientL1.buildInitiateWithdrawal({
account,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1'),
})
const hash = await walletClientL2.initiateWithdrawal(args)
import { account, publicClientL1, walletClientL2 } from './config'
const args = await publicClientL1.buildInitiateWithdrawal({
account,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1'),
})
const hash = await walletClientL2.initiateWithdrawal(args)
import { createPublicClient, createWalletClient, custom, http } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet, optimism } from 'viem/chains'
import { publicActionsL1, walletActionsL2 } from 'viem/op-stack'
export const publicClientL1 = createPublicClient({
chain: mainnet,
transport: http()
}).extend(publicActionsL1())
export const walletClientL2 = createWalletClient({
chain: optimism,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
// JSON-RPC Account
export const [account] = await walletClientL1.getAddresses()
// Local Account
export const account = privateKeyToAccount(...)
import { createPublicClient, createWalletClient, custom, http } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet, optimism } from 'viem/chains'
import { publicActionsL1, walletActionsL2 } from 'viem/op-stack'
export const publicClientL1 = createPublicClient({
chain: mainnet,
transport: http()
}).extend(publicActionsL1())
export const walletClientL2 = createWalletClient({
chain: optimism,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
// JSON-RPC Account
export const [account] = await walletClientL1.getAddresses()
// Local Account
export const account = privateKeyToAccount(...)
See more on the buildInitiateWithdrawal
Action.
Account Hoisting
If you do not wish to pass an account
to every proveWithdrawal
, you can also hoist the Account on the Wallet Client (see config.ts
).
import { account, publicClientL1, walletClientL2 } from './config'
const args = await publicClientL1.buildInitiateWithdrawal({
account,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1'),
})
const hash = await walletClientL2.initiateWithdrawal(args)
import { account, publicClientL1, walletClientL2 } from './config'
const args = await publicClientL1.buildInitiateWithdrawal({
account,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1'),
})
const hash = await walletClientL2.initiateWithdrawal(args)
import { createWalletClient, createPublicClient, custom, http } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet, optimism } from 'viem/chains'
import { publicActionsL1, walletActionsL2 } from 'viem/op-stack'
// Retrieve Account from an EIP-1193 Provider.
const [account] = await window.ethereum.request({
method: 'eth_requestAccounts'
})
export const publicClientL1 = createPublicClient({
chain: mainnet,
transport: http()
}).extend(publicActionsL1())
export const walletClientL2 = createWalletClient({
account,
chain: optimism,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
import { createWalletClient, createPublicClient, custom, http } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet, optimism } from 'viem/chains'
import { publicActionsL1, walletActionsL2 } from 'viem/op-stack'
// Retrieve Account from an EIP-1193 Provider.
const [account] = await window.ethereum.request({
method: 'eth_requestAccounts'
})
export const publicClientL1 = createPublicClient({
chain: mainnet,
transport: http()
}).extend(publicActionsL1())
export const walletClientL2 = createWalletClient({
account,
chain: optimism,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
import { createPublicClient, createWalletClient, custom, http } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet, optimism } from 'viem/chains'
import { publicActionsL1, walletActionsL2 } from 'viem/op-stack'
export const publicClientL1 = createPublicClient({
chain: mainnet,
transport: http()
}).extend(publicActionsL1())
export const walletClientL2 = createWalletClient({
account: privateKeyToAccount('0x...'),
chain: optimism,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
import { createPublicClient, createWalletClient, custom, http } from 'viem'
import { privateKeyToAccount } from 'viem/accounts'
import { mainnet, optimism } from 'viem/chains'
import { publicActionsL1, walletActionsL2 } from 'viem/op-stack'
export const publicClientL1 = createPublicClient({
chain: mainnet,
transport: http()
}).extend(publicActionsL1())
export const walletClientL2 = createWalletClient({
account: privateKeyToAccount('0x...'),
chain: optimism,
transport: custom(window.ethereum)
}).extend(walletActionsL2())
Returns
The L2 Transaction hash.
Parameters
account
- Type:
Account | Address
The Account to send the transaction from.
Accepts a JSON-RPC Account or Local Account (Private Key, etc).
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
targetChain: base,
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
targetChain: base,
})
args.data (optional)
- Type:
Hex
Encoded contract method & arguments.
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
data: '0x...',
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
data: '0x...',
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
args.gas
- Type:
bigint
Gas limit for transaction execution on the L1.
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
args.to
- Type:
Address
L1 Transaction recipient.
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
args.value (optional)
- Type:
bigint
Value in wei to withdrawal from the L2 to the L1. Debited from the caller's L2 balance.
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
})
chain (optional)
- Type:
Chain
- Default:
client.chain
The L2 chain. If there is a mismatch between the wallet's current chain & this chain, an error will be thrown.
import { optimism } from 'viem/chains'
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
chain: optimism,
})
import { optimism } from 'viem/chains'
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
chain: optimism,
})
maxFeePerGas (optional)
- Type:
bigint
Total fee per gas (in wei), inclusive of maxPriorityFeePerGas
.
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
maxFeePerGas: parseGwei('20'),
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
maxFeePerGas: parseGwei('20'),
})
maxPriorityFeePerGas (optional)
- Type:
bigint
Max priority fee per gas (in wei). Only applies to EIP-1559 Transactions
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
maxFeePerGas: parseGwei('20'),
maxPriorityFeePerGas: parseGwei('2'),
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
maxFeePerGas: parseGwei('20'),
maxPriorityFeePerGas: parseGwei('2'),
})
nonce (optional)
- Type:
number
Unique number identifying this transaction.
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
nonce: 69,
})
const hash = await client.initiateWithdrawal({
account: '0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266',
request: {
gas: 21_000n,
to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
value: parseEther('1')
},
nonce: 69,
})