Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add transformer that converts 4337 User Ops -> pseudo transactions #291

Merged
merged 7 commits into from
Apr 18, 2024

Conversation

datadanne
Copy link
Collaborator

@datadanne datadanne commented Apr 8, 2024

Notes

  • May need to add more accounts in the future
  • We do support multiple user ops per transaction for the same account currently.
  • handleAggregatedOps - if the bundler bundles multiple ops from different accounts into one root transaction, we don't support that

Next steps

  • Deploy this code in the API so that we can return pseudotransactions, with assetTransfers and net asset transfers for each.
  • Generate test data for contextualizers.
  • One new PR to consume pseudotransactions for a single tx and run context on it.
  • Create new contextualizer for transactions that include user ops
  • Outside of the repo, will need to call contextualizers on pseudotransactions. User op hash is returned in a field called meta
  • Modify all to return new objects rather than passing by reference and modifying

How it works

  1. Split all User Operations from transactions sent to the ERC4337 entrypoint into separate 'UserOp transactions' (1 transaction to the entrypoint can include multiple user operations). This steps also removes log entries from the entry point contract and the eth transfer from the entry point to the bundler that submitted the transaction since those are not relevant to the user operation

  2. Decode the call from the entry point to the smart account contract. Smart account contracts all contain functions that the entry point calls that then executes the user operation, so we need to decode that function call and get the arguments from that to get to what the user wants to do. There are lots of different account implementations where the entrypoint fn signature differ slightly but do the same thing:

    function execute(address,uint256,bytes)                       // 0xb61d27f6
    function execute(address[],uint256[],bytes[])                 // 0xa516a5bf
    function execute(address,uint256,bytes,uint8)                 // 0x51945447
    function executeBatch((address,uint256,bytes)[])              // 0x34fcd5be
    function execTransactionFromEntrypoint(address,uint256,bytes) // 0x70641a22
    function executeBatch(address[],uint256[],bytes[])            // 0x47e1da2a

After these two steps the existing contextualizers can use the same logic as for non-ERC4337 transactions to give context to the transaction, I've included examples for a token approval, token transfer, eth transfer and an nft mint.

This WIP implementation only supports transactions where each user operation only contains "one action" (either just execute or executeBatch with just one action)

The diff is best viewed with whitespace hidden (https://github.com/Once-Upon/context/pull/291/files?diff=unified&w=1)

accessing the transformer from children using children[key] returns a
value of type any since key isn't a const so the type of children[key]
cannot be known
most transformers don't need the block and can operate on one
transaction at a time
src/helpers/utils.ts Show resolved Hide resolved
src/transformers/_common/assetTransfers.ts Show resolved Hide resolved
sigHash: String(trace.action.input).slice(0, 10),
}));
export const transform: TxnTransformer = (_block, tx) => {
if (!isRawTransaction(tx)) return tx;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@datadanne Why was this needed for this one but not for the others?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you find anything based on this investigation, we can circle back in a follow-up PR. This doesn't need to block merging.

@pcowgill pcowgill merged commit 59ca0ac into main Apr 18, 2024
2 checks passed
@pcowgill pcowgill deleted the account-abstraction branch April 18, 2024 16:27
@pcowgill pcowgill mentioned this pull request Apr 18, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants