prool 0.0.25 → 0.1.1

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 (114) hide show
  1. package/{LICENSE → LICENSE.md} +1 -1
  2. package/README.md +46 -163
  3. package/{_lib/instance.d.ts → dist/Instance.d.ts} +28 -25
  4. package/dist/Instance.d.ts.map +1 -0
  5. package/{_lib/instance.js → dist/Instance.js} +9 -4
  6. package/dist/Instance.js.map +1 -0
  7. package/{_lib/pool.d.ts → dist/Pool.d.ts} +15 -13
  8. package/dist/Pool.d.ts.map +1 -0
  9. package/{_lib/pool.js → dist/Pool.js} +3 -3
  10. package/dist/Pool.js.map +1 -0
  11. package/{_lib/server.d.ts → dist/Server.d.ts} +7 -10
  12. package/dist/Server.d.ts.map +1 -0
  13. package/{_lib/server.js → dist/Server.js} +8 -9
  14. package/dist/Server.js.map +1 -0
  15. package/dist/index.d.ts +4 -0
  16. package/dist/index.d.ts.map +1 -0
  17. package/dist/index.js +4 -0
  18. package/dist/index.js.map +1 -0
  19. package/dist/instances/alto.d.ts +452 -0
  20. package/dist/instances/alto.d.ts.map +1 -0
  21. package/{_lib → dist}/instances/alto.js +4 -4
  22. package/dist/instances/alto.js.map +1 -0
  23. package/dist/instances/anvil.d.ts +458 -0
  24. package/dist/instances/anvil.d.ts.map +1 -0
  25. package/{_lib → dist}/instances/anvil.js +4 -4
  26. package/dist/instances/anvil.js.map +1 -0
  27. package/dist/instances/tempo.d.ts +189 -0
  28. package/dist/instances/tempo.d.ts.map +1 -0
  29. package/dist/instances/tempo.js +200 -0
  30. package/dist/instances/tempo.js.map +1 -0
  31. package/{_lib → dist/internal}/utils.d.ts +5 -5
  32. package/dist/internal/utils.d.ts.map +1 -0
  33. package/{_lib → dist/internal}/utils.js +37 -7
  34. package/dist/internal/utils.js.map +1 -0
  35. package/{_lib → dist}/processes/execa.d.ts +11 -10
  36. package/dist/processes/execa.d.ts.map +1 -0
  37. package/{_lib → dist}/processes/execa.js +1 -1
  38. package/dist/processes/execa.js.map +1 -0
  39. package/package.json +17 -16
  40. package/{instance.test.ts → src/Instance.test.ts} +12 -12
  41. package/{instance.ts → src/Instance.ts} +51 -42
  42. package/{pool.test.ts → src/Pool.test.ts} +41 -55
  43. package/{pool.ts → src/Pool.ts} +21 -19
  44. package/{server.test.ts → src/Server.test.ts} +26 -149
  45. package/{server.ts → src/Server.ts} +9 -11
  46. package/src/index.ts +3 -0
  47. package/{instances → src/instances}/alto.test.ts +8 -11
  48. package/src/instances/alto.ts +289 -0
  49. package/{instances → src/instances}/anvil.test.ts +5 -6
  50. package/src/instances/anvil.ts +306 -0
  51. package/{instances/silius.test.ts → src/instances/tempo.test.ts} +20 -44
  52. package/src/instances/tempo.ts +322 -0
  53. package/{utils.test.ts → src/internal/utils.test.ts} +20 -6
  54. package/{utils.ts → src/internal/utils.ts} +47 -17
  55. package/{processes → src/processes}/execa.test.ts +6 -11
  56. package/{processes → src/processes}/execa.ts +19 -15
  57. package/src/processes/index.ts +1 -0
  58. package/CHANGELOG.md +0 -154
  59. package/_lib/exports/index.d.ts +0 -5
  60. package/_lib/exports/index.d.ts.map +0 -1
  61. package/_lib/exports/index.js +0 -5
  62. package/_lib/exports/index.js.map +0 -1
  63. package/_lib/exports/instances.d.ts +0 -7
  64. package/_lib/exports/instances.d.ts.map +0 -1
  65. package/_lib/exports/instances.js +0 -7
  66. package/_lib/exports/instances.js.map +0 -1
  67. package/_lib/exports/processes.d.ts +0 -2
  68. package/_lib/exports/processes.d.ts.map +0 -1
  69. package/_lib/exports/processes.js +0 -2
  70. package/_lib/exports/processes.js.map +0 -1
  71. package/_lib/instance.d.ts.map +0 -1
  72. package/_lib/instance.js.map +0 -1
  73. package/_lib/instances/alto.d.ts +0 -449
  74. package/_lib/instances/alto.d.ts.map +0 -1
  75. package/_lib/instances/alto.js.map +0 -1
  76. package/_lib/instances/anvil.d.ts +0 -455
  77. package/_lib/instances/anvil.d.ts.map +0 -1
  78. package/_lib/instances/anvil.js.map +0 -1
  79. package/_lib/instances/rundler.d.ts +0 -604
  80. package/_lib/instances/rundler.d.ts.map +0 -1
  81. package/_lib/instances/rundler.js +0 -86
  82. package/_lib/instances/rundler.js.map +0 -1
  83. package/_lib/instances/silius.d.ts +0 -224
  84. package/_lib/instances/silius.d.ts.map +0 -1
  85. package/_lib/instances/silius.js +0 -117
  86. package/_lib/instances/silius.js.map +0 -1
  87. package/_lib/instances/stackup.d.ts +0 -86
  88. package/_lib/instances/stackup.d.ts.map +0 -1
  89. package/_lib/instances/stackup.js +0 -89
  90. package/_lib/instances/stackup.js.map +0 -1
  91. package/_lib/pool.d.ts.map +0 -1
  92. package/_lib/pool.js.map +0 -1
  93. package/_lib/processes/execa.d.ts.map +0 -1
  94. package/_lib/processes/execa.js.map +0 -1
  95. package/_lib/server.d.ts.map +0 -1
  96. package/_lib/server.js.map +0 -1
  97. package/_lib/utils.d.ts.map +0 -1
  98. package/_lib/utils.js.map +0 -1
  99. package/exports/index.test.ts +0 -16
  100. package/exports/index.ts +0 -29
  101. package/exports/instances.test.ts +0 -15
  102. package/exports/instances.ts +0 -13
  103. package/exports/processes.test.ts +0 -10
  104. package/exports/processes.ts +0 -8
  105. package/instances/alto.ts +0 -280
  106. package/instances/anvil.ts +0 -304
  107. package/instances/package.json +0 -5
  108. package/instances/rundler.test.ts +0 -111
  109. package/instances/rundler.ts +0 -451
  110. package/instances/silius.ts +0 -347
  111. package/instances/stackup.test.ts +0 -106
  112. package/instances/stackup.ts +0 -162
  113. package/processes/package.json +0 -5
  114. package/tsconfig.build.tsbuildinfo +0 -1
@@ -1,18 +1,17 @@
1
1
  import {
2
+ createServer as createServer_,
2
3
  type IncomingMessage,
3
4
  type Server,
4
5
  type ServerResponse,
5
- createServer as createServer_,
6
6
  } from 'node:http'
7
7
  import type { AddressInfo } from 'node:net'
8
8
  import httpProxy from 'http-proxy'
9
-
10
- import { type DefinePoolParameters, definePool } from './pool.js'
11
- import { extractPath } from './utils.js'
9
+ import { extractPath } from './internal/utils.js'
10
+ import * as Pool from './Pool.js'
12
11
 
13
12
  const { createProxyServer } = httpProxy
14
13
 
15
- export type CreateServerParameters = DefinePoolParameters<number> &
14
+ export type CreateServerParameters = Pool.define.Parameters<number> &
16
15
  (
17
16
  | {
18
17
  /** Host to run the server on. */
@@ -40,11 +39,10 @@ export type CreateServerReturnType = Omit<
40
39
  *
41
40
  * @example
42
41
  * ```
43
- * import { createServer } from 'prool'
44
- * import { anvil } from 'prool/instances'
42
+ * import { Instance, Server } from 'prool'
45
43
  *
46
- * const server = createServer({
47
- * instance: anvil(),
44
+ * const server = Server.create({
45
+ * instance: Instance.anvil(),
48
46
  * })
49
47
  *
50
48
  * const server = await server.start()
@@ -59,12 +57,12 @@ export type CreateServerReturnType = Omit<
59
57
  * // "http://localhost:8545/healthcheck"
60
58
  * ```
61
59
  */
62
- export function createServer(
60
+ export function create(
63
61
  parameters: CreateServerParameters,
64
62
  ): CreateServerReturnType {
65
63
  const { host = '::', instance, limit, port } = parameters
66
64
 
67
- const pool = definePool({ instance, limit })
65
+ const pool = Pool.define({ instance, limit })
68
66
  const proxy = createProxyServer({
69
67
  ignorePath: true,
70
68
  ws: true,
package/src/index.ts ADDED
@@ -0,0 +1,3 @@
1
+ export * as Instance from './Instance.js'
2
+ export * as Pool from './Pool.js'
3
+ export * as Server from './Server.js'
@@ -1,17 +1,14 @@
1
1
  import getPort from 'get-port'
2
+ import { Instance } from 'prool'
2
3
  import { afterEach, beforeAll, expect, test } from 'vitest'
3
-
4
4
  import { altoOptions } from '../../test/utils.js'
5
- import type { Instance } from '../instance.js'
6
- import { type AltoParameters, alto } from './alto.js'
7
- import { anvil } from './anvil.js'
8
5
 
9
- const instances: Instance[] = []
6
+ const instances: Instance.Instance[] = []
10
7
 
11
8
  const port = await getPort()
12
9
 
13
- const defineInstance = (parameters: Partial<AltoParameters> = {}) => {
14
- const instance = alto({
10
+ const defineInstance = (parameters: Partial<Instance.alto.Parameters> = {}) => {
11
+ const instance = Instance.alto({
15
12
  ...altoOptions({ port, pool: false }),
16
13
  ...parameters,
17
14
  })
@@ -20,8 +17,8 @@ const defineInstance = (parameters: Partial<AltoParameters> = {}) => {
20
17
  }
21
18
 
22
19
  beforeAll(() =>
23
- anvil({
24
- forkUrl: process.env.VITE_FORK_URL ?? 'https://eth.merkle.io',
20
+ Instance.anvil({
21
+ forkUrl: process.env['VITE_FORK_URL'] ?? 'https://eth.merkle.io',
25
22
  port,
26
23
  }).start(),
27
24
  )
@@ -64,7 +61,7 @@ test.skip('behavior: instance errored (duplicate ports)', async () => {
64
61
  await expect(() => instance_2.start()).rejects.toThrowError()
65
62
  })
66
63
 
67
- test('behavior: start and stop multiple times', async () => {
64
+ test.skip('behavior: start and stop multiple times', async () => {
68
65
  const instance = defineInstance()
69
66
 
70
67
  await instance.start()
@@ -100,7 +97,7 @@ test.skip('behavior: can subscribe to stderr', async () => {
100
97
  test('behavior: exit', async () => {
101
98
  const instance = defineInstance()
102
99
 
103
- let exitCode: number | null | undefined = undefined
100
+ let exitCode: number | null | undefined
104
101
  instance.on('exit', (code) => {
105
102
  exitCode = code
106
103
  })
@@ -0,0 +1,289 @@
1
+ import { resolve } from 'node:path'
2
+ import * as Instance from '../Instance.js'
3
+ import { toArgs } from '../internal/utils.js'
4
+ import { execa } from '../processes/execa.js'
5
+
6
+ /**
7
+ * Defines an Alto instance.
8
+ *
9
+ * @example
10
+ * ```ts
11
+ * const instance = Instance.alto({
12
+ * entrypoints: ['0x0000000071727De22E5E9d8BAf0edAc6f37da032'],
13
+ * rpcUrl: `http://localhost:8545`,
14
+ * executorPrivateKeys: ['0x...'],
15
+ * })
16
+ * await instance.start()
17
+ * // ...
18
+ * await instance.stop()
19
+ * ```
20
+ */
21
+ export const alto = Instance.define((parameters?: alto.Parameters) => {
22
+ const { ...args } = (parameters || {}) as alto.Parameters
23
+
24
+ const name = 'alto'
25
+ const process = execa({ name })
26
+
27
+ return {
28
+ _internal: {
29
+ args,
30
+ get process() {
31
+ return process._internal.process
32
+ },
33
+ },
34
+ host: 'localhost',
35
+ name,
36
+ port: args.port ?? 3000,
37
+ async start({ port = args.port ?? 3000 }, options) {
38
+ const binary = (() => {
39
+ if (args.binary) return [args.binary]
40
+ const libPath = (
41
+ 'resolve' in import.meta
42
+ ? import.meta.resolve('@pimlico/alto').split('file:')[1]
43
+ : require.resolve('@pimlico/alto')
44
+ )!
45
+ return ['node', resolve(libPath, '../cli/alto.js')]
46
+ })()
47
+
48
+ await process.start(($) => $`${binary} ${toArgs({ port, ...args })}`, {
49
+ ...options,
50
+ // Resolve when the process is listening via a "Server listening at" message.
51
+ resolver({ process, reject, resolve }) {
52
+ process.stdout.on('data', (data) => {
53
+ const message = data.toString()
54
+ if (message.includes('Server listening at')) resolve()
55
+ })
56
+ process.stderr.on('data', reject)
57
+ },
58
+ })
59
+ },
60
+ async stop() {
61
+ await process.stop()
62
+ },
63
+ }
64
+ })
65
+
66
+ export declare namespace alto {
67
+ export type Parameters = {
68
+ /**
69
+ * API version (used for internal Pimlico versioning compatibility).
70
+ */
71
+ apiVersion?: readonly string[] | undefined
72
+ /**
73
+ * Override the sender native token balance during estimation
74
+ */
75
+ balanceOverride?: boolean | undefined
76
+ /**
77
+ * Binary path of the `alto` executable.
78
+ */
79
+ binary?: string | undefined
80
+ /**
81
+ * Address of the `BundleBulker` contract.
82
+ */
83
+ bundleBulkerAddress?: `0x${string}` | undefined
84
+ /**
85
+ * Set if the bundler bundle user operations automatically or only when calling `debug_bundler_sendBundleNow`.
86
+ * @default "auto"
87
+ */
88
+ bundleMode?: 'auto' | 'manual' | undefined
89
+ /**
90
+ * Indicates weather the chain is a OP stack chain, arbitrum chain, or default EVM chain.
91
+ */
92
+ chainType?: 'default' | 'op-stack' | 'arbitrum' | undefined
93
+ /**
94
+ * Path to JSON config file.
95
+ */
96
+ config?: string | undefined
97
+ /**
98
+ * Skip user operation validation, use with caution.
99
+ */
100
+ dangerousSkipUserOperationValidation?: boolean | undefined
101
+ /**
102
+ * Default API version.
103
+ */
104
+ defaultApiVersion?: string | undefined
105
+ /**
106
+ * Enable debug endpoints.
107
+ * @default false
108
+ */
109
+ enableDebugEndpoints?: boolean | undefined
110
+ /**
111
+ * Include user ops with the same sender in the single bundle.
112
+ * @default true
113
+ */
114
+ enforceUniqueSendersPerBundle?: boolean | undefined
115
+ /**
116
+ * EntryPoint contract addresses.
117
+ */
118
+ entrypoints: readonly `0x${string}`[]
119
+ /**
120
+ * Address of the EntryPoint simulations contract.
121
+ */
122
+ entrypointSimulationContract?: `0x${string}` | undefined
123
+ /**
124
+ * Private keys of the executor accounts.
125
+ */
126
+ executorPrivateKeys?: readonly `0x${string}`[]
127
+ /**
128
+ * Interval to refill the signer balance (seconds).
129
+ * @default 1200
130
+ */
131
+ executorRefillInterval?: number | undefined
132
+ /**
133
+ * Should the node make expiration checks.
134
+ * @default true
135
+ */
136
+ expirationCheck?: boolean | undefined
137
+ /**
138
+ * Amount to multiply the gas prices fetched from the node.
139
+ * @default "100"
140
+ */
141
+ gasPriceBump?: string | undefined
142
+ /**
143
+ * Maximum that the gas prices fetched using pimlico_getUserOperationGasPrice will be accepted for (seconds).
144
+ * @default 10
145
+ */
146
+ gasPriceExpiry?: number | undefined
147
+ /**
148
+ * The minimum percentage of incoming user operation gas prices compared to the gas price used by the bundler to submit bundles.
149
+ * @default 101
150
+ */
151
+ gasPriceFloorPercent?: number | undefined
152
+ /**
153
+ * Amount to multiply the gas prices fetched using `pimlico_getUserOperationGasPrice`.
154
+ * @default "105,110,115"
155
+ */
156
+ gasPriceMultipliers?: readonly string[] | undefined
157
+ /**
158
+ * Use a fixed value for gas limits during bundle transaction gas limit estimations
159
+ */
160
+ fixedGasLimitForEstimation?: string | undefined
161
+ /**
162
+ * Flush stuck transactions with old nonces during bundler startup.
163
+ */
164
+ flushStuckTransactionsDuringStartup?: boolean | undefined
165
+ /**
166
+ * Log in JSON format.
167
+ */
168
+ json?: boolean | undefined
169
+ /**
170
+ * Send legacy transactions instead of an EIP-1559 transactions.
171
+ * @default false
172
+ */
173
+ legacyTransactions?: boolean | undefined
174
+ /**
175
+ * Calculate the bundle transaction gas limits locally instead of using the RPC gas limit estimation.
176
+ */
177
+ localGasLimitCalculation?: boolean | undefined
178
+ /**
179
+ * Default log level.
180
+ */
181
+ logLevel?:
182
+ | 'trace'
183
+ | 'debug'
184
+ | 'info'
185
+ | 'warn'
186
+ | 'error'
187
+ | 'fatal'
188
+ | undefined
189
+ /**
190
+ * Max block range for `eth_getLogs` calls.
191
+ */
192
+ maxBlockRange?: number | undefined
193
+ /**
194
+ * Maximum number of operations allowed in the mempool before a bundle is submitted.
195
+ * @default 10
196
+ */
197
+ maxBundleSize?: number | undefined
198
+ /**
199
+ * Maximum time to wait for a bundle to be submitted (ms).
200
+ * @default 1000
201
+ */
202
+ maxBundleWait?: number | undefined
203
+ /**
204
+ * Maximum amount of gas per bundle.
205
+ * @default "5000000"
206
+ */
207
+ maxGasPerBundle?: string | undefined
208
+ /**
209
+ * Maximum number of executor accounts to use from the list of executor private keys.
210
+ */
211
+ maxExecutors?: number | undefined
212
+ /**
213
+ * Maximum amount of parallel user ops to keep in the meempool (same sender, different nonce keys).
214
+ * @default 10
215
+ */
216
+ mempoolMaxParallelOps?: number | undefined
217
+ /**
218
+ * Maximum amount of sequential user ops to keep in the mempool (same sender and nonce key, different nonce values).
219
+ * @default 0
220
+ */
221
+ mempoolMaxQueuedOps?: number | undefined
222
+ /**
223
+ * Minimum stake required for a relay (in 10e18).
224
+ * @default 1
225
+ */
226
+ minEntityStake?: number | undefined
227
+ /**
228
+ * Minimum unstake delay (seconds).
229
+ * @default 1
230
+ */
231
+ minEntityUnstakeDelay?: number | undefined
232
+ /**
233
+ * Minimum balance required for each executor account (below which the utility account will refill).
234
+ */
235
+ minExecutorBalance?: string | undefined
236
+ /**
237
+ * Name of the network (used for metrics).
238
+ * @default "localhost"
239
+ */
240
+ networkName?: string | undefined
241
+ /**
242
+ * Amount to multiply the paymaster gas limits fetched from simulations.
243
+ */
244
+ paymasterGasLimitMultiplier?: string | undefined
245
+ /**
246
+ * Address of the `PerOpInflator` contract.
247
+ */
248
+ perOpInflatorAddress?: `0x${string}` | undefined
249
+ /**
250
+ * Polling interval for querying for new blocks (ms).
251
+ * @default 1000
252
+ */
253
+ pollingInterval?: number | undefined
254
+ /**
255
+ * Port to listen on.
256
+ * @default 3000
257
+ */
258
+ port?: number | undefined
259
+ /**
260
+ * RPC url to connect to.
261
+ */
262
+ rpcUrl: string
263
+ /**
264
+ * Enable safe mode (enforcing all ERC-4337 rules).
265
+ * @default true
266
+ */
267
+ safeMode?: boolean | undefined
268
+ /**
269
+ * RPC url to send transactions to (e.g. flashbots relay).
270
+ */
271
+ sendTransactionRpcUrl?: string | undefined
272
+ /**
273
+ * Timeout for incoming requests (in ms).
274
+ */
275
+ timeout?: number | undefined
276
+ /**
277
+ * Private key of the utility account.
278
+ */
279
+ utilityPrivateKey?: string | undefined
280
+ /**
281
+ * Maximum payload size for websocket messages in bytes (default to 1MB).
282
+ */
283
+ websocketMaxPayloadSize?: number | undefined
284
+ /**
285
+ * Enable websocket server.
286
+ */
287
+ websocket?: boolean | undefined
288
+ }
289
+ }
@@ -1,12 +1,11 @@
1
+ import { Instance } from 'prool'
1
2
  import { afterEach, expect, test } from 'vitest'
2
- import type { Instance } from '../instance.js'
3
- import { type AnvilParameters, anvil } from './anvil.js'
4
3
 
5
- const instances: Instance[] = []
4
+ const instances: Instance.Instance[] = []
6
5
  const timestamp = 1717114065
7
6
 
8
- const defineInstance = (parameters: AnvilParameters = {}) => {
9
- const instance = anvil(parameters)
7
+ const defineInstance = (parameters: Instance.anvil.Parameters = {}) => {
8
+ const instance = Instance.anvil(parameters)
10
9
  instances.push(instance)
11
10
  return instance
12
11
  }
@@ -100,7 +99,7 @@ test.skip('behavior: starts anvil with custom options', async () => {
100
99
  test('behavior: exit', async () => {
101
100
  const instance = defineInstance({ timestamp })
102
101
 
103
- let exitCode: number | null | undefined = undefined
102
+ let exitCode: number | null | undefined
104
103
  instance.on('exit', (code) => {
105
104
  exitCode = code
106
105
  })