-
Notifications
You must be signed in to change notification settings - Fork 22
Commit
- Loading branch information
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,132 @@ | ||
import { createWalletClient, Hex, http, parseEther, zeroAddress } from "viem"; | ||
Check failure on line 1 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
Check failure on line 1 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
Check failure on line 1 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
Check failure on line 1 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
Check failure on line 1 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
Check failure on line 1 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
|
||
import { DeployerService } from "../ts/deployer/deployer.service"; | ||
import { FileService } from "../ts/file/file.service"; | ||
import { SessionKeysService } from "../ts/sessionKeys/sessionKeys.service"; | ||
import { genPimlicoRPCUrl, getPublicClient } from "../ts/common/accountAbstraction"; | ||
Check failure on line 5 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
Check failure on line 5 in packages/coordinator/tests/aa.test.ts GitHub Actions / check (lint:ts)
|
||
import { ErrorCodes, ESupportedNetworks } from "../ts/common"; | ||
import { signerToEcdsaValidator } from "@zerodev/ecdsa-validator"; | ||
import { ENTRYPOINT_ADDRESS_V07 } from "permissionless"; | ||
import { KERNEL_V3_1 } from "@zerodev/sdk/constants"; | ||
import { addressToEmptyAccount, createKernelAccount, createKernelAccountClient } from "@zerodev/sdk"; | ||
import { toECDSASigner } from "@zerodev/permissions/signers"; | ||
import { serializePermissionAccount, toPermissionValidator } from "@zerodev/permissions"; | ||
|
||
import dotenv from "dotenv"; | ||
import { privateKeyToAccount } from "viem/accounts"; | ||
import { testMaciDeploymentConfig } from "../ts/deployer/__tests__/utils"; | ||
import { toSudoPolicy } from "@zerodev/permissions/policies"; | ||
import { optimismSepolia } from "viem/chains"; | ||
|
||
dotenv.config(); | ||
|
||
const entryPoint = ENTRYPOINT_ADDRESS_V07; | ||
const kernelVersion = KERNEL_V3_1; | ||
|
||
/** | ||
* Generate an approval for a session key | ||
* | ||
* @returns - the approval | ||
*/ | ||
export const generateApproval = async (sessionKeyAddress: Hex): Promise<string> => { | ||
const publicClient = getPublicClient(ESupportedNetworks.OPTIMISM_SEPOLIA); | ||
|
||
const sessionKeySigner = privateKeyToAccount(process.env.TEST_PRIVATE_KEY! as `0x${string}`); | ||
const ecdsaValidator = await signerToEcdsaValidator(publicClient, { | ||
signer: sessionKeySigner, | ||
entryPoint, | ||
kernelVersion, | ||
}); | ||
|
||
const emptyAccount = addressToEmptyAccount(sessionKeyAddress); | ||
const emptySessionKeySigner = toECDSASigner({ signer: emptyAccount }); | ||
|
||
const permissionPlugin = await toPermissionValidator(publicClient, { | ||
entryPoint, | ||
kernelVersion, | ||
signer: emptySessionKeySigner, | ||
policies: [toSudoPolicy({})], | ||
}); | ||
|
||
const sessionKeyAccount = await createKernelAccount(publicClient, { | ||
entryPoint, | ||
kernelVersion, | ||
plugins: { | ||
sudo: ecdsaValidator, | ||
regular: permissionPlugin, | ||
}, | ||
}); | ||
|
||
return serializePermissionAccount(sessionKeyAccount); | ||
}; | ||
|
||
describe("Account Abstraction e2e", () => { | ||
const fileService = new FileService(); | ||
const sessionKeyService = new SessionKeysService(fileService); | ||
const deployerService = new DeployerService(sessionKeyService, fileService); | ||
|
||
const sessionKeyAddress = sessionKeyService.generateSessionKey().sessionKeyAddress; | ||
|
||
let approval: string; | ||
|
||
beforeAll(async () => { | ||
approval = await generateApproval(sessionKeyAddress); | ||
}); | ||
|
||
describe("sessionKeys", () => { | ||
it("should create a client from a session key and an approval", async () => { | ||
const client = await sessionKeyService.generateClientFromSessionKey( | ||
sessionKeyAddress, | ||
approval, | ||
ESupportedNetworks.OPTIMISM_SEPOLIA, | ||
); | ||
|
||
expect(client).toBeDefined(); | ||
expect(client.transport.key).toBe("http"); | ||
expect(client.key).toBe("Account"); | ||
expect(client.account.address).not.toBe(zeroAddress); | ||
expect(client.account.kernelVersion).toBe(kernelVersion); | ||
expect(client.account.entryPoint).toBe(entryPoint); | ||
// this is an account with limited permissions so no sudo validator | ||
expect(client.account.kernelPluginManager.address).toBe(zeroAddress); | ||
expect(client.account.kernelPluginManager.sudoValidator).toBe(undefined); | ||
|
||
// try a transaction | ||
await client.sendTransaction({ | ||
to: zeroAddress, | ||
value: 0n, | ||
data: "0x", | ||
authorizationList: [], | ||
// @ts-expect-error | ||
account: client.account, | ||
}); | ||
}); | ||
|
||
it("should not allow to create a client after the session key has been deactivated", async () => { | ||
sessionKeyService.deactivateSessionKey(sessionKeyAddress); | ||
|
||
await expect( | ||
sessionKeyService.generateClientFromSessionKey( | ||
sessionKeyAddress, | ||
approval, | ||
ESupportedNetworks.OPTIMISM_SEPOLIA, | ||
), | ||
).rejects.toThrow(ErrorCodes.SESSION_KEY_NOT_FOUND); | ||
}); | ||
}); | ||
|
||
describe("deployMaci", () => { | ||
it("should deploy all maci related contracts", async () => { | ||
const newSessionKeyAddress = sessionKeyService.generateSessionKey().sessionKeyAddress; | ||
const approval = await generateApproval(newSessionKeyAddress); | ||
|
||
const maciAddress = await deployerService.deployMaci({ | ||
approval, | ||
sessionKeyAddress: newSessionKeyAddress, | ||
chain: ESupportedNetworks.OPTIMISM_SEPOLIA, | ||
config: testMaciDeploymentConfig, | ||
}); | ||
|
||
expect(maciAddress).not.toBe(zeroAddress); | ||
}); | ||
}); | ||
}); |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,3 @@ | ||
export { ErrorCodes } from "./errors"; | ||
export { ESupportedNetworks } from "./networks"; | ||
export const MESSAGE_TREE_ARITY = 5n; |