Common Hooks
A reference to preset hook functions for an Account to call into when building UserOperations.
As briefly mentioned in the Quickstart guide, every User Operation typically follows the same high level steps during its build lifecycle. When configuring Account Options, we can implement these hook functions to return the relevant value for each area of a User Operation that is suited for a particular Smart Account implementation.
For V06
, these hooks include:
Hook | Description |
---|---|
setFactoryData | Value used to generate initCode and derive sender address. |
requestSignature | Directly used to set the signature field. |
requestGasPrice | Directly used to set the maxFeePerGas and maxPriorityFeePerGas . |
requestGasValues | Directly used to set preVerificationGas , verificationGasLimit , and callGasLimit . |
requestPaymaster | Directly used to set paymasterAndData and other other optional field required by the paymaster. |
onBuild | Called once the final User Operation has been built. |
There are certain use cases where a single hook can be reused in many different implementations. For these cases we package them up in the presets detailed below.
RequestSignature
RequestSignature
These preset hooks are available for common signature use cases.
withViemWalletClient
withViemWalletClient
Uses the signMessage
function on a given viem WalletClient
to create a User Operation signature.
import { V06 } from "userop";
const account = new V06.Account.Instance({
// Account opts...
requestSignature: V06.Account.Hooks.RequestSignature.withViemWalletClient(
viemWalletClient,
// Pass viem Account if not yet hoisted in the WalletClient
),
})
withEthersSigner
withEthersSigner
Uses the signMessage
function on a given ethers.js Signer
to create a User Operation signature.
import { V06 } from "userop";
const account = new V06.Account.Instance({
// Account opts...
requestSignature: V06.Account.Hooks.RequestSignature.withEthersSigner(ethersSigner),
})
RequestGasPrice
RequestGasPrice
These preset hooks are available for common gas fee logic.
withEthClient
withEthClient
Uses an instance of a viem PublicClient
or ethers.js JsonRpcProvider
to fetch the latest gas prices. This hook will attempt to set EIP-1559 gas prices using the given heuristics:
const maxFeePerGas = currentBlockBaseFee * 2 + maxPriorityFeePerGas
The currentBlockBaseFee
is derived from eth_getBlockByNumber
and maxPriorityFeePerGas
from eth_maxPriorityFeePerGas
. The priority fee allows for timely inclusion while the max fee allows for the User Operation to be marketable longer in case of spikes in network activity. If the network does not support EIP-1559, it will fallback to legacy gas prices with eth_gasPrice
.
This is the default gas price hook used by an Account
instance.
import { V06 } from "userop";
const account = new V06.Account.Instance({
// Account opts...
requestGasPrice: V06.Account.Hooks.RequestGasPrice.withEthClient(
viemPublicClient, // will also accept an ethers.js JsonRpcProvider
),
})
RequestGasValues
RequestGasValues
These preset hooks are available for common gas value logic.
withEthClient
withEthClient
Uses an instance of viem PublicClient
or ethers.js JsonRpcProvider
to estimate User Operation gas using the Bundler's eth_estimateUserOperationGas
RPC method.
This is the default gas value hook used by an Account
instance.
import { V06 } from "userop";
const account = new V06.Account.Instance({
// Account opts...
requestGasValues: V06.Account.Hooks.RequestGasValues.withEthClient(
viemPublicClient, // will also accept an ethers.js JsonRpcProvider
),
})
RequestPaymaster
RequestPaymaster
These preset hooks are available for common paymaster implementations.
withCommon
withCommon
Given a PaymasterOpts
, it will generate a User Operation with a Paymaster for gas abstraction.
Configuring this hook will depend on the underlying Paymaster used.
import { V06 } from "userop";
const account = new V06.Account.Instance({
// Account opts...
requestPaymaster: V06.Account.Hooks.RequestPaymaster.withCommon({
variant: "stackupV1",
parameters: {
rpcUrl: STACKUP_V1_PM_RPC,
type: "payg",
},
}),
})
import { V06 } from "userop";
const account = new V06.Account.Instance({
// Account opts...
requestPaymaster: V06.Account.Hooks.RequestPaymaster.withCommon({
variant: "stackupV1",
parameters: {
rpcUrl: STACKUP_V1_PM_RPC,
type: "erc20token",
token: TOKEN_ADDRESS,
},
}),
})
Updated 8 months ago