From 66b3bf177abd7df39936b941a8e3844c03233d04 Mon Sep 17 00:00:00 2001 From: souradeep-das Date: Wed, 10 Jan 2024 14:30:12 +0530 Subject: [PATCH] feat: minor changes to aa bundler --- packages/boba/bundler/src/BundlerCollectorTracer.ts | 4 ++-- .../boba/bundler/src/modules/ExecutionManager.ts | 2 +- packages/boba/bundler/src/modules/MempoolManager.ts | 12 ++++++++---- .../boba/bundler/src/modules/ReputationManager.ts | 2 +- packages/boba/bundler/src/parseScannerResult.ts | 2 ++ packages/boba/bundler_sdk/README.md | 10 +++++----- .../boba/bundler_sdk/src/ERC4337EthersProvider.ts | 4 ++-- packages/boba/bundler_sdk/src/SimpleAccountAPI.ts | 6 +++--- packages/boba/bundler_sdk/src/index.ts | 1 + 9 files changed, 25 insertions(+), 18 deletions(-) diff --git a/packages/boba/bundler/src/BundlerCollectorTracer.ts b/packages/boba/bundler/src/BundlerCollectorTracer.ts index c7527fed04..1819180420 100644 --- a/packages/boba/bundler/src/BundlerCollectorTracer.ts +++ b/packages/boba/bundler/src/BundlerCollectorTracer.ts @@ -144,7 +144,7 @@ export function bundlerCollectorTracer(): BundlerCollectorTracer { this.calls.push({ type: frame.getError() != null ? 'REVERT' : 'RETURN', gasUsed: frame.getGasUsed(), - data: toHex(frame.getOutput()).slice(0, 1000), + data: toHex(frame.getOutput()).slice(0, 4000), }) }, @@ -165,7 +165,7 @@ export function bundlerCollectorTracer(): BundlerCollectorTracer { // from opcode const ofs = parseInt(log.stack.peek(0).toString()) const len = parseInt(log.stack.peek(1).toString()) - const data = toHex(log.memory.slice(ofs, ofs + len)).slice(0, 1000) + const data = toHex(log.memory.slice(ofs, ofs + len)).slice(0, 4000) // this.debug.push(opcode + ' ' + data) this.calls.push({ type: opcode, diff --git a/packages/boba/bundler/src/modules/ExecutionManager.ts b/packages/boba/bundler/src/modules/ExecutionManager.ts index 3a46102d2e..ea9fb61df8 100644 --- a/packages/boba/bundler/src/modules/ExecutionManager.ts +++ b/packages/boba/bundler/src/modules/ExecutionManager.ts @@ -69,7 +69,7 @@ export class ExecutionManager { this.autoInterval = autoBundleInterval if (autoBundleInterval !== 0) { this.autoBundleInterval = setInterval(() => { - void this.attemptBundle(true) + void this.attemptBundle(true).catch(e => console.error('auto-bundle failed', e)) }, autoBundleInterval * 1000) } this.maxMempoolSize = maxMempoolSize diff --git a/packages/boba/bundler/src/modules/MempoolManager.ts b/packages/boba/bundler/src/modules/MempoolManager.ts index 1adafaf8dd..bd658b15f0 100644 --- a/packages/boba/bundler/src/modules/MempoolManager.ts +++ b/packages/boba/bundler/src/modules/MempoolManager.ts @@ -77,11 +77,15 @@ export class MempoolManager { } private checkReplaceUserOp (oldEntry: MempoolEntry, entry: MempoolEntry): void { - const oldGas = BigNumber.from(oldEntry.userOp.maxPriorityFeePerGas).toNumber() - const newGas = BigNumber.from(entry.userOp.maxPriorityFeePerGas).toNumber() + const oldMaxPriorityFeePerGas = BigNumber.from(oldEntry.userOp.maxPriorityFeePerGas).toNumber() + const newMaxPriorityFeePerGas = BigNumber.from(entry.userOp.maxPriorityFeePerGas).toNumber() + const oldMaxFeePerGas = BigNumber.from(oldEntry.userOp.maxFeePerGas).toNumber() + const newMaxFeePerGas = BigNumber.from(entry.userOp.maxFeePerGas).toNumber() // the error is "invalid fields", even though it is detected only after validation - requireCond(newGas > oldGas * 1.1, - `Replacement UserOperation must have higher gas (old=${oldGas} new=${newGas}) `, ValidationErrors.InvalidFields) + requireCond(newMaxPriorityFeePerGas >= oldMaxPriorityFeePerGas * 1.1, + `Replacement UserOperation must have higher maxPriorityFeePerGas (old=${oldMaxPriorityFeePerGas} new=${newMaxPriorityFeePerGas}) `, ValidationErrors.InvalidFields) + requireCond(newMaxFeePerGas >= oldMaxFeePerGas * 1.1, + `Replacement UserOperation must have higher maxFeePerGas (old=${oldMaxFeePerGas} new=${newMaxFeePerGas}) `, ValidationErrors.InvalidFields) } getSortedForInclusion (): MempoolEntry[] { diff --git a/packages/boba/bundler/src/modules/ReputationManager.ts b/packages/boba/bundler/src/modules/ReputationManager.ts index 6c21092fca..780b000166 100644 --- a/packages/boba/bundler/src/modules/ReputationManager.ts +++ b/packages/boba/bundler/src/modules/ReputationManager.ts @@ -136,7 +136,7 @@ export class ReputationManager { if (entry == null) { return ReputationStatus.OK } - const minExpectedIncluded = Math.min(entry.opsSeen / this.params.minInclusionDenominator) + const minExpectedIncluded = Math.floor(entry.opsSeen / this.params.minInclusionDenominator) if (minExpectedIncluded <= entry.opsIncluded + this.params.throttlingSlack) { return ReputationStatus.OK } else if (minExpectedIncluded <= entry.opsIncluded + this.params.banSlack) { diff --git a/packages/boba/bundler/src/parseScannerResult.ts b/packages/boba/bundler/src/parseScannerResult.ts index 18d94d5be2..bd48042bdc 100644 --- a/packages/boba/bundler/src/parseScannerResult.ts +++ b/packages/boba/bundler/src/parseScannerResult.ts @@ -213,6 +213,8 @@ export function parseScannerResult( 'CREATE', 'COINBASE', 'SELFDESTRUCT', + 'RANDOM', + 'PREVRANDAO', ]) // eslint-disable-next-line @typescript-eslint/no-base-to-string diff --git a/packages/boba/bundler_sdk/README.md b/packages/boba/bundler_sdk/README.md index 17bc011bc7..670b63a544 100644 --- a/packages/boba/bundler_sdk/README.md +++ b/packages/boba/bundler_sdk/README.md @@ -18,7 +18,7 @@ An abstract base-class to create UserOperation for a contract wallet. ### SimpleWalletAPI -An implementation of the BaseWalletAPi, for the SimpleWallet sample of account-abstraction. +An implementation of the BaseWalletAPI, for the SimpleWallet sample of account-abstraction. ```typescript owner = provider.getSigner() @@ -28,7 +28,7 @@ const walletAPI = new SimpleWalletAPI({ owner, factoryAddress }) -const op = await walletAPi.createSignedUserOp({ +const op = await walletAPI.createSignedUserOp({ target: recipient.address, data: recipient.interface.encodeFunctionData('something', ['hello']) }) @@ -39,20 +39,20 @@ const op = await walletAPi.createSignedUserOp({ A simplified mode that doesn't require a different wallet extension. Instead, the current provider's account is used as wallet owner by calling its "Sign Message" operation. -This can only work for wallets that use an EIP-191 ("Ethereum Signed Message") signatures (like our sample SimpleWallet) +This can only work for wallets that use an EIP-191 ("Ethereum Signed Message") signature (like our sample SimpleWallet) Also, the UX is not great (the user is asked to sign a hash, and even the wallet address is not mentioned, only the signer) ```typescript import { wrapProvider } from '@bobanetwork/bundler_sdk' //use this account as wallet-owner (which will be used to sign the requests) -const signer = provider.getSigner() +const aaSigner = provider.getSigner() const config = { chainId: await provider.getNetwork().then(net => net.chainId), entryPointAddress, bundlerUrl: 'http://localhost:3000/rpc' } -const aaProvider = await wrapProvider(provider, config, aasigner, entryPointWrapperAddress) +const aaProvider = await wrapProvider(provider, config, aaSigner, entryPointWrapperAddress) const walletAddress = await aaProvider.getSigner().getAddress() // send some eth to the wallet Address: wallet should have some balance to pay for its own creation, and for calling methods. diff --git a/packages/boba/bundler_sdk/src/ERC4337EthersProvider.ts b/packages/boba/bundler_sdk/src/ERC4337EthersProvider.ts index bd0a3f18cb..16f7c2fa56 100644 --- a/packages/boba/bundler_sdk/src/ERC4337EthersProvider.ts +++ b/packages/boba/bundler_sdk/src/ERC4337EthersProvider.ts @@ -128,7 +128,7 @@ export class ERC4337EthersProvider extends BaseProvider { this.config.entryPointAddress, this.chainId ) - const waitPromise = new Promise((resolve, reject) => { + const waitForUserOp = async (): Promise => await new Promise((resolve, reject) => { new UserOperationEventListener( resolve, reject, @@ -148,7 +148,7 @@ export class ERC4337EthersProvider extends BaseProvider { data: hexValue(userOp.callData), // should extract the actual called method from this "execFromEntryPoint()" call chainId: this.chainId, wait: async (confirmations?: number): Promise => { - const transactionReceipt = await waitPromise + const transactionReceipt = await waitForUserOp() if (userOp.initCode.length !== 0) { // checking if the wallet has been deployed by the transaction; it must be if we are here await this.smartAccountAPI.checkAccountPhantom() diff --git a/packages/boba/bundler_sdk/src/SimpleAccountAPI.ts b/packages/boba/bundler_sdk/src/SimpleAccountAPI.ts index 032661cb98..7280b9678a 100644 --- a/packages/boba/bundler_sdk/src/SimpleAccountAPI.ts +++ b/packages/boba/bundler_sdk/src/SimpleAccountAPI.ts @@ -18,7 +18,7 @@ import { BaseApiParams, BaseAccountAPI } from './BaseAccountAPI' export interface SimpleAccountApiParams extends BaseApiParams { owner: Signer factoryAddress?: string - index?: number + index?: BigNumberish } @@ -32,7 +32,7 @@ export interface SimpleAccountApiParams extends BaseApiParams { export class SimpleAccountAPI extends BaseAccountAPI { factoryAddress?: string owner: Signer - index: number + index: BigNumberish /** * our account contract. @@ -46,7 +46,7 @@ export class SimpleAccountAPI extends BaseAccountAPI { super(params) this.factoryAddress = params.factoryAddress this.owner = params.owner - this.index = params.index ?? 0 + this.index = BigNumber.from(params.index ?? 0) } async _getAccountContract (): Promise { diff --git a/packages/boba/bundler_sdk/src/index.ts b/packages/boba/bundler_sdk/src/index.ts index ff4aa6e1bd..eabae18946 100644 --- a/packages/boba/bundler_sdk/src/index.ts +++ b/packages/boba/bundler_sdk/src/index.ts @@ -1,3 +1,4 @@ +export { BaseAccountAPI } from './BaseAccountAPI' export { SimpleAccountAPI } from './SimpleAccountAPI' export { PaymasterAPI } from './PaymasterAPI' export { wrapProvider } from './Provider'