@zerodev/sdk 4.0.31 → 4.0.33

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (100) hide show
  1. package/dist/cjs/kernel-zerodev/abis/KernelAccountAbi.d.ts +42 -4
  2. package/dist/cjs/kernel-zerodev/abis/KernelAccountAbi.js +53 -4
  3. package/dist/cjs/kernel-zerodev/abis/KernelAccountAbi.js.map +1 -1
  4. package/dist/cjs/kernel-zerodev/account.d.ts +3 -0
  5. package/dist/cjs/kernel-zerodev/account.js +47 -6
  6. package/dist/cjs/kernel-zerodev/account.js.map +1 -1
  7. package/dist/cjs/kernel-zerodev/client/create-client.js.map +1 -1
  8. package/dist/cjs/kernel-zerodev/constants.d.ts +2 -2
  9. package/dist/cjs/kernel-zerodev/constants.js +2 -2
  10. package/dist/cjs/kernel-zerodev/constants.js.map +1 -1
  11. package/dist/cjs/kernel-zerodev/ethers-provider/account-signer.d.ts +1 -1
  12. package/dist/cjs/kernel-zerodev/ethers-provider/account-signer.js.map +1 -1
  13. package/dist/cjs/kernel-zerodev/middleware/paymaster.js +19 -6
  14. package/dist/cjs/kernel-zerodev/middleware/paymaster.js.map +1 -1
  15. package/dist/cjs/kernel-zerodev/owner/getCustodialOwner.d.ts +7 -3
  16. package/dist/cjs/kernel-zerodev/owner/getCustodialOwner.js +45 -18
  17. package/dist/cjs/kernel-zerodev/owner/getCustodialOwner.js.map +1 -1
  18. package/dist/cjs/kernel-zerodev/owner/passkey/createPasskeyOwner.js.map +1 -1
  19. package/dist/cjs/kernel-zerodev/owner/passkey/getAutocompletePasskeyOwner.js.map +1 -1
  20. package/dist/cjs/kernel-zerodev/owner/passkey/getPasskeyOwner.js.map +1 -1
  21. package/dist/cjs/kernel-zerodev/owner/passkey/utils.d.ts +0 -1
  22. package/dist/cjs/kernel-zerodev/owner/passkey/utils.js.map +1 -1
  23. package/dist/cjs/kernel-zerodev/paymaster/base.js +36 -33
  24. package/dist/cjs/kernel-zerodev/paymaster/base.js.map +1 -1
  25. package/dist/cjs/kernel-zerodev/paymaster/token-paymaster.d.ts +4 -3
  26. package/dist/cjs/kernel-zerodev/paymaster/token-paymaster.js +48 -39
  27. package/dist/cjs/kernel-zerodev/paymaster/token-paymaster.js.map +1 -1
  28. package/dist/cjs/kernel-zerodev/paymaster/verifying-paymaster.js +7 -15
  29. package/dist/cjs/kernel-zerodev/paymaster/verifying-paymaster.js.map +1 -1
  30. package/dist/cjs/kernel-zerodev/provider.js +1 -2
  31. package/dist/cjs/kernel-zerodev/provider.js.map +1 -1
  32. package/dist/esm/kernel-zerodev/abis/KernelAccountAbi.d.ts +42 -4
  33. package/dist/esm/kernel-zerodev/abis/KernelAccountAbi.js +53 -4
  34. package/dist/esm/kernel-zerodev/abis/KernelAccountAbi.js.map +1 -1
  35. package/dist/esm/kernel-zerodev/account.d.ts +3 -0
  36. package/dist/esm/kernel-zerodev/account.js +47 -6
  37. package/dist/esm/kernel-zerodev/account.js.map +1 -1
  38. package/dist/esm/kernel-zerodev/client/create-client.js.map +1 -1
  39. package/dist/esm/kernel-zerodev/constants.d.ts +2 -2
  40. package/dist/esm/kernel-zerodev/constants.js +2 -2
  41. package/dist/esm/kernel-zerodev/constants.js.map +1 -1
  42. package/dist/esm/kernel-zerodev/ethers-provider/account-signer.d.ts +1 -1
  43. package/dist/esm/kernel-zerodev/ethers-provider/account-signer.js.map +1 -1
  44. package/dist/esm/kernel-zerodev/middleware/paymaster.js +19 -6
  45. package/dist/esm/kernel-zerodev/middleware/paymaster.js.map +1 -1
  46. package/dist/esm/kernel-zerodev/owner/getCustodialOwner.d.ts +7 -3
  47. package/dist/esm/kernel-zerodev/owner/getCustodialOwner.js +46 -18
  48. package/dist/esm/kernel-zerodev/owner/getCustodialOwner.js.map +1 -1
  49. package/dist/esm/kernel-zerodev/owner/passkey/createPasskeyOwner.js.map +1 -1
  50. package/dist/esm/kernel-zerodev/owner/passkey/getAutocompletePasskeyOwner.js.map +1 -1
  51. package/dist/esm/kernel-zerodev/owner/passkey/getPasskeyOwner.js.map +1 -1
  52. package/dist/esm/kernel-zerodev/owner/passkey/utils.d.ts +0 -1
  53. package/dist/esm/kernel-zerodev/owner/passkey/utils.js.map +1 -1
  54. package/dist/esm/kernel-zerodev/paymaster/base.js +36 -33
  55. package/dist/esm/kernel-zerodev/paymaster/base.js.map +1 -1
  56. package/dist/esm/kernel-zerodev/paymaster/token-paymaster.d.ts +4 -3
  57. package/dist/esm/kernel-zerodev/paymaster/token-paymaster.js +47 -39
  58. package/dist/esm/kernel-zerodev/paymaster/token-paymaster.js.map +1 -1
  59. package/dist/esm/kernel-zerodev/paymaster/verifying-paymaster.js +7 -15
  60. package/dist/esm/kernel-zerodev/paymaster/verifying-paymaster.js.map +1 -1
  61. package/dist/esm/kernel-zerodev/provider.js +1 -2
  62. package/dist/esm/kernel-zerodev/provider.js.map +1 -1
  63. package/dist/types/kernel-zerodev/abis/KernelAccountAbi.d.ts +42 -4
  64. package/dist/types/kernel-zerodev/abis/KernelAccountAbi.d.ts.map +1 -1
  65. package/dist/types/kernel-zerodev/account.d.ts +3 -0
  66. package/dist/types/kernel-zerodev/account.d.ts.map +1 -1
  67. package/dist/types/kernel-zerodev/client/create-client.d.ts.map +1 -1
  68. package/dist/types/kernel-zerodev/constants.d.ts +2 -2
  69. package/dist/types/kernel-zerodev/constants.d.ts.map +1 -1
  70. package/dist/types/kernel-zerodev/ethers-provider/account-signer.d.ts +1 -1
  71. package/dist/types/kernel-zerodev/ethers-provider/account-signer.d.ts.map +1 -1
  72. package/dist/types/kernel-zerodev/middleware/paymaster.d.ts.map +1 -1
  73. package/dist/types/kernel-zerodev/owner/getCustodialOwner.d.ts +7 -3
  74. package/dist/types/kernel-zerodev/owner/getCustodialOwner.d.ts.map +1 -1
  75. package/dist/types/kernel-zerodev/owner/passkey/createPasskeyOwner.d.ts.map +1 -1
  76. package/dist/types/kernel-zerodev/owner/passkey/getAutocompletePasskeyOwner.d.ts.map +1 -1
  77. package/dist/types/kernel-zerodev/owner/passkey/getPasskeyOwner.d.ts.map +1 -1
  78. package/dist/types/kernel-zerodev/owner/passkey/utils.d.ts +0 -1
  79. package/dist/types/kernel-zerodev/owner/passkey/utils.d.ts.map +1 -1
  80. package/dist/types/kernel-zerodev/paymaster/base.d.ts.map +1 -1
  81. package/dist/types/kernel-zerodev/paymaster/token-paymaster.d.ts +4 -3
  82. package/dist/types/kernel-zerodev/paymaster/token-paymaster.d.ts.map +1 -1
  83. package/dist/types/kernel-zerodev/paymaster/verifying-paymaster.d.ts.map +1 -1
  84. package/dist/types/kernel-zerodev/provider.d.ts.map +1 -1
  85. package/package.json +4 -2
  86. package/src/kernel-zerodev/abis/KernelAccountAbi.ts +53 -4
  87. package/src/kernel-zerodev/account.ts +57 -10
  88. package/src/kernel-zerodev/client/create-client.ts +1 -0
  89. package/src/kernel-zerodev/constants.ts +3 -2
  90. package/src/kernel-zerodev/ethers-provider/account-signer.ts +1 -1
  91. package/src/kernel-zerodev/middleware/paymaster.ts +20 -9
  92. package/src/kernel-zerodev/owner/getCustodialOwner.ts +94 -36
  93. package/src/kernel-zerodev/owner/passkey/createPasskeyOwner.ts +0 -4
  94. package/src/kernel-zerodev/owner/passkey/getAutocompletePasskeyOwner.ts +0 -2
  95. package/src/kernel-zerodev/owner/passkey/getPasskeyOwner.ts +0 -2
  96. package/src/kernel-zerodev/owner/passkey/utils.ts +0 -1
  97. package/src/kernel-zerodev/paymaster/base.ts +44 -38
  98. package/src/kernel-zerodev/paymaster/token-paymaster.ts +74 -53
  99. package/src/kernel-zerodev/paymaster/verifying-paymaster.ts +7 -14
  100. package/src/kernel-zerodev/provider.ts +1 -2
@@ -1,9 +1,30 @@
1
- import type { SmartAccountSigner } from "@alchemy/aa-core";
1
+ import type { SignTypedDataParams, SmartAccountSigner } from "@alchemy/aa-core";
2
2
  import { API_URL } from "../constants.js";
3
3
  import axios from "axios";
4
- import type { Hex } from "viem";
5
- import type { SignTypedDataParams } from "@alchemy/aa-core";
4
+ import { TurnkeyClient } from "@turnkey/http";
6
5
 
6
+ /**
7
+ * Params to get a custodial owner
8
+ * Priv / pub key combo or custodial file path should be in different types
9
+ */
10
+ type GetCustodialOwnerParams = {
11
+ // ZeroDev api url
12
+ apiUrl?: string;
13
+ // Turnkey client (if the client want to reuse it
14
+ turnKeyClient?: TurnkeyClient;
15
+
16
+ // Direct access to priv / pub key
17
+ privateKey?: string;
18
+ publicKey?: string;
19
+ keyId?: string;
20
+
21
+ // Or read them from the custodial file path
22
+ custodialFilePath?: string;
23
+ };
24
+
25
+ /**
26
+ * Returns a signer for a custodial wallet via TurnKey
27
+ */
7
28
  export async function getCustodialOwner(
8
29
  identifier: string,
9
30
  {
@@ -12,14 +33,10 @@ export async function getCustodialOwner(
12
33
  publicKey,
13
34
  keyId,
14
35
  apiUrl = API_URL,
15
- }: {
16
- privateKey?: string;
17
- publicKey?: string;
18
- keyId?: string;
19
- custodialFilePath?: string;
20
- apiUrl?: string;
21
- }
36
+ turnKeyClient,
37
+ }: GetCustodialOwnerParams
22
38
  ): Promise<SmartAccountSigner | undefined> {
39
+ // Extract data from the custodial file path if provided
23
40
  if (custodialFilePath) {
24
41
  let fsModule;
25
42
  try {
@@ -30,45 +47,86 @@ export async function getCustodialOwner(
30
47
  }
31
48
  const data = fsModule.readFileSync(custodialFilePath, "utf8");
32
49
  const values = data.split("\n");
50
+ // Override the values, if they are provided, to the one from the custodial file
33
51
  [privateKey, publicKey, keyId] = values;
34
52
  }
35
- let TurnkeySigner;
36
- try {
37
- TurnkeySigner =
38
- require.resolve("@turnkey/ethers") &&
39
- require("@turnkey/ethers").TurnkeySigner;
40
- } catch (error) {
41
- console.log(
42
- "@turnkey/ethers module not available. Skipping FS operation..."
43
- );
44
- return;
45
- }
53
+
54
+ // Ensure we have the required values
46
55
  if (!privateKey || !publicKey || !keyId) {
47
56
  throw new Error(
48
57
  "Must provide custodialFilePath or privateKey, publicKey, and keyId."
49
58
  );
50
59
  }
51
60
 
52
- const response = await axios.post(`${apiUrl}/wallets/${identifier}`, {
53
- keyId,
54
- });
61
+ // Get our turnkey client (build it if needed)
62
+ if (!turnKeyClient) {
63
+ // Try to fetch turnkey client & api key stamper
64
+ let TurnkeyClient;
65
+ let ApiKeyStamper;
66
+ // TODO: Would be cleaner with something like radash and a tryit function?
67
+ try {
68
+ TurnkeyClient =
69
+ require.resolve("@turnkey/http") &&
70
+ require("@turnkey/http").TurnkeyClient;
71
+ ApiKeyStamper =
72
+ require.resolve("@turnkey/api-key-stamper") &&
73
+ require("@turnkey/api-key-stamper").ApiKeyStamper;
74
+ } catch (error) {
75
+ console.log(
76
+ "@turnkey/http or @turnkey/api-key-stamper module not available. Skipping FS operation..."
77
+ );
78
+ return;
79
+ }
55
80
 
56
- const turnkeySigner = new TurnkeySigner({
57
- apiPublicKey: publicKey,
58
- apiPrivateKey: privateKey,
59
- baseUrl: "https://api.turnkey.com",
81
+ // Build the turnkey client
82
+ turnKeyClient = new TurnkeyClient(
83
+ {
84
+ baseUrl: "https://api.turnkey.com",
85
+ },
86
+ new ApiKeyStamper({
87
+ apiPublicKey: publicKey,
88
+ apiPrivateKey: privateKey,
89
+ })
90
+ );
91
+ }
92
+
93
+ // Get the wallet identifier from the API
94
+ const response = await axios.post<any, { data: { walletId: string } }>(
95
+ `${apiUrl}/wallets/${identifier}`,
96
+ {
97
+ keyId,
98
+ }
99
+ );
100
+
101
+ // Build the turnkey viem account
102
+ let createAccount;
103
+ try {
104
+ createAccount =
105
+ require.resolve("@turnkey/viem") &&
106
+ require("@turnkey/viem").createAccount;
107
+ } catch (error) {
108
+ console.log("@turnkey/viem module not available. Skipping FS operation...");
109
+ return;
110
+ }
111
+ const turnkeySigner = await createAccount({
112
+ client: turnKeyClient,
60
113
  organizationId: keyId,
61
114
  privateKeyId: response.data.walletId,
62
115
  });
116
+
117
+ // Return an alchemy AA signer from the turnkey signer
63
118
  return {
64
- getAddress: async () => (await turnkeySigner.getAddress()) as `0x${string}`,
65
- signMessage: async (msg: Uint8Array | string) =>
66
- (await turnkeySigner.signMessage(msg)) as `0x${string}`,
119
+ getAddress: async () => turnkeySigner.address,
120
+ signMessage: async (msg: Uint8Array | string) => {
121
+ if (typeof msg === "string") {
122
+ // If the msg is a string, sign it directly
123
+ return turnkeySigner.signMessage({ message: msg });
124
+ } else {
125
+ // Otherwise, sign the raw data
126
+ return turnkeySigner.signMessage({ message: { raw: msg } });
127
+ }
128
+ },
67
129
  signTypedData: async (params: SignTypedDataParams) =>
68
- (await turnkeySigner.signTypedData(
69
- params.domain,
70
- params.types,
71
- params.message
72
- )) as Hex,
130
+ turnkeySigner.signTypedData(params),
73
131
  };
74
132
  }
@@ -27,7 +27,6 @@ export async function createPasskeyOwner({
27
27
  fallback?: () => Promise<SmartAccountSigner | undefined>;
28
28
  apiUrl?: string;
29
29
  }): Promise<SmartAccountSigner | undefined> {
30
- //@ts-expect-error
31
30
  if (typeof window !== "undefined") {
32
31
  const challenge = generateRandomBuffer();
33
32
  let credentials = undefined;
@@ -43,9 +42,7 @@ export async function createPasskeyOwner({
43
42
  const attestation = await getWebAuthnAttestation({
44
43
  publicKey: {
45
44
  rp: {
46
- //@ts-expect-error
47
45
  id: window.location.hostname,
48
- //@ts-expect-error
49
46
  name: window.location.hostname,
50
47
  },
51
48
  authenticatorSelection: {
@@ -100,7 +97,6 @@ export async function createPasskeyOwner({
100
97
  };
101
98
  return owner;
102
99
  } catch (e) {
103
- //@ts-expect-error
104
100
  if (e instanceof DOMException && e.name === "InvalidStateError") {
105
101
  if (fallback) return await fallback();
106
102
  }
@@ -28,7 +28,6 @@ export async function getAutocompletePasskeyOwner({
28
28
  return;
29
29
  }
30
30
 
31
- //@ts-expect-error
32
31
  if (typeof window !== "undefined") {
33
32
  const challenge = generateRandomBuffer();
34
33
  try {
@@ -37,7 +36,6 @@ export async function getAutocompletePasskeyOwner({
37
36
  await getWebAuthnAssertion(base64UrlEncode(challenge), {
38
37
  mediation: "conditional",
39
38
  publicKey: {
40
- //@ts-expect-error
41
39
  rpId: window.location.hostname,
42
40
  userVerification: "required",
43
41
  },
@@ -22,7 +22,6 @@ export async function getPasskeyOwner({
22
22
  apiUrl?: string;
23
23
  withCredentials?: boolean;
24
24
  }): Promise<SmartAccountSigner | undefined> {
25
- //@ts-expect-error
26
25
  if (typeof window !== "undefined") {
27
26
  const challenge = generateRandomBuffer();
28
27
  try {
@@ -30,7 +29,6 @@ export async function getPasskeyOwner({
30
29
  const assertion = JSON.parse(
31
30
  await getWebAuthnAssertion(base64UrlEncode(challenge), {
32
31
  publicKey: {
33
- //@ts-expect-error
34
32
  rpId: window.location.hostname,
35
33
  userVerification: "required",
36
34
  allowCredentials: withCredentials
@@ -23,7 +23,6 @@ export const es256 = -7;
23
23
 
24
24
  export const generateRandomBuffer = (): ArrayBuffer => {
25
25
  const arr = new Uint8Array(32);
26
- //@ts-expect-error
27
26
  crypto.getRandomValues(arr);
28
27
  return arr.buffer;
29
28
  };
@@ -36,45 +36,51 @@ export abstract class Paymaster {
36
36
  paymasterProvider?: PaymasterAndBundlerProviders;
37
37
  shouldOverrideFee?: boolean;
38
38
  }): Promise<any> {
39
- try {
40
- const hexifiedUserOp = deepHexlify(await resolveProperties(userOp));
41
- let resolvedERC20UserOp;
42
- let hexifiedERC20UserOp: any;
43
- if (erc20UserOp) {
44
- resolvedERC20UserOp = await resolveProperties(erc20UserOp);
39
+ const hexifiedUserOp = deepHexlify(await resolveProperties(userOp));
40
+ let resolvedERC20UserOp;
41
+ let hexifiedERC20UserOp: any;
42
+ if (erc20UserOp) {
43
+ resolvedERC20UserOp = await resolveProperties(erc20UserOp);
45
44
 
46
- hexifiedERC20UserOp = hexifyUserOp(resolvedERC20UserOp);
47
- }
48
- const chainId = await getChainId(this.provider.getProjectId());
49
- if (!chainId) throw new Error("ChainId not found");
50
- let requestBodyParams = Object.fromEntries(
51
- Object.entries({
52
- projectId: this.provider.getProjectId(),
53
- chainId,
54
- userOp: hexifiedUserOp,
55
- entryPointAddress: ENTRYPOINT_ADDRESS,
56
- callData: callData instanceof Promise ? await callData : callData,
57
- tokenAddress: gasTokenAddress,
58
- erc20UserOp: hexifiedERC20UserOp,
59
- erc20CallData:
60
- erc20CallData instanceof Promise
61
- ? await erc20CallData
62
- : erc20CallData,
63
- paymasterProvider,
64
- shouldOverrideFee,
65
- }).filter(([_, value]) => value !== undefined)
66
- );
67
- const { data: paymasterResp } = await axios.post(
68
- `${PAYMASTER_URL}/sign`,
69
- {
70
- ...requestBodyParams,
71
- },
72
- { headers: { "Content-Type": "application/json" } }
73
- );
74
- return paymasterResp;
75
- } catch (error) {
76
- console.log(error);
77
- return undefined;
45
+ hexifiedERC20UserOp = hexifyUserOp(resolvedERC20UserOp);
78
46
  }
47
+ const chainId = await getChainId(this.provider.getProjectId());
48
+ if (!chainId) throw new Error("ChainId not found");
49
+ let requestBodyParams = Object.fromEntries(
50
+ Object.entries({
51
+ projectId: this.provider.getProjectId(),
52
+ chainId,
53
+ userOp: hexifiedUserOp,
54
+ entryPointAddress: ENTRYPOINT_ADDRESS,
55
+ callData: callData instanceof Promise ? await callData : callData,
56
+ gasTokenData:
57
+ gasTokenAddress && hexifiedERC20UserOp && erc20CallData
58
+ ? {
59
+ tokenAddress: gasTokenAddress,
60
+ erc20UserOp: hexifiedERC20UserOp,
61
+ erc20CallData:
62
+ erc20CallData instanceof Promise
63
+ ? await erc20CallData
64
+ : erc20CallData,
65
+ }
66
+ : undefined,
67
+ tokenAddress: gasTokenAddress,
68
+ erc20UserOp: hexifiedERC20UserOp,
69
+ erc20CallData:
70
+ erc20CallData instanceof Promise
71
+ ? await erc20CallData
72
+ : erc20CallData,
73
+ paymasterProvider,
74
+ shouldOverrideFee,
75
+ }).filter(([_, value]) => value !== undefined)
76
+ );
77
+ const { data: paymasterResp } = await axios.post(
78
+ `${PAYMASTER_URL}/getPaymasterAndData`,
79
+ {
80
+ ...requestBodyParams,
81
+ },
82
+ { headers: { "Content-Type": "application/json" } }
83
+ );
84
+ return paymasterResp;
79
85
  }
80
86
  }
@@ -3,6 +3,7 @@ import {
3
3
  type BytesLike,
4
4
  type UserOperationCallData,
5
5
  type UserOperationStruct,
6
+ type BatchUserOperationCallData,
6
7
  } from "@alchemy/aa-core";
7
8
  import axios from "axios";
8
9
  import {
@@ -14,12 +15,11 @@ import {
14
15
  } from "viem";
15
16
  import { ERC20Abi } from "../abis/ERC20Abi.js";
16
17
  import { KernelAccountAbi } from "../abis/KernelAccountAbi.js";
17
- import { MultiSendAbi } from "../abis/MultiSendAbi.js";
18
18
  import {
19
19
  PAYMASTER_URL,
20
20
  ENTRYPOINT_ADDRESS,
21
- MULTISEND_ADDR,
22
21
  ERC20_APPROVAL_AMOUNT,
22
+ MULTISEND_ADDR,
23
23
  } from "../constants.js";
24
24
  import {
25
25
  AccountNotConnected,
@@ -36,7 +36,13 @@ import {
36
36
  type PaymasterConfig,
37
37
  } from "./types.js";
38
38
  import { getChainId } from "../api/index.js";
39
+ import { MultiSendAbi } from "../abis/MultiSendAbi.js";
39
40
 
41
+ export function isBatchUserOperationCallData(
42
+ data: any
43
+ ): data is BatchUserOperationCallData {
44
+ return data && Array.isArray(data);
45
+ }
40
46
  export class TokenPaymaster extends Paymaster {
41
47
  constructor(
42
48
  provider: ZeroDevProvider,
@@ -68,7 +74,12 @@ export class TokenPaymaster extends Paymaster {
68
74
  async decodeMainCallFromCallData(
69
75
  kernelAddress: PromiseOrValue<string>,
70
76
  callData: PromiseOrValue<BytesLike>
71
- ): Promise<UserOperationCallDataWithDelegate | undefined> {
77
+ ): Promise<
78
+ | UserOperationCallData
79
+ | BatchUserOperationCallData
80
+ | UserOperationCallDataWithDelegate
81
+ | undefined
82
+ > {
72
83
  let data: Hex = "0x";
73
84
  if (callData instanceof Promise) {
74
85
  const _data = await callData;
@@ -113,6 +124,13 @@ export class TokenPaymaster extends Paymaster {
113
124
  };
114
125
  }
115
126
  return mainCall;
127
+ } else if (functionName === "executeBatch") {
128
+ const [txs] = args;
129
+ return txs.map((tx) => ({
130
+ target: tx.to,
131
+ value: tx.value ?? 0n,
132
+ data: tx.data,
133
+ }));
116
134
  }
117
135
  } catch (error) {
118
136
  return {
@@ -127,9 +145,11 @@ export class TokenPaymaster extends Paymaster {
127
145
  return;
128
146
  }
129
147
 
130
- async getERC20UserOp(
148
+ async getERC20UserOp<
149
+ T extends UserOperationCallData | BatchUserOperationCallData
150
+ >(
131
151
  struct: UserOperationStruct,
132
- mainCall: UserOperationCallDataWithDelegate,
152
+ mainCall: T,
133
153
  gasTokenAddress: Hex,
134
154
  paymasterAddress: Hex
135
155
  ): Promise<UserOperationStruct | undefined> {
@@ -146,10 +166,17 @@ export class TokenPaymaster extends Paymaster {
146
166
  if (!this.provider.account) {
147
167
  throw AccountNotConnected;
148
168
  }
149
- const erc20CallData = await this.provider.account.encodeBatchExecute([
150
- approveData,
151
- mainCall,
152
- ]);
169
+
170
+ let calls: BatchUserOperationCallData;
171
+
172
+ if (isBatchUserOperationCallData(mainCall)) {
173
+ calls = [approveData, ...mainCall];
174
+ } else {
175
+ calls = [approveData, mainCall];
176
+ }
177
+ const erc20CallData = await this.provider.account.encodeBatchExecute(
178
+ calls
179
+ );
153
180
  return {
154
181
  ...struct,
155
182
  callData: erc20CallData,
@@ -176,52 +203,46 @@ export class TokenPaymaster extends Paymaster {
176
203
  paymasterProvider?: PaymasterAndBundlerProviders,
177
204
  shouldOverrideFee?: boolean
178
205
  ): Promise<UserOperationStruct | undefined> {
179
- try {
180
- const mainCall = await this.decodeMainCallFromCallData(
181
- struct.sender,
182
- struct.callData
183
- );
184
- if (!mainCall) {
185
- throw IncorrectCallDataForTokenPaymaster;
186
- }
187
- const chainId = await getChainId(this.provider.getProjectId());
188
- if (!chainId) {
189
- throw new Error("ChainId not found");
190
- }
191
- const gasTokenAddress = getGasTokenAddress(
192
- this.paymasterConfig.gasToken,
193
- chainId
206
+ const mainCall = await this.decodeMainCallFromCallData(
207
+ struct.sender,
208
+ struct.callData
209
+ );
210
+ if (!mainCall) {
211
+ throw IncorrectCallDataForTokenPaymaster;
212
+ }
213
+ const chainId = await getChainId(this.provider.getProjectId());
214
+ if (!chainId) {
215
+ throw new Error("ChainId not found");
216
+ }
217
+ const gasTokenAddress = getGasTokenAddress(
218
+ this.paymasterConfig.gasToken,
219
+ chainId
220
+ );
221
+ let paymasterAddress = await this.getPaymasterAddress(paymasterProvider);
222
+ if (
223
+ gasTokenAddress !== undefined &&
224
+ paymasterAddress !== undefined &&
225
+ isAddress(paymasterAddress)
226
+ ) {
227
+ const erc20UserOp = await this.getERC20UserOp(
228
+ struct,
229
+ mainCall,
230
+ gasTokenAddress,
231
+ paymasterAddress
194
232
  );
195
- let paymasterAddress = await this.getPaymasterAddress(paymasterProvider);
196
- if (
197
- gasTokenAddress !== undefined &&
198
- paymasterAddress !== undefined &&
199
- isAddress(paymasterAddress)
200
- ) {
201
- const erc20UserOp = await this.getERC20UserOp(
202
- struct,
203
- mainCall,
204
- gasTokenAddress,
205
- paymasterAddress
206
- );
207
- if (!erc20UserOp) {
208
- return;
209
- }
210
- const paymasterResp = await this.signUserOp({
211
- userOp: struct,
212
- callData: struct.callData,
213
- gasTokenAddress,
214
- erc20UserOp,
215
- erc20CallData: erc20UserOp.callData,
216
- paymasterProvider,
217
- shouldOverrideFee,
218
- });
219
- if (paymasterResp) {
220
- return paymasterResp;
221
- }
233
+ if (!erc20UserOp) {
234
+ return;
222
235
  }
223
- } catch (error) {
224
- console.log(error);
236
+ const paymasterResp = await this.signUserOp({
237
+ userOp: struct,
238
+ callData: struct.callData,
239
+ gasTokenAddress,
240
+ erc20UserOp,
241
+ erc20CallData: erc20UserOp.callData,
242
+ paymasterProvider,
243
+ shouldOverrideFee,
244
+ });
245
+ return paymasterResp;
225
246
  }
226
247
  return;
227
248
  }
@@ -19,19 +19,12 @@ export class VerifyingPaymaster extends Paymaster {
19
19
  paymasterProvider?: PaymasterAndBundlerProviders,
20
20
  shouldOverrideFee?: boolean
21
21
  ): Promise<UserOperationStruct | undefined> {
22
- try {
23
- const hexifiedUserOp = deepHexlify(await resolveProperties(struct));
24
- const paymasterResp = await this.signUserOp({
25
- userOp: hexifiedUserOp,
26
- paymasterProvider,
27
- shouldOverrideFee,
28
- });
29
- if (paymasterResp) {
30
- return paymasterResp;
31
- }
32
- } catch (error) {
33
- console.log(error);
34
- }
35
- return;
22
+ const hexifiedUserOp = deepHexlify(await resolveProperties(struct));
23
+ const paymasterResp = await this.signUserOp({
24
+ userOp: hexifiedUserOp,
25
+ paymasterProvider,
26
+ shouldOverrideFee,
27
+ });
28
+ return paymasterResp;
36
29
  }
37
30
  }
@@ -298,8 +298,7 @@ export class ZeroDevProvider extends SmartAccountProvider<HttpTransport> {
298
298
  dummyPaymasterDataMiddleware: AccountMiddlewareFn = async (
299
299
  struct: UserOperationStruct
300
300
  ): Promise<UserOperationStruct> => {
301
- struct.paymasterAndData =
302
- "0xfe7dbcab8aaee4eb67943c1e6be95b1d065985c6000000000000000000000000000000000000000000000000000001869aa31cf400000000000000000000000000000000000000000000000000000000000000007dfe2190f34af27b265bae608717cdc9368b471fc0c097ab7b4088f255b4961e57b039e7e571b15221081c5dce7bcb93459b27a3ab65d2f8a889f4a40b4022801b";
301
+ struct.paymasterAndData = "0x";
303
302
  return struct;
304
303
  };
305
304