Batch Transactions for EOAs
Supercharged EOAs will save millions of dollars & cement the EVM's network effects
An externally-owned-address (EOA) is what most people call a Metamask wallet. It makes direct transactions using a private key. Unlike smart contract wallets like a gnosis safe or ERC-4337 wallet, an EOA has no code. If you’ve sent an Ethereum transaction, you probably did it from an EOA wallet.
The UX leaves much to be desired. Who among us hasn’t asked, “Why do I need to do this approval just to buy a token on uniswap?” The two-step process is confusing and insecure. It’s even more convoluted for medium-complexity tasks like withdrawing from one protocol and depositing into another. The process is so annoying that entire protocols (Zaps) have spun up to ease the pain.
It doesn’t have to be like this - batch transactions for EOAs are the key Ethereum upgrade that can make daily interactions faster, safer, and cheaper. Simply put, batch transaction upgrades would let EOAs act like a smart contract without deploying one. Let’s explore how batch transactions:
1) Fix stale approval attacks
2) Reduce state growth
3) Remove trusted intermediaries
Why Batch Transactions
Batch Transactions Fix Stale Approval Attacks
In December 2023 we saw back-to-backs on NFT finance protocols. First NFTTrader was hit for 50 apes + mutants on a contract nearly two years old. Then Floor Protocol saw 40 penguins drained, plus more apes and azukis. In Jan 2023 we saw the Bungee/Socket bridge hit for another $5 million. These mass exploits weren’t phishing attacks. They didn’t use malicious signatures. They didn’t drain protocol assets. The common thread? Stale approvals.
Note the key adjective stale. ERC20/721/1155 approvals are valid until explicitly revoked, they can last for months and years. This fits with some usecases such as marketplace bids and offers, but is the wrong behavior for the more common usecase of depositing an asset into a protocol and receiving proper attribution for it.
For example, a user wants to deposit a bored ape into Floor Protocol and receive μBAYC tokens. The median nontechnical crypto user thinks it happens like this: send ape to protocol, then get tokens. Surprisingly, this is wrong! How it actually works: approve protocol to move all my apes forever, then ask protocol to move my ape into itself, then get tokens.
Not only is this an annoying UX (two transactions instead of one), it’s a gigantic security risk. The approval still exists forever until explicitly revoked, even if I withdraw my ape from the protocol and never use the protocol again. An end user might think they’re safe since they “stopped using” the protocol. But they are still at risk! The asset they approved can be stolen in case of a protocol exploit, and more likely all assets in the relevant collection have been approved and are at risk of being stolen too.
With batch transactions, users can do direct deposit of ERC20/721 then trigger receiver functions in the protocol with no risk of unbundling, no approval required. Even if the approval pattern persists, users are far more likely to only approve the necessary amount because we’ve removed extra clicks.
Batch Transactions Reduce State Growth
An underlooked side effect of sequential transactions is unnecessary state growth bloat. Each transaction uses a minimum of 21,000 gas to account for overhead of transaction validity checks, even if its storage slot usage is minimal. Grouping into fewer transactions to verify reduces mempool and ordering overhead.
Another underappreciated aspect of batch transactions: they reduce gas volatility and act as a pseudo-1559 UX improvement. When a human user goes to manually make a sequence of transactions using a frontend website, such as (1) approve USDT; (2) swap for wstETH; (3) deposit wstETH on Aave, they must wait for each transaction to be included before submitting the next. To get on with their day, users must pay for immediate inclusion of the first few methods - approve, swap, etc, and can only let the final transaction sit for hours. Users overpay for inclusion of the first tx in a sequence.
With batch transactions, nontechnical users can queue up a whole sequence of actions and set a low basefee, waiting several hours to execute noncritical transactions for cheaper and alleviating congestion during peak hours. Removing transaction overhead for sequential transactions will also use less state for the same sequential actions than the status quo.
Batch Transactions Remove Trusted Intermediaries
Among sophisticated users making rivalrous transactions, private mempool usage dominates the public one. A key element of this is transaction ordering. Many MEV actors depend on specific transaction ordering or they can lose millions. Another simple example, consider a scenario where a team needs to initialize a lending pool then seed it with some de minimis amount of liquidity to prevent rounding error attacks. As it stands, they’re reliant on a combination of reputational goodwill and previously-hacked TEE hardware for their relay to enforce transaction sequencing within a block, the core Ethereum consensus mechanism does no such thing. Enshrining batch transactions into the protocol itself removes any risk whatsoever of a malicious unbundler and makes relaying more open by removing the need for reputation-as-collateral.
With batch transactions, users could send (their own) sequenced transactions to private relays like Flashbots/Manifold/bloXroute with guarantees that even a malicious relay would be unable to unbundle the sequence. This reduces tail risk and makes relaying more competitive since there’s less need to rely on relayer reputation.
Why EOAs Matter in a 4337 World
Smart contract wallets are welcome infrastructure, but EOAs remain >90% of all addresses. Several reasons for this - cheaper gas, familiarity, wallet support, counterfactual multichain addresses, compatibility with msg.sender == tx.origin checks, compatibility with EIP-712 message signing. Can smart contract wallets address these problems in due time? Potentially! But this will be a multiyear rollout process before there’s even sufficient maturity for most users to consider migrating. In the meantime, the path-dependent blockchain wars rage on and the EVM must supercharge EOAs to remain an attractive option. Far from competing, lightclients points out that EIP-3074 makes EOAs compatible with 4337!
From a censorship resistance and permissionless perspective, creating an EOA is a trivial off-chain activity which can take place on any device, doesn’t require connectivity and doesn’t require any funds or sponsor. Creating an account with a contract wallet requires either a funded EOA to start from or a sponsor.
Counterpoints
“We should be moving beyond EOAs, not enshrining them even further” - This is a mindset of jealousy not growth. I hope smart contract wallets thrive, but dangerous to do so by handicapping EOA functionality and fearfully blocking improvements. Nobody would suggest crippling existing EOA functionality so SC wallets can grow; likewise, we should not reject EOA improvements proposals so SC wallets can grow. EOAs were already enshrined in the core protocol on day 1, improving them is just that - an improvement not an enshrinement.
“Batch transactions are a new security risk since users can lose all their assets at once” - The rise of aggregator apps like Uniswap’s permit2 and Seaport/Blur’s batch orders means a single malicious EIP-712 signature already drains most of the user’s assets. Batch transactions are actually an improvement from this status quo, since as an onchain transaction rather than an offchain signature wallets can simulate and display the results. In fact, lack of batch transactions has harmed users when they go to revoke.cash and have to do one-at-a-time revokes instead of revoking everything at once. Even experienced aligned devotees are confused. The cure here is improved wallet simulation not handicapping the EOA experience.
“4337 wallets already have batching” - 4337 is a noble cause, but EOAs are 99.9% of users and will be 90%+ for the next several years. EOAs offer critical features by default like identical counterfactual addresses on all chains and cheaper gas than the most optimized smart contract wallet. Most importantly, they are the dominant usecase today, and cannot be abandoned yet in favor of an unproven future. I hope 4337 succeeds; in the meantime the default EOA experience must be focused on and improved in tandem. Path dependency matters, Ethereum should not lose focus on its current users.
“Batch transactions don’t enable sponsored paymasters” - Correct, but we should not let the absence of one good thing torpedo a proposal for a completely different good thing. There are many avenues to paymaster sponsorship, batch transactions should not be blocked by this.
Which EIP is Best?
EIP-3074 by lightclients: Use ECDSA signatures for an EOA to delegate control of its own account to a smart contract with the AUTH and AUTHCALL opcodes. There are concerns about how to revoke these, and about multichain replay attacks.
alternative EIP-3074 by yoav weiss: Instead of AUTH’ing a specific contract to do actions on the EOA’s behalf, have the EOA sign each specific call it wants to be AUTH’d. This reduces the invoker trust surface.
EIP-5806 by hadrien croubois: Add a new transaction type that allows an EOA to execute arbitrary code directly by simply delegatecall’ing another contract, no invoker permissions needed whatsoever.
EOA batch transactions should be implemented by the simplest means possible. My personal ranking is (1) 5806; (2) alternative 3074; (3) 3074. However this ranking is secondary to an incredibly strong conviction that EOA batch transactions of some sort need to ship in the next hardfork. EIP-5806 does not introduce the need for any novel canonical singleton invoker middleware; several multicall implementations are well-verified and deployed on mainnet. If 3074 is chosen, then the authorization is a pesky implementation detail rather than a feature, and should be atomically scoped to that single transaction rather than persistent (otherwise we’ve reinvented stale approvals under another name, or simply enshrined permit2 with all its offchain signature risks).
In any case, Ethereum is ossifying and EVM improvements will have outsized benefits on L1s and L2s far beyond Ethereum itself. Supercharged EOAs are a necessity at the Ethereum level itself to coordinate among all the wallet and dapp infra, it’s a responsibility too important to push to L2 RIPs. There’s a critical need to ship these core improvements for the default flow before it’s too late. Shipping some form of EOA batch transaction in Prague/Electra is a necessity to protect retail users, help with state growth, and reduce reliance on trusted third parties. Call your local core dev today!