viem 2.22.17 → 2.22.20

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 (134) hide show
  1. package/CHANGELOG.md +30 -0
  2. package/_cjs/actions/public/simulate.js +1 -1
  3. package/_cjs/actions/public/simulate.js.map +1 -1
  4. package/_cjs/chains/definitions/berachain.js +24 -0
  5. package/_cjs/chains/definitions/berachain.js.map +1 -0
  6. package/_cjs/chains/definitions/donatuz.js +29 -0
  7. package/_cjs/chains/definitions/donatuz.js.map +1 -0
  8. package/_cjs/chains/definitions/forta.js +25 -0
  9. package/_cjs/chains/definitions/forta.js.map +1 -0
  10. package/_cjs/chains/definitions/sidra.js +25 -0
  11. package/_cjs/chains/definitions/sidra.js.map +1 -0
  12. package/_cjs/chains/definitions/songbird.js +6 -0
  13. package/_cjs/chains/definitions/songbird.js.map +1 -1
  14. package/_cjs/chains/definitions/wmcTestnet.js +22 -0
  15. package/_cjs/chains/definitions/wmcTestnet.js.map +1 -0
  16. package/_cjs/chains/index.js +21 -11
  17. package/_cjs/chains/index.js.map +1 -1
  18. package/_cjs/errors/version.js +1 -1
  19. package/_cjs/experimental/erc7821/actions/execute.js +13 -57
  20. package/_cjs/experimental/erc7821/actions/execute.js.map +1 -1
  21. package/_cjs/experimental/erc7821/actions/executeBatches.js +33 -0
  22. package/_cjs/experimental/erc7821/actions/executeBatches.js.map +1 -0
  23. package/_cjs/experimental/erc7821/actions/supportsExecutionMode.js +11 -3
  24. package/_cjs/experimental/erc7821/actions/supportsExecutionMode.js.map +1 -1
  25. package/_cjs/experimental/erc7821/constants.js +1 -0
  26. package/_cjs/experimental/erc7821/constants.js.map +1 -1
  27. package/_cjs/experimental/erc7821/decorators/erc7821.js +2 -0
  28. package/_cjs/experimental/erc7821/decorators/erc7821.js.map +1 -1
  29. package/_cjs/experimental/erc7821/index.js +11 -1
  30. package/_cjs/experimental/erc7821/index.js.map +1 -1
  31. package/_cjs/experimental/erc7821/utils/encodeCalls.js +21 -0
  32. package/_cjs/experimental/erc7821/utils/encodeCalls.js.map +1 -0
  33. package/_cjs/experimental/erc7821/utils/encodeExecuteBatchesData.js +22 -0
  34. package/_cjs/experimental/erc7821/utils/encodeExecuteBatchesData.js.map +1 -0
  35. package/_cjs/experimental/erc7821/utils/encodeExecuteData.js +17 -0
  36. package/_cjs/experimental/erc7821/utils/encodeExecuteData.js.map +1 -0
  37. package/_cjs/experimental/erc7821/utils/getExecuteError.js +40 -0
  38. package/_cjs/experimental/erc7821/utils/getExecuteError.js.map +1 -0
  39. package/_esm/actions/public/simulate.js +1 -1
  40. package/_esm/actions/public/simulate.js.map +1 -1
  41. package/_esm/chains/definitions/berachain.js +21 -0
  42. package/_esm/chains/definitions/berachain.js.map +1 -0
  43. package/_esm/chains/definitions/donatuz.js +26 -0
  44. package/_esm/chains/definitions/donatuz.js.map +1 -0
  45. package/_esm/chains/definitions/forta.js +22 -0
  46. package/_esm/chains/definitions/forta.js.map +1 -0
  47. package/_esm/chains/definitions/sidra.js +22 -0
  48. package/_esm/chains/definitions/sidra.js.map +1 -0
  49. package/_esm/chains/definitions/songbird.js +6 -0
  50. package/_esm/chains/definitions/songbird.js.map +1 -1
  51. package/_esm/chains/definitions/wmcTestnet.js +19 -0
  52. package/_esm/chains/definitions/wmcTestnet.js.map +1 -0
  53. package/_esm/chains/index.js +5 -0
  54. package/_esm/chains/index.js.map +1 -1
  55. package/_esm/errors/version.js +1 -1
  56. package/_esm/experimental/erc7821/actions/execute.js +15 -59
  57. package/_esm/experimental/erc7821/actions/execute.js.map +1 -1
  58. package/_esm/experimental/erc7821/actions/executeBatches.js +121 -0
  59. package/_esm/experimental/erc7821/actions/executeBatches.js.map +1 -0
  60. package/_esm/experimental/erc7821/actions/supportsExecutionMode.js +11 -3
  61. package/_esm/experimental/erc7821/actions/supportsExecutionMode.js.map +1 -1
  62. package/_esm/experimental/erc7821/constants.js +1 -0
  63. package/_esm/experimental/erc7821/constants.js.map +1 -1
  64. package/_esm/experimental/erc7821/decorators/erc7821.js +2 -0
  65. package/_esm/experimental/erc7821/decorators/erc7821.js.map +1 -1
  66. package/_esm/experimental/erc7821/index.js +5 -1
  67. package/_esm/experimental/erc7821/index.js.map +1 -1
  68. package/_esm/experimental/erc7821/utils/encodeCalls.js +18 -0
  69. package/_esm/experimental/erc7821/utils/encodeCalls.js.map +1 -0
  70. package/_esm/experimental/erc7821/utils/encodeExecuteBatchesData.js +19 -0
  71. package/_esm/experimental/erc7821/utils/encodeExecuteBatchesData.js.map +1 -0
  72. package/_esm/experimental/erc7821/utils/encodeExecuteData.js +14 -0
  73. package/_esm/experimental/erc7821/utils/encodeExecuteData.js.map +1 -0
  74. package/_esm/experimental/erc7821/utils/getExecuteError.js +37 -0
  75. package/_esm/experimental/erc7821/utils/getExecuteError.js.map +1 -0
  76. package/_types/actions/public/simulate.d.ts.map +1 -1
  77. package/_types/chains/definitions/berachain.d.ts +37 -0
  78. package/_types/chains/definitions/berachain.d.ts.map +1 -0
  79. package/_types/chains/definitions/donatuz.d.ts +33 -0
  80. package/_types/chains/definitions/donatuz.d.ts.map +1 -0
  81. package/_types/chains/definitions/forta.d.ts +37 -0
  82. package/_types/chains/definitions/forta.d.ts.map +1 -0
  83. package/_types/chains/definitions/sidra.d.ts +37 -0
  84. package/_types/chains/definitions/sidra.d.ts.map +1 -0
  85. package/_types/chains/definitions/songbird.d.ts +6 -10
  86. package/_types/chains/definitions/songbird.d.ts.map +1 -1
  87. package/_types/chains/definitions/wmcTestnet.d.ts +37 -0
  88. package/_types/chains/definitions/wmcTestnet.d.ts.map +1 -0
  89. package/_types/chains/index.d.ts +5 -0
  90. package/_types/chains/index.d.ts.map +1 -1
  91. package/_types/errors/version.d.ts +1 -1
  92. package/_types/experimental/erc7821/actions/execute.d.ts +3 -4
  93. package/_types/experimental/erc7821/actions/execute.d.ts.map +1 -1
  94. package/_types/experimental/erc7821/actions/executeBatches.d.ts +121 -0
  95. package/_types/experimental/erc7821/actions/executeBatches.d.ts.map +1 -0
  96. package/_types/experimental/erc7821/actions/supportsExecutionMode.d.ts +1 -1
  97. package/_types/experimental/erc7821/actions/supportsExecutionMode.d.ts.map +1 -1
  98. package/_types/experimental/erc7821/constants.d.ts +1 -0
  99. package/_types/experimental/erc7821/constants.d.ts.map +1 -1
  100. package/_types/experimental/erc7821/decorators/erc7821.d.ts +93 -0
  101. package/_types/experimental/erc7821/decorators/erc7821.d.ts.map +1 -1
  102. package/_types/experimental/erc7821/index.d.ts +5 -1
  103. package/_types/experimental/erc7821/index.d.ts.map +1 -1
  104. package/_types/experimental/erc7821/utils/encodeCalls.d.ts +8 -0
  105. package/_types/experimental/erc7821/utils/encodeCalls.d.ts.map +1 -0
  106. package/_types/experimental/erc7821/utils/encodeExecuteBatchesData.d.ts +21 -0
  107. package/_types/experimental/erc7821/utils/encodeExecuteBatchesData.d.ts.map +1 -0
  108. package/_types/experimental/erc7821/utils/encodeExecuteData.d.ts +16 -0
  109. package/_types/experimental/erc7821/utils/encodeExecuteData.d.ts.map +1 -0
  110. package/_types/experimental/erc7821/utils/getExecuteError.d.ts +12 -0
  111. package/_types/experimental/erc7821/utils/getExecuteError.d.ts.map +1 -0
  112. package/_types/types/calls.d.ts +21 -0
  113. package/_types/types/calls.d.ts.map +1 -1
  114. package/actions/public/simulate.ts +8 -7
  115. package/chains/definitions/berachain.ts +20 -0
  116. package/chains/definitions/donatuz.ts +26 -0
  117. package/chains/definitions/forta.ts +22 -0
  118. package/chains/definitions/sidra.ts +22 -0
  119. package/chains/definitions/songbird.ts +6 -0
  120. package/chains/definitions/wmcTestnet.ts +19 -0
  121. package/chains/index.ts +5 -0
  122. package/errors/version.ts +1 -1
  123. package/experimental/erc7821/actions/execute.ts +28 -89
  124. package/experimental/erc7821/actions/executeBatches.ts +194 -0
  125. package/experimental/erc7821/actions/supportsExecutionMode.ts +22 -9
  126. package/experimental/erc7821/constants.ts +2 -0
  127. package/experimental/erc7821/decorators/erc7821.ts +109 -0
  128. package/experimental/erc7821/index.ts +28 -1
  129. package/experimental/erc7821/utils/encodeCalls.ts +38 -0
  130. package/experimental/erc7821/utils/encodeExecuteBatchesData.ts +48 -0
  131. package/experimental/erc7821/utils/encodeExecuteData.ts +42 -0
  132. package/experimental/erc7821/utils/getExecuteError.ts +66 -0
  133. package/package.json +1 -1
  134. package/types/calls.ts +18 -0
@@ -5,17 +5,24 @@ import type { Transport } from '../../../clients/transports/createTransport.js'
5
5
  import type { ErrorType } from '../../../errors/utils.js'
6
6
  import type { Chain } from '../../../types/chain.js'
7
7
  import type { Hex } from '../../../types/misc.js'
8
+ import { withCache } from '../../../utils/promise/withCache.js'
8
9
  import { abi, executionMode } from '../constants.js'
9
10
 
10
11
  export type SupportsExecutionModeParameters = {
11
12
  address: Address
12
- opData?: Hex | undefined
13
+ mode?: 'default' | 'opData' | 'batchOfBatches' | Hex
13
14
  }
14
15
 
15
16
  export type SupportsExecutionModeReturnType = boolean
16
17
 
17
18
  export type SupportsExecutionModeErrorType = ErrorType
18
19
 
20
+ const toSerializedMode = {
21
+ default: executionMode.default,
22
+ opData: executionMode.opData,
23
+ batchOfBatches: executionMode.batchOfBatches,
24
+ } as const
25
+
19
26
  /**
20
27
  * Checks if the contract supports the ERC-7821 execution mode.
21
28
  *
@@ -45,15 +52,21 @@ export async function supportsExecutionMode<
45
52
  client: Client<Transport, chain>,
46
53
  parameters: SupportsExecutionModeParameters,
47
54
  ): Promise<SupportsExecutionModeReturnType> {
48
- const { address, opData } = parameters
49
- const mode = opData ? executionMode.opData : executionMode.default
55
+ const { address, mode: m = 'default' } = parameters
56
+ const mode = m.startsWith('0x') ? m : (toSerializedMode as any)[m]
50
57
  try {
51
- return await readContract(client, {
52
- abi,
53
- address,
54
- functionName: 'supportsExecutionMode',
55
- args: [mode],
56
- })
58
+ return await withCache(
59
+ () =>
60
+ readContract(client, {
61
+ abi,
62
+ address,
63
+ functionName: 'supportsExecutionMode',
64
+ args: [mode],
65
+ }),
66
+ {
67
+ cacheKey: `supportsExecutionMode.${address}.${mode}`,
68
+ },
69
+ )
57
70
  } catch {
58
71
  return false
59
72
  }
@@ -59,4 +59,6 @@ export const abi = [
59
59
  export const executionMode = {
60
60
  default: '0x0100000000000000000000000000000000000000000000000000000000000000',
61
61
  opData: '0x0100000000007821000100000000000000000000000000000000000000000000',
62
+ batchOfBatches:
63
+ '0x0100000000007821000200000000000000000000000000000000000000000000',
62
64
  } as const
@@ -7,6 +7,12 @@ import {
7
7
  type ExecuteReturnType,
8
8
  execute,
9
9
  } from '../actions/execute.js'
10
+ import {
11
+ type Batch,
12
+ type ExecuteBatchesParameters,
13
+ type ExecuteBatchesReturnType,
14
+ executeBatches,
15
+ } from '../actions/executeBatches.js'
10
16
  import {
11
17
  type SupportsExecutionModeParameters,
12
18
  type SupportsExecutionModeReturnType,
@@ -91,6 +97,108 @@ export type Erc7821Actions<
91
97
  >(
92
98
  parameters: ExecuteParameters<calls, chain, account, chainOverride>,
93
99
  ) => Promise<ExecuteReturnType>
100
+ /**
101
+ * Executes batches of call(s) using "batch of batches" mode on an [ERC-7821-compatible contract](https://eips.ethereum.org/EIPS/eip-7821).
102
+ *
103
+ * @example
104
+ * ```ts
105
+ * import { createClient, http, parseEther } from 'viem'
106
+ * import { privateKeyToAccount } from 'viem/accounts'
107
+ * import { mainnet } from 'viem/chains'
108
+ * import { erc7821Actions } from 'viem/experimental'
109
+ *
110
+ * const account = privateKeyToAccount('0x...')
111
+ *
112
+ * const client = createClient({
113
+ * chain: mainnet,
114
+ * transport: http(),
115
+ * }).extend(erc7821Actions())
116
+ *
117
+ * const hash = await client.executeBatches({
118
+ * account,
119
+ * batches: [
120
+ * {
121
+ * calls: [
122
+ * {
123
+ * to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
124
+ * value: parseEther('1'),
125
+ * },
126
+ * ],
127
+ * },
128
+ * {
129
+ * calls: [
130
+ * {
131
+ * to: '0xcb98643b8786950F0461f3B0edf99D88F274574D',
132
+ * value: parseEther('2'),
133
+ * },
134
+ * {
135
+ * data: '0xdeadbeef',
136
+ * to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
137
+ * },
138
+ * ],
139
+ * },
140
+ * ],
141
+ * to: account.address,
142
+ * })
143
+ * ```
144
+ *
145
+ * @example
146
+ * ```ts
147
+ * // Account Hoisting
148
+ * import { createClient, http, parseEther } from 'viem'
149
+ * import { privateKeyToAccount } from 'viem/accounts'
150
+ * import { mainnet } from 'viem/chains'
151
+ * import { erc7821Actions } from 'viem/experimental'
152
+ *
153
+ * const account = privateKeyToAccount('0x...')
154
+ *
155
+ * const client = createClient({
156
+ * chain: mainnet,
157
+ * transport: http(),
158
+ * }).extend(erc7821Actions())
159
+ *
160
+ * const hash = await client.executeBatches({
161
+ * batches: [
162
+ * {
163
+ * calls: [
164
+ * {
165
+ * to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
166
+ * value: parseEther('1'),
167
+ * },
168
+ * ],
169
+ * },
170
+ * {
171
+ * calls: [
172
+ * {
173
+ * to: '0xcb98643b8786950F0461f3B0edf99D88F274574D',
174
+ * value: parseEther('2'),
175
+ * },
176
+ * {
177
+ * data: '0xdeadbeef',
178
+ * to: '0x70997970c51812dc3a010c7d01b50e0d17dc79c8',
179
+ * },
180
+ * ],
181
+ * },
182
+ * ],
183
+ * to: account.address,
184
+ * })
185
+ * ```
186
+ *
187
+ * @param client - Client to use.
188
+ * @param parameters - {@link ExecuteBatchesParameters}
189
+ * @returns Transaction hash. {@link ExecuteBatchesReturnType}
190
+ */
191
+ executeBatches: <
192
+ const batches extends readonly Batch[],
193
+ chainOverride extends Chain | undefined = undefined,
194
+ >(
195
+ parameters: ExecuteBatchesParameters<
196
+ batches,
197
+ chain,
198
+ account,
199
+ chainOverride
200
+ >,
201
+ ) => Promise<ExecuteBatchesReturnType>
94
202
  /**
95
203
  * Checks if the contract supports the ERC-7821 execution mode.
96
204
  *
@@ -142,6 +250,7 @@ export function erc7821Actions() {
142
250
  ): Erc7821Actions<chain, account> => {
143
251
  return {
144
252
  execute: (parameters) => execute(client, parameters),
253
+ executeBatches: (parameters) => executeBatches(client, parameters),
145
254
  supportsExecutionMode: (parameters) =>
146
255
  supportsExecutionMode(client, parameters),
147
256
  }
@@ -1,4 +1,3 @@
1
- /** */
2
1
  // biome-ignore lint/performance/noBarrelFile: entrypoint
3
2
  export {
4
3
  type ExecuteErrorType,
@@ -6,6 +5,12 @@ export {
6
5
  type ExecuteReturnType,
7
6
  execute,
8
7
  } from './actions/execute.js'
8
+ export {
9
+ type ExecuteBatchesErrorType,
10
+ type ExecuteBatchesParameters,
11
+ type ExecuteBatchesReturnType,
12
+ executeBatches,
13
+ } from './actions/executeBatches.js'
9
14
  export {
10
15
  type SupportsExecutionModeErrorType,
11
16
  type SupportsExecutionModeParameters,
@@ -21,3 +26,25 @@ export {
21
26
  } from './errors.js'
22
27
 
23
28
  export { type Erc7821Actions, erc7821Actions } from './decorators/erc7821.js'
29
+
30
+ export {
31
+ type EncodeCallsErrorType,
32
+ encodeCalls,
33
+ } from './utils/encodeCalls.js'
34
+ export {
35
+ type EncodeExecuteBatchesDataErrorType,
36
+ type EncodeExecuteBatchesDataParameters,
37
+ type EncodeExecuteBatchesDataReturnType,
38
+ encodeExecuteBatchesData,
39
+ } from './utils/encodeExecuteBatchesData.js'
40
+ export {
41
+ type EncodeExecuteDataErrorType,
42
+ type EncodeExecuteDataParameters,
43
+ type EncodeExecuteDataReturnType,
44
+ encodeExecuteData,
45
+ } from './utils/encodeExecuteData.js'
46
+ export {
47
+ type GetExecuteErrorParameters,
48
+ type GetExecuteErrorReturnType,
49
+ getExecuteError,
50
+ } from './utils/getExecuteError.js'
@@ -0,0 +1,38 @@
1
+ import * as AbiParameters from 'ox/AbiParameters'
2
+
3
+ import type { ErrorType } from '../../../errors/utils.js'
4
+ import type { Call, Calls } from '../../../types/calls.js'
5
+ import type { Hex } from '../../../types/misc.js'
6
+ import {
7
+ type EncodeFunctionDataErrorType,
8
+ encodeFunctionData,
9
+ } from '../../../utils/abi/encodeFunctionData.js'
10
+
11
+ export type EncodeCallsErrorType =
12
+ | AbiParameters.encode.ErrorType
13
+ | AbiParameters.from.ErrorType
14
+ | EncodeFunctionDataErrorType
15
+ | ErrorType
16
+
17
+ export function encodeCalls(
18
+ calls_: Calls<readonly unknown[]>,
19
+ opData?: Hex | undefined,
20
+ ) {
21
+ const calls = calls_.map((call_) => {
22
+ const call = call_ as Call
23
+ return {
24
+ data: call.abi ? encodeFunctionData(call) : (call.data ?? '0x'),
25
+ value: call.value ?? 0n,
26
+ target: call.to,
27
+ }
28
+ })
29
+
30
+ return AbiParameters.encode(
31
+ AbiParameters.from([
32
+ 'struct Call { address target; uint256 value; bytes data; }',
33
+ 'Call[] calls',
34
+ ...(opData ? ['bytes opData'] : []),
35
+ ]),
36
+ [calls, ...(opData ? [opData] : [])] as any,
37
+ )
38
+ }
@@ -0,0 +1,48 @@
1
+ import type { Narrow } from 'abitype'
2
+ import * as AbiParameters from 'ox/AbiParameters'
3
+ import type { ErrorType } from '../../../errors/utils.js'
4
+
5
+ import type { Batches } from '../../../types/calls.js'
6
+ import type { Hex } from '../../../types/misc.js'
7
+ import {
8
+ type EncodeFunctionDataErrorType,
9
+ encodeFunctionData,
10
+ } from '../../../utils/abi/encodeFunctionData.js'
11
+ import { abi, executionMode } from '../constants.js'
12
+ import { type EncodeCallsErrorType, encodeCalls } from './encodeCalls.js'
13
+
14
+ /** @internal */
15
+ export type Batch = { calls: readonly unknown[]; opData?: Hex | undefined }
16
+
17
+ export type EncodeExecuteBatchesDataParameters<
18
+ batches extends readonly Batch[] = readonly Batch[],
19
+ > = {
20
+ /** Batches to execute. */
21
+ batches: Batches<Narrow<batches>, { opData?: Hex | undefined }>
22
+ }
23
+
24
+ export type EncodeExecuteBatchesDataReturnType = Hex
25
+
26
+ export type EncodeExecuteBatchesDataErrorType =
27
+ | EncodeCallsErrorType
28
+ | EncodeFunctionDataErrorType
29
+ | ErrorType
30
+
31
+ export function encodeExecuteBatchesData<batches extends readonly Batch[]>(
32
+ parameters: EncodeExecuteBatchesDataParameters<batches>,
33
+ ): EncodeExecuteBatchesDataReturnType {
34
+ const { batches } = parameters
35
+
36
+ const encodedBatches = AbiParameters.encode(AbiParameters.from('bytes[]'), [
37
+ batches.map((b) => {
38
+ const batch = b as Batch
39
+ return encodeCalls(batch.calls, batch.opData)
40
+ }),
41
+ ])
42
+
43
+ return encodeFunctionData({
44
+ abi,
45
+ functionName: 'execute',
46
+ args: [executionMode.batchOfBatches, encodedBatches],
47
+ })
48
+ }
@@ -0,0 +1,42 @@
1
+ import type { Narrow } from 'abitype'
2
+
3
+ import type { ErrorType } from '../../../errors/utils.js'
4
+ import type { Calls } from '../../../types/calls.js'
5
+ import type { Hex } from '../../../types/misc.js'
6
+ import {
7
+ type EncodeFunctionDataErrorType,
8
+ encodeFunctionData,
9
+ } from '../../../utils/abi/encodeFunctionData.js'
10
+ import { abi, executionMode } from '../constants.js'
11
+ import { type EncodeCallsErrorType, encodeCalls } from './encodeCalls.js'
12
+
13
+ export type EncodeExecuteDataParameters<
14
+ calls extends readonly unknown[] = readonly unknown[],
15
+ > = {
16
+ /** Calls to execute. */
17
+ calls: Calls<Narrow<calls>>
18
+ /** Additional data to include for execution. */
19
+ opData?: Hex | undefined
20
+ }
21
+
22
+ export type EncodeExecuteDataReturnType = Hex
23
+
24
+ export type EncodeExecuteDataErrorType =
25
+ | EncodeCallsErrorType
26
+ | EncodeFunctionDataErrorType
27
+ | ErrorType
28
+
29
+ export function encodeExecuteData<const calls extends readonly unknown[]>(
30
+ parameters: EncodeExecuteDataParameters<calls>,
31
+ ): EncodeExecuteDataReturnType {
32
+ const { calls, opData } = parameters
33
+
34
+ const encodedCalls = encodeCalls(calls, opData)
35
+ const mode = opData ? executionMode.opData : executionMode.default
36
+
37
+ return encodeFunctionData({
38
+ abi,
39
+ functionName: 'execute',
40
+ args: [mode, encodedCalls],
41
+ })
42
+ }
@@ -0,0 +1,66 @@
1
+ import type { Abi, Narrow } from 'abitype'
2
+ import * as AbiError from 'ox/AbiError'
3
+
4
+ import type { BaseError } from '../../../errors/base.js'
5
+ import type { Call, Calls } from '../../../types/calls.js'
6
+ import type { Hex } from '../../../types/misc.js'
7
+ import { decodeErrorResult } from '../../../utils/abi/decodeErrorResult.js'
8
+ import {
9
+ type GetContractErrorReturnType,
10
+ getContractError,
11
+ } from '../../../utils/errors/getContractError.js'
12
+ import {
13
+ FunctionSelectorNotRecognizedError,
14
+ type FunctionSelectorNotRecognizedErrorType,
15
+ } from '../errors.js'
16
+
17
+ export type GetExecuteErrorParameters<
18
+ calls extends readonly unknown[] = readonly unknown[],
19
+ > = {
20
+ /** Calls to execute. */
21
+ calls: Calls<Narrow<calls>>
22
+ }
23
+
24
+ export type GetExecuteErrorReturnType =
25
+ | FunctionSelectorNotRecognizedErrorType
26
+ | GetContractErrorReturnType
27
+
28
+ export function getExecuteError<const calls extends readonly unknown[]>(
29
+ e: BaseError,
30
+ parameters: GetExecuteErrorParameters<calls>,
31
+ ): GetExecuteErrorReturnType {
32
+ const error = e.walk((e) => 'data' in (e as Error)) as
33
+ | (BaseError & { data?: Hex | undefined })
34
+ | undefined
35
+
36
+ if (!error?.data) throw e
37
+ if (
38
+ error.data ===
39
+ AbiError.getSelector(AbiError.from('error FnSelectorNotRecognized()'))
40
+ )
41
+ return new FunctionSelectorNotRecognizedError() as never
42
+
43
+ let matched: Call | null = null
44
+ for (const c of parameters.calls) {
45
+ const call = c as Call
46
+ if (!call.abi) continue
47
+ try {
48
+ const matches = Boolean(
49
+ decodeErrorResult({
50
+ abi: call.abi,
51
+ data: error.data!,
52
+ }),
53
+ )
54
+ if (!matches) continue
55
+ matched = call
56
+ } catch {}
57
+ }
58
+ if (!matched) throw e
59
+
60
+ return getContractError(error as BaseError, {
61
+ abi: matched.abi as Abi,
62
+ address: matched.to,
63
+ args: matched.args,
64
+ functionName: matched.functionName,
65
+ })
66
+ }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "viem",
3
3
  "description": "TypeScript Interface for Ethereum",
4
- "version": "2.22.17",
4
+ "version": "2.22.20",
5
5
  "main": "./_cjs/index.js",
6
6
  "module": "./_esm/index.js",
7
7
  "types": "./_types/index.d.ts",
package/types/calls.ts CHANGED
@@ -45,3 +45,21 @@ export type Calls<
45
45
  ? readonly Prettify<call>[]
46
46
  : // Fallback
47
47
  readonly OneOf<Call>[]
48
+
49
+ export type Batches<
50
+ batches extends readonly { calls: readonly unknown[] }[],
51
+ properties extends Record<string, any> = {},
52
+ ///
53
+ result extends readonly any[] = [],
54
+ > = batches extends readonly [infer batch extends { calls: readonly unknown[] }]
55
+ ? [...result, { calls: Calls<batch['calls']> } & properties]
56
+ : batches extends readonly [
57
+ infer batch extends { calls: readonly unknown[] },
58
+ ...infer rest extends readonly { calls: readonly unknown[] }[],
59
+ ]
60
+ ? Batches<
61
+ [...rest],
62
+ properties,
63
+ [...result, { calls: Calls<batch['calls']> } & properties]
64
+ >
65
+ : batches