From e8a528b99a61192e8b22858196980c0857d936de Mon Sep 17 00:00:00 2001 From: Sahil Vasava Date: Tue, 16 Apr 2024 03:37:24 +0530 Subject: [PATCH 1/2] feat: added encodeModuleInstallCallData to kernelAccount, a flow for enabling recovery using that | updated to latest permissionless and viem with getAction bug fix --- bun.lockb | Bin 210248 -> 211728 bytes .../accounts/kernel/createKernelAccount.ts | 22 +++- .../ep0_6/encodeModuleInstallCallData.ts | 35 +++++ .../utils/account/ep0_7/getKernelV3Nonce.ts | 5 +- .../ep0_6/getPluginsEnableTypedData.ts | 1 - .../plugins/ep0_7/isPluginInitialized.ts | 5 +- .../kernel/v1/createKernelV1Account.ts | 3 + .../kernel/v2/createKernelV2Account.ts | 22 +--- packages/core/accounts/utils/6492.ts | 5 +- .../accounts/utils/toKernelPluginManager.ts | 19 +++ .../account-client/signUserOperation.ts | 5 +- packages/core/package.json | 4 +- packages/core/types/kernel.ts | 19 ++- packages/core/utils.ts | 3 +- packages/presets/package.json | 4 +- packages/test/package.json | 4 +- packages/test/recoveryKernelAccount.test.ts | 124 ++++++++++++++++++ packages/test/utils.ts | 41 +++++- packages/test/v0.7/ecdsaKernelAccount.test.ts | 8 +- plugins/ecdsa/package.json | 4 +- plugins/modularPermission/package.json | 4 +- .../toModularPermissionValidatorPlugin.ts | 16 +-- plugins/passkey/package.json | 4 +- plugins/permission/package.json | 4 +- plugins/permission/toPermissionValidator.ts | 10 +- plugins/session-key/package.json | 4 +- .../toSessionKeyValidatorPlugin.ts | 17 ++- plugins/session-key/utils.ts | 3 +- plugins/weighted-ecdsa/constants.ts | 20 +++ plugins/weighted-ecdsa/index.ts | 8 +- plugins/weighted-ecdsa/package.json | 4 +- .../toWeightedECDSAValidatorPlugin.ts | 11 +- 32 files changed, 344 insertions(+), 94 deletions(-) create mode 100644 packages/core/accounts/kernel/utils/account/ep0_6/encodeModuleInstallCallData.ts create mode 100644 packages/test/recoveryKernelAccount.test.ts create mode 100644 plugins/weighted-ecdsa/constants.ts diff --git a/bun.lockb b/bun.lockb index 3de78ceb56b0a87ba80b67512ef614c39489de09..36dc0457d7577b24d07a47b51e08d88975fbe28d 100755 GIT binary patch delta 8999 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 Promise generateInitCode: () => Promise encodeCallData: (args: KernelEncodeCallDataArgs) => Promise + encodeModuleInstallCallData: () => Promise } export type CreateKernelAccountParameters = { @@ -267,21 +268,23 @@ export async function createKernelAccount< plugins, entryPoint: entryPointAddress, index = 0n, - factoryAddress = KERNEL_ADDRESSES.FACTORY_ADDRESS_V0_6, - accountLogicAddress = KERNEL_ADDRESSES.ACCOUNT_LOGIC_V0_6, + factoryAddress, + accountLogicAddress, factoryStakerAddress = KERNEL_ADDRESSES.FACTORY_STAKER, deployedAccountAddress }: CreateKernelAccountParameters ): Promise> { const entryPointVersion = getEntryPointVersion(entryPointAddress) accountLogicAddress = - entryPointVersion === "v0.6" + accountLogicAddress ?? + (entryPointVersion === "v0.6" ? KERNEL_ADDRESSES.ACCOUNT_LOGIC_V0_6 - : KERNEL_ADDRESSES.ACCOUNT_LOGIC_V0_7 + : KERNEL_ADDRESSES.ACCOUNT_LOGIC_V0_7) factoryAddress = - entryPointVersion === "v0.6" + factoryAddress ?? + (entryPointVersion === "v0.6" ? KERNEL_ADDRESSES.FACTORY_ADDRESS_V0_6 - : KERNEL_ADDRESSES.FACTORY_ADDRESS_V0_7 + : KERNEL_ADDRESSES.FACTORY_ADDRESS_V0_7) const kernelPluginManager = isKernelPluginManager(plugins) ? plugins @@ -294,6 +297,8 @@ export async function createKernelAccount< }) // Helper to generate the init code for the smart account const generateInitCode = async () => { + if (!accountLogicAddress || !factoryAddress) + throw new Error("Missing account logic address or factory address") return getAccountInitCode({ index, factoryAddress, @@ -323,6 +328,11 @@ export async function createKernelAccount< return { kernelPluginManager, generateInitCode, + encodeModuleInstallCallData: async () => { + return await kernelPluginManager.encodeModuleInstallCallData( + accountAddress + ) + }, ...toSmartAccount({ address: accountAddress, publicKey: accountAddress, diff --git a/packages/core/accounts/kernel/utils/account/ep0_6/encodeModuleInstallCallData.ts b/packages/core/accounts/kernel/utils/account/ep0_6/encodeModuleInstallCallData.ts new file mode 100644 index 00000000..74d5b130 --- /dev/null +++ b/packages/core/accounts/kernel/utils/account/ep0_6/encodeModuleInstallCallData.ts @@ -0,0 +1,35 @@ +import type { ENTRYPOINT_ADDRESS_V06_TYPE } from "permissionless/types/entrypoint" +import { type Address, type Hex, encodeFunctionData } from "viem" +import type { PluginInstallData } from "../../../../../types/kernel.js" +import { KernelAccountAbi } from "../../../abi/KernelAccountAbi.js" +import { encodeCallData } from "./encodeCallData.js" + +export const encodeModuleInstallCallData = async ({ + accountAddress, + enableData, + executor, + selector, + validAfter, + validUntil, + validator +}: { + accountAddress: Address +} & PluginInstallData): Promise => { + return encodeCallData({ + to: accountAddress, + value: 0n, + data: encodeFunctionData({ + abi: KernelAccountAbi, + functionName: "setExecution", + args: [ + selector, + executor, + validator, + validUntil, + validAfter, + enableData + ] + }), + callType: "call" + }) +} diff --git a/packages/core/accounts/kernel/utils/account/ep0_7/getKernelV3Nonce.ts b/packages/core/accounts/kernel/utils/account/ep0_7/getKernelV3Nonce.ts index 9690cde6..14446e48 100644 --- a/packages/core/accounts/kernel/utils/account/ep0_7/getKernelV3Nonce.ts +++ b/packages/core/accounts/kernel/utils/account/ep0_7/getKernelV3Nonce.ts @@ -1,6 +1,6 @@ -import { getAction } from "permissionless" import type { Address, Client } from "viem" import { readContract } from "viem/actions" +import { getAction } from "viem/utils" import { KernelV3AccountAbi } from "../../../abi/kernel_v_3_0_0/KernelAccountAbi.js" export const getKernelV3Nonce = async ( @@ -10,7 +10,8 @@ export const getKernelV3Nonce = async ( try { const nonce = await getAction( client, - readContract + readContract, + "sendTransaction" )({ abi: KernelV3AccountAbi, address: accountAddress, diff --git a/packages/core/accounts/kernel/utils/plugins/ep0_6/getPluginsEnableTypedData.ts b/packages/core/accounts/kernel/utils/plugins/ep0_6/getPluginsEnableTypedData.ts index 2366e46f..84adf872 100644 --- a/packages/core/accounts/kernel/utils/plugins/ep0_6/getPluginsEnableTypedData.ts +++ b/packages/core/accounts/kernel/utils/plugins/ep0_6/getPluginsEnableTypedData.ts @@ -34,7 +34,6 @@ export const getPluginsEnableTypedData = async < accountAddress: Address chainId: number kernelVersion: string - // { action, validator }: Kernel2_0_plugins } & Kernel2_0_plugins & PluginValidityData): Promise< Parameters[0] diff --git a/packages/core/accounts/kernel/utils/plugins/ep0_7/isPluginInitialized.ts b/packages/core/accounts/kernel/utils/plugins/ep0_7/isPluginInitialized.ts index cddecff5..cbeb75a1 100644 --- a/packages/core/accounts/kernel/utils/plugins/ep0_7/isPluginInitialized.ts +++ b/packages/core/accounts/kernel/utils/plugins/ep0_7/isPluginInitialized.ts @@ -1,6 +1,6 @@ -import { getAction } from "permissionless" import type { Address, Client } from "viem" import { readContract } from "viem/actions" +import { getAction } from "viem/utils" import { KernelModuleIsInitializedAbi } from "../../../abi/kernel_v_3_0_0/KernelModuleAbi.js" export const isPluginInitialized = async ( @@ -11,7 +11,8 @@ export const isPluginInitialized = async ( try { return await getAction( client, - readContract + readContract, + "readContract" )({ abi: KernelModuleIsInitializedAbi, address: pluginAddress, diff --git a/packages/core/accounts/kernel/v1/createKernelV1Account.ts b/packages/core/accounts/kernel/v1/createKernelV1Account.ts index ec979929..1ffa09bf 100644 --- a/packages/core/accounts/kernel/v1/createKernelV1Account.ts +++ b/packages/core/accounts/kernel/v1/createKernelV1Account.ts @@ -213,6 +213,9 @@ export async function createKernelV1Account< return { ...account, generateInitCode, + encodeModuleInstallCallData: async () => { + throw new Error("Not implemented") + }, client: client, publicKey: accountAddress, entryPoint: entryPointAddress, diff --git a/packages/core/accounts/kernel/v2/createKernelV2Account.ts b/packages/core/accounts/kernel/v2/createKernelV2Account.ts index c665e6e9..c0134e5a 100644 --- a/packages/core/accounts/kernel/v2/createKernelV2Account.ts +++ b/packages/core/accounts/kernel/v2/createKernelV2Account.ts @@ -4,10 +4,7 @@ import { getSenderAddress, isSmartAccountDeployed } from "permissionless" -import { - SignTransactionNotSupportedBySmartAccount, - type SmartAccount -} from "permissionless/accounts" +import { SignTransactionNotSupportedBySmartAccount } from "permissionless/accounts" import type { ENTRYPOINT_ADDRESS_V06_TYPE, EntryPoint @@ -47,20 +44,10 @@ import { isKernelPluginManager, toKernelPluginManager } from "../../utils/toKernelPluginManager.js" +import { type KernelSmartAccount } from "../createKernelAccount.js" import { KernelAccountV2Abi } from "./abi/KernelAccountV2Abi.js" import { KernelFactoryV2Abi } from "./abi/KernelFactoryV2Abi.js" -export type KernelSmartAccount< - entryPoint extends EntryPoint, - transport extends Transport = Transport, - chain extends Chain | undefined = Chain | undefined -> = SmartAccount & { - kernelPluginManager: KernelPluginManager - getNonce: (customNonceKey?: bigint) => Promise - generateInitCode: () => Promise - encodeCallData: (args: KernelEncodeCallDataArgs) => Promise -} - // Safe's library for create and create2: https://github.com/safe-global/safe-contracts/blob/0acdd35a203299585438f53885df630f9d486a86/contracts/libraries/CreateCall.sol // Address was found here: https://github.com/safe-global/safe-deployments/blob/926ec6bbe2ebcac3aa2c2c6c0aff74aa590cbc6a/src/assets/v1.4.1/create_call.json const createCallAddress = "0x9b35Af71d77eaf8d7e40252370304687390A1A52" @@ -289,6 +276,11 @@ export async function createKernelV2Account< source: "kernelSmartAccount", kernelPluginManager, generateInitCode, + encodeModuleInstallCallData: async () => { + return await kernelPluginManager.encodeModuleInstallCallData( + accountAddress + ) + }, async getFactory() { if (smartAccountDeployed) return undefined diff --git a/packages/core/accounts/utils/6492.ts b/packages/core/accounts/utils/6492.ts index 4d9fcb6f..f970a668 100644 --- a/packages/core/accounts/utils/6492.ts +++ b/packages/core/accounts/utils/6492.ts @@ -1,6 +1,5 @@ // copied from: https://github.com/alchemyplatform/aa-sdk/blob/266c9757cd721ef0bd97d04c0b592a329f8a9da5/packages/core/src/signer/utils.ts -import { getAction } from "permissionless" import { type Address, type Chain, @@ -14,6 +13,7 @@ import { parseAbiParameters } from "viem" import { getStorageAt } from "viem/actions" +import { getAction } from "viem/utils" export type SignWith6492Params = { factoryAddress: Address @@ -85,7 +85,8 @@ export const getKernelImplementationAddress = async < try { const strgAddr = await getAction( client, - getStorageAt + getStorageAt, + "getStorageAt" )({ address: accountAddress, slot: "0x360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc" diff --git a/packages/core/accounts/utils/toKernelPluginManager.ts b/packages/core/accounts/utils/toKernelPluginManager.ts index 3b11bc47..2d8a43c7 100644 --- a/packages/core/accounts/utils/toKernelPluginManager.ts +++ b/packages/core/accounts/utils/toKernelPluginManager.ts @@ -15,6 +15,7 @@ import { zeroAddress } from "viem" import { getChainId } from "viem/actions" +import { encodeModuleInstallCallData as encodeModuleInstallCallDataEpV06 } from "../../accounts/kernel/utils/account/ep0_6/encodeModuleInstallCallData.js" import { VALIDATOR_MODE, VALIDATOR_TYPE } from "../../constants.js" import { type KernelPluginManager, @@ -193,6 +194,24 @@ export async function toKernelPluginManager< return { ...activeValidator, getIdentifier, + encodeModuleInstallCallData: async (accountAddress: Address) => { + if (!action) { + throw new Error("Action data must be set") + } + if (!regular) throw new Error("regular validator not set") + if (entryPointVersion === "v0.6") { + return await encodeModuleInstallCallDataEpV06({ + accountAddress, + selector: action.selector, + executor: action.address, + validator: regular?.address, + validUntil, + validAfter, + enableData: await regular.getEnableData(accountAddress) + }) + } + throw new Error("EntryPoint v0.7 not supported yet") + }, signUserOperation: async (userOperation) => { const userOpSig = await activeValidator.signUserOperation(userOperation) diff --git a/packages/core/actions/account-client/signUserOperation.ts b/packages/core/actions/account-client/signUserOperation.ts index 74019ee8..f9a80e01 100644 --- a/packages/core/actions/account-client/signUserOperation.ts +++ b/packages/core/actions/account-client/signUserOperation.ts @@ -13,10 +13,10 @@ import type { } from "permissionless/types" import { AccountOrClientNotFoundError, - getAction, parseAccount } from "permissionless/utils" import type { Chain, Client, Transport } from "viem" +import { getAction } from "viem/utils" export type SignUserOperationParameters< entryPoint extends EntryPoint, @@ -60,7 +60,8 @@ export async function signUserOperation< const userOperation = await getAction( client, - prepareUserOperationRequest + prepareUserOperationRequest, + "prepareUserOperationRequest" )(args) userOperation.signature = await account.signUserOperation( diff --git a/packages/core/package.json b/packages/core/package.json index 03cb1401..a1ff6f1d 100644 --- a/packages/core/package.json +++ b/packages/core/package.json @@ -90,8 +90,8 @@ } }, "peerDependencies": { - "viem": "^2.0.0", - "permissionless": "^0.1.16" + "viem": "^2.9.17", + "permissionless": "^0.1.17" }, "dependencies": { "semver": "^7.6.0" diff --git a/packages/core/types/kernel.ts b/packages/core/types/kernel.ts index 40e889dc..3eef4db1 100644 --- a/packages/core/types/kernel.ts +++ b/packages/core/types/kernel.ts @@ -1,4 +1,7 @@ -import type { EntryPoint } from "permissionless/types" +import type { + ENTRYPOINT_ADDRESS_V06_TYPE, + EntryPoint +} from "permissionless/types" import type { GetEntryPointVersion } from "permissionless/types/entrypoint" import type { UserOperation, @@ -151,8 +154,22 @@ export type KernelPluginManager = getAction(): Action getValidityData(): PluginValidityData getIdentifier(isSudo?: boolean): Hex + encodeModuleInstallCallData: (accountAddress: Address) => Promise } +export type PluginInstallData = + entryPoint extends ENTRYPOINT_ADDRESS_V06_TYPE + ? { + selector: Hex + executor: Address + validator: Address + validUntil: number + validAfter: number + enableData: Hex + } + : // TODO: Add support for EP v0.7 + never + export type KernelPluginManagerParams = { sudo?: KernelValidator regular?: KernelValidator diff --git a/packages/core/utils.ts b/packages/core/utils.ts index 561d37ea..395b44cd 100644 --- a/packages/core/utils.ts +++ b/packages/core/utils.ts @@ -98,7 +98,8 @@ export const fixSignedData = (sig: Hex): Hex => { let { r, s, v } = hexToSignature(signature) if (v === 0n || v === 1n) v += 27n - const joined = signatureToHex({ r, s, v }) + // biome-ignore lint/style/noNonNullAssertion: + const joined = signatureToHex({ r, s, v: v! }) return joined } diff --git a/packages/presets/package.json b/packages/presets/package.json index f0e25183..6150a4b7 100644 --- a/packages/presets/package.json +++ b/packages/presets/package.json @@ -52,7 +52,7 @@ "typescript": "^5.0.0", "@zerodev/sdk": "^5.2.0", "@zerodev/ecdsa-validator": "^5.2.0", - "permissionless": "^0.1.16", - "viem": "^2.0.0" + "permissionless": "^0.1.17", + "viem": "^2.9.17" } } diff --git a/packages/test/package.json b/packages/test/package.json index 960e32d9..6a902c23 100644 --- a/packages/test/package.json +++ b/packages/test/package.json @@ -7,11 +7,11 @@ }, "dependencies": { "dotenv": "^16.3.1", - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "workspace:*", "@zerodev/ecdsa-validator": "workspace:*", "@zerodev/session-key": "workspace:*", "@zerodev/modular-permission": "workspace:*", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/packages/test/recoveryKernelAccount.test.ts b/packages/test/recoveryKernelAccount.test.ts new file mode 100644 index 00000000..03532164 --- /dev/null +++ b/packages/test/recoveryKernelAccount.test.ts @@ -0,0 +1,124 @@ +// @ts-expect-error +import { beforeAll, describe, expect, test } from "bun:test" +import { KernelAccountClient, KernelSmartAccount } from "@zerodev/sdk" +import dotenv from "dotenv" +import { BundlerClient, bundlerActions } from "permissionless" +import { EntryPoint } from "permissionless/types/entrypoint.js" +import { Chain, type PublicClient, Transport, zeroAddress } from "viem" +import { generatePrivateKey } from "viem/accounts" +import { + getEcdsaKernelAccountWithPrivateKey, + getEntryPoint, + getKernelAccountClient, + getPublicClient, + getRecoveryKernelAccount, + getZeroDevPaymasterClient +} from "./utils.js" + +dotenv.config() + +const requiredEnvVars = [ + "FACTORY_ADDRESS", + "TEST_PRIVATE_KEY", + "RPC_URL", + "ENTRYPOINT_ADDRESS", + "GREETER_ADDRESS", + "ZERODEV_PROJECT_ID", + "ZERODEV_BUNDLER_RPC_HOST", + "ZERODEV_PAYMASTER_RPC_HOST" +] + +const validateEnvironmentVariables = (envVars: string[]): void => { + const unsetEnvVars = envVars.filter((envVar) => !process.env[envVar]) + if (unsetEnvVars.length > 0) { + throw new Error( + `The following environment variables are not set: ${unsetEnvVars.join( + ", " + )}` + ) + } +} + +validateEnvironmentVariables(requiredEnvVars) + +const ETHEREUM_ADDRESS_LENGTH = 42 +const ETHEREUM_ADDRESS_REGEX = /^0x[0-9a-fA-F]{40}$/ +const TEST_TIMEOUT = 1000000 + +describe("Recovery kernel Account", () => { + let ownerAccount: KernelSmartAccount + let recoveryAccount: KernelSmartAccount + let publicClient: PublicClient + let bundlerClient: BundlerClient + let ownerKernelClient: KernelAccountClient< + EntryPoint, + Transport, + Chain, + KernelSmartAccount + > + + beforeAll(async () => { + publicClient = await getPublicClient() + const ownerPrivateKey = generatePrivateKey() + ownerAccount = + await getEcdsaKernelAccountWithPrivateKey(ownerPrivateKey) + + recoveryAccount = await getRecoveryKernelAccount(ownerAccount.address) + ownerKernelClient = await getKernelAccountClient({ + account: ownerAccount, + middleware: { + sponsorUserOperation: async ({ userOperation, entryPoint }) => { + const zerodevPaymaster = getZeroDevPaymasterClient() + return zerodevPaymaster.sponsorUserOperation({ + userOperation, + entryPoint + }) + } + } + }) + + bundlerClient = ownerKernelClient.extend( + bundlerActions(getEntryPoint()) + ) + }) + + test("Account address should be a valid Ethereum address", async () => { + expect(ownerAccount.address).toBeString() + expect(ownerAccount.address).toHaveLength(ETHEREUM_ADDRESS_LENGTH) + expect(ownerAccount.address).toMatch(ETHEREUM_ADDRESS_REGEX) + expect(ownerAccount.address).not.toEqual(zeroAddress) + }) + + test( + "enable recovery", + async () => { + console.log("Deploying the Owner Kernel Account") + const txHash = await ownerKernelClient.sendTransaction({ + to: zeroAddress + }) + console.log( + `✅ Owner account Deployed {accountAddress: ${ownerAccount.address}}, txHash:`, + txHash + ) + const userOpHash = await ownerKernelClient.sendUserOperation({ + userOperation: { + callData: + await recoveryAccount.encodeModuleInstallCallData() + } + }) + console.log("userOpHash:", userOpHash) + + expect(userOpHash).toHaveLength(66) + + const transactionReceipt = + await bundlerClient.waitForUserOperationReceipt({ + hash: userOpHash + }) + console.log( + "recoveryTransactionLink", + `https://sepolia.etherscan.io/tx/${transactionReceipt.receipt.transactionHash}` + ) + }, + TEST_TIMEOUT + ) +}) diff --git a/packages/test/utils.ts b/packages/test/utils.ts index 3967f00e..b1f49361 100644 --- a/packages/test/utils.ts +++ b/packages/test/utils.ts @@ -11,7 +11,6 @@ import { createKernelAccount } from "@zerodev/sdk/accounts" import { createKernelV2Account } from "@zerodev/sdk/accounts" -import { KernelV1SmartAccount } from "@zerodev/sdk/accounts/kernel/v1/createKernelV1Account.js" import type { Action } from "@zerodev/sdk/types" import { ParamOperator, @@ -22,6 +21,7 @@ import { signerToSessionKeyValidator } from "@zerodev/session-key" import { createWeightedECDSAValidator } from "@zerodev/weighted-ecdsa-validator" +import { getRecoveryAction } from "@zerodev/weighted-ecdsa-validator/constants.js" import { BundlerClient, ENTRYPOINT_ADDRESS_V06, @@ -52,7 +52,7 @@ import { generatePrivateKey, privateKeyToAccount } from "viem/accounts" -import { type Chain, goerli, sepolia } from "viem/chains" +import { type Chain, sepolia } from "viem/chains" import * as allChains from "viem/chains" import { Policy } from "../../plugins/modularPermission/policies/types.js" import { toECDSASigner } from "../../plugins/modularPermission/signers/toECDSASigner.js" @@ -62,7 +62,8 @@ import { TEST_ERC20Abi } from "./abis/Test_ERC20Abi.js" import { config } from "./config.js" export const Test_ERC20Address = "0x3870419Ba2BBf0127060bCB37f69A1b1C090992B" -export const index = 543853232332340n +export const index = 5438533232332340n +const DEFAULT_PROVIDER = "STACKUP" const projectId = config["v0.6"].sepolia.projectId export const getFactoryAddress = (): Address => { const factoryAddress = process.env.FACTORY_ADDRESS @@ -120,12 +121,12 @@ export const getSignerToEcdsaKernelAccount = async < } export const getEcdsaKernelAccountWithRandomSigner = async (): Promise< - SmartAccount + KernelSmartAccount > => { return getEcdsaKernelAccountWithPrivateKey(generatePrivateKey()) } -const getEcdsaKernelAccountWithPrivateKey = async < +export const getEcdsaKernelAccountWithPrivateKey = async < entryPoint extends EntryPoint >( privateKey: Hex @@ -305,6 +306,34 @@ export const getSignersToWeightedEcdsaKernelAccount = async ( } } +export const getRecoveryKernelAccount = async ( + deployedAccountAddress: Address +) => { + const privateKey1 = generatePrivateKey() + const signer1 = privateKeyToAccount(privateKey1) + const recoveryPlugin = await createWeightedECDSAValidator( + await getPublicClient(), + { + entryPoint: getEntryPoint(), + config: { + threshold: 100, + delay: 0, + signers: [{ address: signer1.address, weight: 100 }] + }, + signers: [signer1] + } + ) + return await createKernelAccount(await getPublicClient(), { + entryPoint: getEntryPoint(), + deployedAccountAddress, + plugins: { + regular: recoveryPlugin, + action: getRecoveryAction() + }, + index + }) +} + export const getSignerToSessionKeyKernelAccount = async (): Promise< KernelSmartAccount > => { @@ -428,8 +457,6 @@ export const getSessionKeyToSessionKeyKernelAccount = async ( }) } -const DEFAULT_PROVIDER = "STACKUP" - const getBundlerRpc = (): string => { const zeroDevProjectId = projectId const zeroDevBundlerRpcHost = config["v0.6"].sepolia.bundlerUrl diff --git a/packages/test/v0.7/ecdsaKernelAccount.test.ts b/packages/test/v0.7/ecdsaKernelAccount.test.ts index be006cd6..261d1550 100644 --- a/packages/test/v0.7/ecdsaKernelAccount.test.ts +++ b/packages/test/v0.7/ecdsaKernelAccount.test.ts @@ -13,7 +13,11 @@ import { } from "@zerodev/sdk" import dotenv from "dotenv" import { ethers } from "ethers" -import { BundlerClient, ENTRYPOINT_ADDRESS_V07 } from "permissionless" +import { + BundlerClient, + ENTRYPOINT_ADDRESS_V07, + bundlerActions +} from "permissionless" import { SignTransactionNotSupportedBySmartAccount } from "permissionless/accounts" import { PimlicoBundlerClient } from "permissionless/clients/pimlico.js" import { EntryPoint } from "permissionless/types/entrypoint.js" @@ -109,7 +113,6 @@ describe("ECDSA kernel Account", () => { account = await getSignerToEcdsaKernelAccount() owner = privateKeyToAccount(process.env.TEST_PRIVATE_KEY as Hex).address publicClient = await getPublicClient() - bundlerClient = getKernelBundlerClient() pimlicoBundlerClient = getPimlicoBundlerClient() kernelClient = await getKernelAccountClient({ account, @@ -123,6 +126,7 @@ describe("ECDSA kernel Account", () => { } } }) + bundlerClient = kernelClient.extend(bundlerActions(getEntryPoint())) greeterContract = getContract({ abi: GreeterAbi, address: process.env.GREETER_ADDRESS as Address, diff --git a/plugins/ecdsa/package.json b/plugins/ecdsa/package.json index 1924684b..2194bc75 100644 --- a/plugins/ecdsa/package.json +++ b/plugins/ecdsa/package.json @@ -35,8 +35,8 @@ "lint:fix": "bun run lint --apply" }, "peerDependencies": { - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "^5.2.0", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/plugins/modularPermission/package.json b/plugins/modularPermission/package.json index a4dcf1b3..85f45d89 100644 --- a/plugins/modularPermission/package.json +++ b/plugins/modularPermission/package.json @@ -56,8 +56,8 @@ "@simplewebauthn/browser": "^9.0.1" }, "peerDependencies": { - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "^5.2.0", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/plugins/modularPermission/toModularPermissionValidatorPlugin.ts b/plugins/modularPermission/toModularPermissionValidatorPlugin.ts index 052b70f9..c8e485b5 100644 --- a/plugins/modularPermission/toModularPermissionValidatorPlugin.ts +++ b/plugins/modularPermission/toModularPermissionValidatorPlugin.ts @@ -1,9 +1,5 @@ import { KernelAccountAbi } from "@zerodev/sdk" -import { - getAction, - getEntryPointVersion, - getUserOperationHash -} from "permissionless" +import { getEntryPointVersion, getUserOperationHash } from "permissionless" import type { EntryPoint } from "permissionless/types/entrypoint" import { type Address, @@ -18,6 +14,7 @@ import { toHex } from "viem" import { getChainId, readContract } from "viem/actions" +import { getAction } from "viem/utils" import { ModularPermissionValidatorAbi } from "./abi/ModularPermissionValidatorAbi.js" import { MAX_FLAG, MODULAR_PERMISSION_VALIDATOR_ADDRESS } from "./constants.js" import type { Policy } from "./policies/types.js" @@ -62,7 +59,8 @@ export async function createPermissionValidator< ): Promise => { const nonce = await getAction( client, - readContract + readContract, + "readContract" )({ abi: ModularPermissionValidatorAbi, address: validatorAddress, @@ -197,7 +195,8 @@ export async function createPermissionValidator< try { const execDetail = await getAction( client, - readContract + readContract, + "readContract" )({ abi: KernelAccountAbi, address: kernelAccountAddress, @@ -206,7 +205,8 @@ export async function createPermissionValidator< }) const permission = await getAction( client, - readContract + readContract, + "readContract" )({ abi: ModularPermissionValidatorAbi, address: validatorAddress, diff --git a/plugins/passkey/package.json b/plugins/passkey/package.json index c94074a7..7a8d5ce8 100644 --- a/plugins/passkey/package.json +++ b/plugins/passkey/package.json @@ -39,8 +39,8 @@ "@simplewebauthn/browser": "^8.3.4" }, "peerDependencies": { - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "^5.2.0", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/plugins/permission/package.json b/plugins/permission/package.json index 08aeba2d..2f705af3 100644 --- a/plugins/permission/package.json +++ b/plugins/permission/package.json @@ -56,8 +56,8 @@ "@simplewebauthn/browser": "^9.0.1" }, "peerDependencies": { - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "^5.2.0", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/plugins/permission/toPermissionValidator.ts b/plugins/permission/toPermissionValidator.ts index e8bb4653..98fb6ba1 100644 --- a/plugins/permission/toPermissionValidator.ts +++ b/plugins/permission/toPermissionValidator.ts @@ -1,9 +1,5 @@ import { KernelV3AccountAbi } from "@zerodev/sdk" -import { - getAction, - getEntryPointVersion, - getUserOperationHash -} from "permissionless" +import { getEntryPointVersion, getUserOperationHash } from "permissionless" import type { EntryPoint } from "permissionless/types/entrypoint" import { type Address, @@ -18,6 +14,7 @@ import { zeroAddress } from "viem" import { getChainId, readContract } from "viem/actions" +import { getAction } from "viem/utils" import { PolicyFlags } from "./constants.js" import { toPolicyId } from "./policies/index.js" import { toSignerId } from "./signers/index.js" @@ -135,7 +132,8 @@ export async function toPermissionValidator< try { const permissionConfig = await getAction( client, - readContract + readContract, + "readContract" )({ abi: KernelV3AccountAbi, address: kernelAccountAddress, diff --git a/plugins/session-key/package.json b/plugins/session-key/package.json index 8c729f27..910ffcc9 100644 --- a/plugins/session-key/package.json +++ b/plugins/session-key/package.json @@ -38,8 +38,8 @@ "merkletreejs": "^0.3.11" }, "peerDependencies": { - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "^5.2.0", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/plugins/session-key/toSessionKeyValidatorPlugin.ts b/plugins/session-key/toSessionKeyValidatorPlugin.ts index f3ddae03..dc50fcae 100644 --- a/plugins/session-key/toSessionKeyValidatorPlugin.ts +++ b/plugins/session-key/toSessionKeyValidatorPlugin.ts @@ -20,17 +20,13 @@ import { signMessage, signTypedData } from "viem/actions" -import { concat, concatHex } from "viem/utils" +import { concat, concatHex, getAction } from "viem/utils" import { SessionKeyValidatorAbi } from "./abi/SessionKeyValidatorAbi.js" import { KernelAccountAbi } from "@zerodev/sdk" import { constants } from "@zerodev/sdk" import { MerkleTree } from "merkletreejs" -import { - getAction, - getEntryPointVersion, - getUserOperationHash -} from "permissionless" +import { getEntryPointVersion, getUserOperationHash } from "permissionless" import { SignTransactionNotSupportedBySmartAccount, type SmartAccountSigner @@ -204,7 +200,8 @@ export async function signerToSessionKeyValidator< ): Promise => { const nonce = await getAction( client, - readContract + readContract, + "readContract" )({ abi: SessionKeyValidatorAbi, address: validatorAddress, @@ -304,7 +301,8 @@ export async function signerToSessionKeyValidator< try { const execDetail = await getAction( client, - readContract + readContract, + "readContract" )({ abi: KernelAccountAbi, address: kernelAccountAddress, @@ -313,7 +311,8 @@ export async function signerToSessionKeyValidator< }) const enableData = await getAction( client, - readContract + readContract, + "readContract" )({ abi: SessionKeyValidatorAbi, address: validatorAddress, diff --git a/plugins/session-key/utils.ts b/plugins/session-key/utils.ts index 931239b8..a05f9351 100644 --- a/plugins/session-key/utils.ts +++ b/plugins/session-key/utils.ts @@ -92,7 +92,8 @@ export const fixSignedData = (sig: Hex): Hex => { let { r, s, v } = hexToSignature(signature) if (v === 0n || v === 1n) v += 27n - const joined = signatureToHex({ r, s, v }) + // biome-ignore lint/style/noNonNullAssertion: + const joined = signatureToHex({ r, s, v: v! }) return joined } diff --git a/plugins/weighted-ecdsa/constants.ts b/plugins/weighted-ecdsa/constants.ts new file mode 100644 index 00000000..1903a42f --- /dev/null +++ b/plugins/weighted-ecdsa/constants.ts @@ -0,0 +1,20 @@ +import type { Action } from "@zerodev/sdk/types" +import { toFunctionSelector } from "viem" + +const RECOVERY_ACTION_ADDRESS = "0x2f65dB8039fe5CAEE0a8680D2879deB800F31Ae1" +const RECOVERY_ACTION_SELECTOR = toFunctionSelector( + "doRecovery(address, bytes)" +) + +export const getRecoveryAction = (): Action => { + return { + address: RECOVERY_ACTION_ADDRESS, + selector: RECOVERY_ACTION_SELECTOR + } +} + +export const WEIGHTED_ECDSA_VALIDATOR_ADDRESS_V06 = + "0x8012D9ee59176Cb01a4aa80fCFE6f5E8bA58d4fb" + +export const WEIGHTED_ECDSA_VALIDATOR_ADDRESS_V07 = + "0x750Fe8F6FE28b9F2Bd89B4B195c4a9f5D9F5fAa1" diff --git a/plugins/weighted-ecdsa/index.ts b/plugins/weighted-ecdsa/index.ts index 67af2278..de5e29f4 100644 --- a/plugins/weighted-ecdsa/index.ts +++ b/plugins/weighted-ecdsa/index.ts @@ -11,10 +11,4 @@ export { getCurrentSigners, type KernelValidator } - -/// @dev note that only deployed on polygon-mumbai now -export const WEIGHTED_ECDSA_VALIDATOR_ADDRESS_V06 = - "0x8012D9ee59176Cb01a4aa80fCFE6f5E8bA58d4fb" - -export const WEIGHTED_ECDSA_VALIDATOR_ADDRESS_V07 = - "0x750Fe8F6FE28b9F2Bd89B4B195c4a9f5D9F5fAa1" +export * from "./constants.js" diff --git a/plugins/weighted-ecdsa/package.json b/plugins/weighted-ecdsa/package.json index 30f4d1ae..4432822b 100644 --- a/plugins/weighted-ecdsa/package.json +++ b/plugins/weighted-ecdsa/package.json @@ -35,8 +35,8 @@ "lint:fix": "bun run lint --apply" }, "peerDependencies": { - "viem": "^2.0.0", + "viem": "^2.9.17", "@zerodev/sdk": "^5.2.0", - "permissionless": "^0.1.16" + "permissionless": "^0.1.17" } } diff --git a/plugins/weighted-ecdsa/toWeightedECDSAValidatorPlugin.ts b/plugins/weighted-ecdsa/toWeightedECDSAValidatorPlugin.ts index a854bea7..194cd7ee 100644 --- a/plugins/weighted-ecdsa/toWeightedECDSAValidatorPlugin.ts +++ b/plugins/weighted-ecdsa/toWeightedECDSAValidatorPlugin.ts @@ -3,7 +3,6 @@ import type { KernelValidator } from "@zerodev/sdk/types" import type { TypedData } from "abitype" import { type UserOperation, - getAction, getEntryPointVersion, getUserOperationHash } from "permissionless" @@ -29,6 +28,7 @@ import { } from "viem" import { toAccount } from "viem/accounts" import { getChainId, readContract } from "viem/actions" +import { getAction } from "viem/utils" import { WeightedValidatorAbi } from "./abi.js" import { WEIGHTED_ECDSA_VALIDATOR_ADDRESS_V06, @@ -302,7 +302,8 @@ export async function createWeightedECDSAValidator< try { const execDetail = await getAction( client, - readContract + readContract, + "readContract" )({ abi: KernelAccountAbi, address: kernelAccountAddress, @@ -374,7 +375,8 @@ export async function getCurrentSigners< // Fetch first guardian info from weightedStorage const weightedStorage = await getAction( client, - readContract + readContract, + "readContract" )({ abi: WeightedValidatorAbi, address: validatorAddress, @@ -388,7 +390,8 @@ export async function getCurrentSigners< while (nextGuardian !== "0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF") { const guardianStorage = await getAction( client, - readContract + readContract, + "readContract" )({ abi: WeightedValidatorAbi, address: validatorAddress, From 0d9709c6bc155de4323475e9f513984f7f6335ec Mon Sep 17 00:00:00 2001 From: SahilVasava Date: Mon, 15 Apr 2024 22:08:20 +0000 Subject: [PATCH 2/2] chore: format --- bun.lockb | Bin 211728 -> 211160 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/bun.lockb b/bun.lockb index 36dc0457d7577b24d07a47b51e08d88975fbe28d..005bec5d16128a13bcdb67f4c3873cfe12104b4c 100755 GIT binary patch delta 5363 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 LYi!acuh;!wsJ@3X delta 5951 zcmZveX|R*k8OPt7ivcbWHp#_{hCS>71#(%#9zYd8+%R412NdGHZr;t@-;Eb9yvW5))NlgY>M~42aCW~w! z!+%keLpG6-SJmW^EoAgHH3g)*qIC>eM0) z2HsSYM%IwQx71{ib!6zAnk=$`3|H0UkWFOdZ))<$7BYHXO#$ityVfye5$U<0CXOs2 zy%*IakY%LrA8L}w3ex|!niR5%4Aj)5ku_xSl9~*%jtsq{CW~w!!~ay1LpG6-ch%&P zEoAgxY6?jAds@ekMWp9_HF0DK>8-0tAj?SKzttp>6{P>NniR5%41Ay_jjSPqAF9b9 z>&VbYYO=@%GW@Zc9I}awe4-|gY$2l!H3g*mQ>|mjBGU7jnmDqA^j=YuK$eld&($Q6 z6{P>FniR5%41A#`jjSPqU#iI<>&Q@3O%~ZehQCsiLpG6-uhry{EoAf?H3g*mTdiZr zBGU7nnmDqA^j=ewK$eld>uQq73ew+FlR{RJfg5Vl$eQL$!8XkdvaZ=1Y6G%Fg9y7I zb3~Jfv_s~J77^_SSs>iEU=$;YgvSjTCrX63KV*U^6TShENuomd2STQZDiP>_OcOOC zI0!OB)QQkw$Slzy!b2c)M3abkAoE0vhz^A;5bj|Z#fT!|84ejIN`!X=WP&IYzLAhg zqC)s@g-j7uA}|UvP1J~>7cxWCiBKnGmS_;+(U3W!Nkndg%o8ml+67r4++#3`5k6GWNt`5==-h47DsOc7NgFb*oYqD=UvK_-a`;hzqfBC14S24tG35y6>|8KO>v zW_AL}U?Uo@f!##gGNUy#%8eQ6xM|A>%}e z@P;50M49j{gG>??!oM6cMO2Bv3dl53BZ4a-Gen&Tt%A%F4I;c6GDkFt$QsBz(ITQ@ z$O7SBi&2ay5}tLCaiTL7Z7RWr&BBEO%3xsNT0>iHjx(_L`DEKh`4^jc`hPzdbn}DIGdMm=Gz2dm7~k2q=h?O!M_j)d z-n)08Yr7nOdZ24$kDL(gH7T@im+qo+Dk8M*XI}MLn|F(Ob+6kzx77VrNPE-f>39H) z&T*=C!VVcvk*mwlId5)|)YJ5iq+PIM^CIlWd3vrT z;&ef8oAXG$%#OW;V|yHDsK{=S>ff=6!=w&~&{e)`Zn)I5&An%Cgt#km1zmaF+(@Zk z6{jn|Z0=U6*XW%{`%s+xIisY9drW?0(kt?D{Z!h=<~pT*!rUk3MvFUWu3_#rafi%( zYOYJ%Q|3N1H%462T+bDgw~IV%@^f={hoRoWbaT4bZRTc})4g_?n<@1vIac?&U7X(Q zEa|_sn|9m0fVfTO`uCWeEpm%U{YNpt+#IQ|O08|6xjUu4Xs$!3=ebMzOXh~yyt(3z znezy>oG1Obxnbsd=8HUJa)eM<9F(4sVw`ZKP3)HXXZoSEQ8sUZ)IT@pHMdaQ8J#4p z)7&DdSHU>WXgl9x8L!pvzqT%$xJ2sf_Gre4({icwmN}oz3yHg7ZmhXw;$AT~&fIcw zXT<5&j5oJJ>Ob1N2`;(5E?}kf--*=ynkWR#7o)#mo29?3M@U;NPM^#c>A#mk zSGmO8R&%<_rRKIteN<{~A#>ZMJ|gux;WBeOq`ptOE@-(+uCEulNBS?N&^uaT6Qff9 z%G^qGJH_qS1Ej4ow@d1M(sh-q&D|@tu2B0LbGxP11*!|1yHD4zD^$7G~r#}D9CLc1X7u#a) zVX6Nh2kVKqn$x}1N2n*+X6{jQdXDYp;^y=mJItLOE`_v7`t_35cWtO^WB(p~$?6MK zUzp3K>-$jOfBL@D_nW@Y=1D&wxAKg1{f(?kKP&xaeUroGn49%Hse}JDzUgmLe=p@{ zuXkUkYvK40WN=Bk^8fa}Q=P62Z5>rVE0j=NlK9fwa+?CI|7`h~0OM8~mixrns0-Myjt?Yjq!Ucm8V3)_2#9(Q&1y*$7D j$+nJT3#l(J)M*oX_jI@K7&K=Q<#UT{?z!&v_O|~3)xNwH