How to calculate UserOperation's costs using the ERC-20 Paymaster | Pimlico Docs
Skip to content

How to calculate UserOperation's costs using the ERC-20 Paymaster

This guide will show you how to estimate your user operation's cost in denomination of the ERC-20 token as well as USD.

When using Pimlico's ERC-20 Paymaster, the pimlico_getTokenQuotes endpoint helps you calculate the cost of your userOperation. It returns values exchangeRate and exchangeRateNativeToUsd. These are useful for determining how much to approve upfront or for displaying the cost to your users.

Steps

Define imports and create the clients

import { createSmartAccountClient } from "permissionless";
import { toSafeSmartAccount } from "permissionless/accounts";
import { createPimlicoClient } from "permissionless/clients/pimlico";
import { createPublicClient, formatUnits, http } from "viem";
import { privateKeyToAccount } from "viem/accounts";
import { entryPoint07Address } from "viem/account-abstraction";
import { base } from "viem/chains";
import { prepareUserOperationForErc20Paymaster } from "permissionless/experimental/pimlico";
 
const chain = base;
 
export const publicClient = createPublicClient({
	chain,
	transport: http("https://mainnet.base.org"),
});
 
const pimlicoUrl = `https://api.pimlico.io/v2/${chain.id}/rpc?apikey=${process.env.PIMLICO_API_KEY}`;
 
const pimlicoClient = createPimlicoClient({
	chain,
	transport: http(pimlicoUrl),
	entryPoint: {
		address: entryPoint07Address,
		version: "0.7",
	},
});
 
const account = await toSafeSmartAccount({
	client: publicClient,
	owners: [
		privateKeyToAccount(
			"0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
		),
	],
	entryPoint: {
		address: entryPoint07Address,
		version: "0.7",
	},
	version: "1.4.1",
});
 
const smartAccountClient = createSmartAccountClient({
	account,
	chain,
	bundlerTransport: http(pimlicoUrl),
	paymaster: pimlicoClient,
	userOperation: {
		estimateFeesPerGas: async () => {
			return (await pimlicoClient.getUserOperationGasPrice()).fast;
		},
		prepareUserOperation: prepareUserOperationForErc20Paymaster(pimlicoClient),
	},
});

Prepare the user operation

Prepare the user operation for the calls you want to make.

const token = "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913";
const tokenDecimals = 6;
 
const userOperation = await smartAccountClient.prepareUserOperation({
	calls: [
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: 0n,
			data: "0x1234",
		},
	],
	paymasterContext: {
		token,
	},
});
 

Calculate your userOperation's cost

To find the cost of your userOperation in denomination of the ERC-20 & USD, you should use pimlico client's estimateErc20PaymasterCost action.

 
const { costInToken, costInUsd } =
	await pimlicoClient.estimateErc20PaymasterCost({
		userOperation,
		token,
	});
 
// constInToken is in token decimals
const humanReadableCostInToken = formatUnits(costInToken, tokenDecimals);
 
// costInUsd is ALWAYS in 6 decimals
const humanReadableCostInUSD = formatUnits(costInUsd, 6); // this should output $1.05
 

Note: We divide costInUsd is always returned with 6 decimal places and you must format it before displaying it to the user wih formatUnits(costInUsd, 6).