rocketh 0.10.0 → 0.10.2

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.
package/dist/index.d.cts CHANGED
@@ -1,4 +1,4 @@
1
- import { EIP1193Account, EIP1193DATA, EIP1193QUANTITY, EIP1193SignerProvider, EIP1193ProviderWithoutEvents, EIP1193WalletProvider, EIP1193TransactionReceipt, EIP1193GenericRequestProvider } from 'eip-1193';
1
+ import { EIP1193ProviderWithoutEvents, EIP1193GenericRequestProvider, EIP1193Web3ClientVersionRequest, EIP1193Web3SHARequest, EIP1193NetVersionRequest, EIP1193NetListeningRequest, EIP1193NetPeerCountRequest, EIP1193ProtocolVersionRequest, EIP1193SyncingRequest, EIP1193SyncingStatus, EIP1193CoinbaseRequest, EIP1193GasPriceRequest, EIP1193AccountsRequest, EIP1193Accounts, EIP1193BlockNumberRequest, EIP1193GetBalanceRequest, EIP1193GetStorageAtRequest, EIP1193GetTransactionCountRequest, EIP1193GetTransactionCountByHashRequest, EIP1193GetTransactionCountByNumberRequest, EIP1193GetUncleCountByBlockHashRequest, EIP1193GetUncleCountByBlockNumberRequest, EIP1193GetCodeRequest, EIP1193LegacySignRequest, EIP1193SignTransactionRequest, EIP1193SendTransactionRequest, EIP1193SendRawTransactionRequest, EIP1193CallRequest, EIP1193EstimateGasRequest, EIP1193GetBlockByHashRequest, EIP1193Block, EIP1193BlockWithTransactions, EIP1193GetBlockByNumberRequest, EIP1193GetTransactionByHashRequest, EIP1193Transaction, EIP1193GetTransactionByBlockHashAndIndexRequest, EIP1193GetTransactionByBlockNumberAndIndexRequest, EIP1193GetTransactionReceiptRequest, EIP1193TransactionReceipt, EIP1193GetUncleByBlockHashAndIndexRequest, EIP1193GetUncleByBlockNumberAndIndexRequest, EIP1193GetLogsRequest, EIP1193Log, EIP1193PersonalSignRequest, EIP1193PTypedSignv4Request, EIP1193PTypedSignRequest, EIP1193ChainIdRequest, EIP1193RequestAccountsRequest, ERIP1193SwitchChainRequest, EIP1193SwitchChainError, ERIP1193AddChainRequest, EIP1193AddChainError, EIP1193SubscribeRequest, EIP1193UnsubscribeRequest, EIP1193GenericRequest, EIP1193Account, EIP1193DATA, EIP1193QUANTITY, EIP1193SignerProvider, EIP1193WalletProvider } from 'eip-1193';
2
2
  import * as abitype from 'abitype';
3
3
  import { Abi, Narrow } from 'abitype';
4
4
  export { Abi, AbiConstructor, AbiError, AbiEvent, AbiFallback, AbiFunction, AbiReceive } from 'abitype';
@@ -12,6 +12,64 @@ type ProgressIndicator = {
12
12
  fail(msg?: string): ProgressIndicator;
13
13
  };
14
14
 
15
+ declare abstract class BaseProvider implements EIP1193ProviderWithoutEvents {
16
+ protected provider: EIP1193GenericRequestProvider;
17
+ constructor(provider: EIP1193GenericRequestProvider);
18
+ request(args: EIP1193Web3ClientVersionRequest): Promise<string>;
19
+ request(args: EIP1193Web3SHARequest): Promise<`0x${string}`>;
20
+ request(args: EIP1193NetVersionRequest): Promise<`0x${string}`>;
21
+ request(args: EIP1193NetListeningRequest): Promise<boolean>;
22
+ request(args: EIP1193NetPeerCountRequest): Promise<`0x${string}`>;
23
+ request(args: EIP1193ProtocolVersionRequest): Promise<string>;
24
+ request(args: EIP1193SyncingRequest): Promise<false | EIP1193SyncingStatus>;
25
+ request(args: EIP1193CoinbaseRequest): Promise<`0x${string}`>;
26
+ request(args: EIP1193GasPriceRequest): Promise<`0x${string}`>;
27
+ request(args: EIP1193AccountsRequest): Promise<EIP1193Accounts>;
28
+ request(args: EIP1193BlockNumberRequest): Promise<`0x${string}`>;
29
+ request(args: EIP1193GetBalanceRequest): Promise<`0x${string}`>;
30
+ request(args: EIP1193GetStorageAtRequest): Promise<`0x${string}`>;
31
+ request(args: EIP1193GetTransactionCountRequest): Promise<`0x${string}`>;
32
+ request(args: EIP1193GetTransactionCountByHashRequest): Promise<`0x${string}`>;
33
+ request(args: EIP1193GetTransactionCountByNumberRequest): Promise<`0x${string}`>;
34
+ request(args: EIP1193GetUncleCountByBlockHashRequest): Promise<`0x${string}`>;
35
+ request(args: EIP1193GetUncleCountByBlockNumberRequest): Promise<`0x${string}`>;
36
+ request(args: EIP1193GetCodeRequest): Promise<`0x${string}`>;
37
+ request(args: EIP1193LegacySignRequest): Promise<`0x${string}`>;
38
+ request(args: EIP1193SignTransactionRequest): Promise<`0x${string}`>;
39
+ request(args: EIP1193SendTransactionRequest): Promise<`0x${string}`>;
40
+ request(args: EIP1193SendRawTransactionRequest): Promise<`0x${string}`>;
41
+ request(args: EIP1193CallRequest): Promise<`0x${string}`>;
42
+ request(args: EIP1193EstimateGasRequest): Promise<`0x${string}`>;
43
+ request(args: EIP1193GetBlockByHashRequest<false>): Promise<EIP1193Block | null>;
44
+ request(args: EIP1193GetBlockByHashRequest<true>): Promise<EIP1193BlockWithTransactions | null>;
45
+ request(args: EIP1193GetBlockByNumberRequest<false>): Promise<EIP1193Block | null>;
46
+ request(args: EIP1193GetBlockByNumberRequest<true>): Promise<EIP1193BlockWithTransactions | null>;
47
+ request(args: EIP1193GetTransactionByHashRequest): Promise<EIP1193Transaction | null>;
48
+ request(args: EIP1193GetTransactionByBlockHashAndIndexRequest): Promise<EIP1193Transaction | null>;
49
+ request(args: EIP1193GetTransactionByBlockNumberAndIndexRequest): Promise<EIP1193Transaction | null>;
50
+ request(args: EIP1193GetTransactionReceiptRequest): Promise<EIP1193TransactionReceipt | null>;
51
+ request(args: EIP1193GetUncleByBlockHashAndIndexRequest): Promise<EIP1193Block | null>;
52
+ request(args: EIP1193GetUncleByBlockNumberAndIndexRequest): Promise<EIP1193Block | null>;
53
+ request(args: EIP1193GetLogsRequest): Promise<EIP1193Log[]>;
54
+ request(args: EIP1193PersonalSignRequest): Promise<`0x${string}`>;
55
+ request(args: EIP1193PTypedSignv4Request): Promise<`0x${string}`>;
56
+ request(args: EIP1193PTypedSignRequest): Promise<`0x${string}`>;
57
+ request(args: EIP1193ChainIdRequest): Promise<`0x${string}`>;
58
+ request(args: EIP1193RequestAccountsRequest): Promise<EIP1193Accounts>;
59
+ request(args: ERIP1193SwitchChainRequest): Promise<EIP1193SwitchChainError | null>;
60
+ request(args: ERIP1193AddChainRequest): Promise<EIP1193AddChainError | null>;
61
+ request(args: EIP1193SubscribeRequest): Promise<string>;
62
+ request(args: EIP1193UnsubscribeRequest): Promise<boolean>;
63
+ request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
64
+ protected abstract _request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
65
+ }
66
+
67
+ declare class TransactionHashTracker extends BaseProvider {
68
+ transactionHashes: `0x${string}`[];
69
+ constructor(provider: EIP1193GenericRequestProvider);
70
+ protected _request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
71
+ }
72
+
15
73
  type Libraries = {
16
74
  readonly [libraryName: string]: EIP1193Account;
17
75
  };
@@ -216,6 +274,8 @@ type Config = {
216
274
  deployments?: string;
217
275
  saveDeployments?: boolean;
218
276
  tags?: string[];
277
+ askBeforeProceeding?: boolean;
278
+ reportGasUse?: boolean;
219
279
  logLevel?: number;
220
280
  gasPricing?: {};
221
281
  };
@@ -229,6 +289,8 @@ type ResolvedConfig = Config & {
229
289
  fork?: boolean;
230
290
  };
231
291
  saveDeployments?: boolean;
292
+ askBeforeProceeding?: boolean;
293
+ reportGasUse?: boolean;
232
294
  };
233
295
  interface Environment<Artifacts extends UnknownArtifacts = UnknownArtifacts, NamedAccounts extends UnresolvedUnknownNamedAccounts = UnresolvedUnknownNamedAccounts, Deployments extends UnknownDeployments = UnknownDeployments> {
234
296
  config: ResolvedConfig;
@@ -238,7 +300,7 @@ interface Environment<Artifacts extends UnknownArtifacts = UnknownArtifacts, Nam
238
300
  tags: {
239
301
  [tag: string]: boolean;
240
302
  };
241
- provider: EIP1193ProviderWithoutEvents;
303
+ provider: TransactionHashTracker;
242
304
  };
243
305
  deployments: Deployments;
244
306
  accounts: ResolvedNamedAccounts<NamedAccounts>;
@@ -325,6 +387,8 @@ type ConfigOptions = {
325
387
  provider?: EIP1193ProviderWithoutEvents | EIP1193GenericRequestProvider;
326
388
  ignoreMissingRPC?: boolean;
327
389
  saveDeployments?: boolean;
390
+ askBeforeProceeding?: boolean;
391
+ reportGasUse?: boolean;
328
392
  };
329
393
  declare function readConfig(options: ConfigOptions): Config;
330
394
  declare function readAndResolveConfig(options: ConfigOptions): ResolvedConfig;
package/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { EIP1193Account, EIP1193DATA, EIP1193QUANTITY, EIP1193SignerProvider, EIP1193ProviderWithoutEvents, EIP1193WalletProvider, EIP1193TransactionReceipt, EIP1193GenericRequestProvider } from 'eip-1193';
1
+ import { EIP1193ProviderWithoutEvents, EIP1193GenericRequestProvider, EIP1193Web3ClientVersionRequest, EIP1193Web3SHARequest, EIP1193NetVersionRequest, EIP1193NetListeningRequest, EIP1193NetPeerCountRequest, EIP1193ProtocolVersionRequest, EIP1193SyncingRequest, EIP1193SyncingStatus, EIP1193CoinbaseRequest, EIP1193GasPriceRequest, EIP1193AccountsRequest, EIP1193Accounts, EIP1193BlockNumberRequest, EIP1193GetBalanceRequest, EIP1193GetStorageAtRequest, EIP1193GetTransactionCountRequest, EIP1193GetTransactionCountByHashRequest, EIP1193GetTransactionCountByNumberRequest, EIP1193GetUncleCountByBlockHashRequest, EIP1193GetUncleCountByBlockNumberRequest, EIP1193GetCodeRequest, EIP1193LegacySignRequest, EIP1193SignTransactionRequest, EIP1193SendTransactionRequest, EIP1193SendRawTransactionRequest, EIP1193CallRequest, EIP1193EstimateGasRequest, EIP1193GetBlockByHashRequest, EIP1193Block, EIP1193BlockWithTransactions, EIP1193GetBlockByNumberRequest, EIP1193GetTransactionByHashRequest, EIP1193Transaction, EIP1193GetTransactionByBlockHashAndIndexRequest, EIP1193GetTransactionByBlockNumberAndIndexRequest, EIP1193GetTransactionReceiptRequest, EIP1193TransactionReceipt, EIP1193GetUncleByBlockHashAndIndexRequest, EIP1193GetUncleByBlockNumberAndIndexRequest, EIP1193GetLogsRequest, EIP1193Log, EIP1193PersonalSignRequest, EIP1193PTypedSignv4Request, EIP1193PTypedSignRequest, EIP1193ChainIdRequest, EIP1193RequestAccountsRequest, ERIP1193SwitchChainRequest, EIP1193SwitchChainError, ERIP1193AddChainRequest, EIP1193AddChainError, EIP1193SubscribeRequest, EIP1193UnsubscribeRequest, EIP1193GenericRequest, EIP1193Account, EIP1193DATA, EIP1193QUANTITY, EIP1193SignerProvider, EIP1193WalletProvider } from 'eip-1193';
2
2
  import * as abitype from 'abitype';
3
3
  import { Abi, Narrow } from 'abitype';
4
4
  export { Abi, AbiConstructor, AbiError, AbiEvent, AbiFallback, AbiFunction, AbiReceive } from 'abitype';
@@ -12,6 +12,64 @@ type ProgressIndicator = {
12
12
  fail(msg?: string): ProgressIndicator;
13
13
  };
14
14
 
15
+ declare abstract class BaseProvider implements EIP1193ProviderWithoutEvents {
16
+ protected provider: EIP1193GenericRequestProvider;
17
+ constructor(provider: EIP1193GenericRequestProvider);
18
+ request(args: EIP1193Web3ClientVersionRequest): Promise<string>;
19
+ request(args: EIP1193Web3SHARequest): Promise<`0x${string}`>;
20
+ request(args: EIP1193NetVersionRequest): Promise<`0x${string}`>;
21
+ request(args: EIP1193NetListeningRequest): Promise<boolean>;
22
+ request(args: EIP1193NetPeerCountRequest): Promise<`0x${string}`>;
23
+ request(args: EIP1193ProtocolVersionRequest): Promise<string>;
24
+ request(args: EIP1193SyncingRequest): Promise<false | EIP1193SyncingStatus>;
25
+ request(args: EIP1193CoinbaseRequest): Promise<`0x${string}`>;
26
+ request(args: EIP1193GasPriceRequest): Promise<`0x${string}`>;
27
+ request(args: EIP1193AccountsRequest): Promise<EIP1193Accounts>;
28
+ request(args: EIP1193BlockNumberRequest): Promise<`0x${string}`>;
29
+ request(args: EIP1193GetBalanceRequest): Promise<`0x${string}`>;
30
+ request(args: EIP1193GetStorageAtRequest): Promise<`0x${string}`>;
31
+ request(args: EIP1193GetTransactionCountRequest): Promise<`0x${string}`>;
32
+ request(args: EIP1193GetTransactionCountByHashRequest): Promise<`0x${string}`>;
33
+ request(args: EIP1193GetTransactionCountByNumberRequest): Promise<`0x${string}`>;
34
+ request(args: EIP1193GetUncleCountByBlockHashRequest): Promise<`0x${string}`>;
35
+ request(args: EIP1193GetUncleCountByBlockNumberRequest): Promise<`0x${string}`>;
36
+ request(args: EIP1193GetCodeRequest): Promise<`0x${string}`>;
37
+ request(args: EIP1193LegacySignRequest): Promise<`0x${string}`>;
38
+ request(args: EIP1193SignTransactionRequest): Promise<`0x${string}`>;
39
+ request(args: EIP1193SendTransactionRequest): Promise<`0x${string}`>;
40
+ request(args: EIP1193SendRawTransactionRequest): Promise<`0x${string}`>;
41
+ request(args: EIP1193CallRequest): Promise<`0x${string}`>;
42
+ request(args: EIP1193EstimateGasRequest): Promise<`0x${string}`>;
43
+ request(args: EIP1193GetBlockByHashRequest<false>): Promise<EIP1193Block | null>;
44
+ request(args: EIP1193GetBlockByHashRequest<true>): Promise<EIP1193BlockWithTransactions | null>;
45
+ request(args: EIP1193GetBlockByNumberRequest<false>): Promise<EIP1193Block | null>;
46
+ request(args: EIP1193GetBlockByNumberRequest<true>): Promise<EIP1193BlockWithTransactions | null>;
47
+ request(args: EIP1193GetTransactionByHashRequest): Promise<EIP1193Transaction | null>;
48
+ request(args: EIP1193GetTransactionByBlockHashAndIndexRequest): Promise<EIP1193Transaction | null>;
49
+ request(args: EIP1193GetTransactionByBlockNumberAndIndexRequest): Promise<EIP1193Transaction | null>;
50
+ request(args: EIP1193GetTransactionReceiptRequest): Promise<EIP1193TransactionReceipt | null>;
51
+ request(args: EIP1193GetUncleByBlockHashAndIndexRequest): Promise<EIP1193Block | null>;
52
+ request(args: EIP1193GetUncleByBlockNumberAndIndexRequest): Promise<EIP1193Block | null>;
53
+ request(args: EIP1193GetLogsRequest): Promise<EIP1193Log[]>;
54
+ request(args: EIP1193PersonalSignRequest): Promise<`0x${string}`>;
55
+ request(args: EIP1193PTypedSignv4Request): Promise<`0x${string}`>;
56
+ request(args: EIP1193PTypedSignRequest): Promise<`0x${string}`>;
57
+ request(args: EIP1193ChainIdRequest): Promise<`0x${string}`>;
58
+ request(args: EIP1193RequestAccountsRequest): Promise<EIP1193Accounts>;
59
+ request(args: ERIP1193SwitchChainRequest): Promise<EIP1193SwitchChainError | null>;
60
+ request(args: ERIP1193AddChainRequest): Promise<EIP1193AddChainError | null>;
61
+ request(args: EIP1193SubscribeRequest): Promise<string>;
62
+ request(args: EIP1193UnsubscribeRequest): Promise<boolean>;
63
+ request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
64
+ protected abstract _request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
65
+ }
66
+
67
+ declare class TransactionHashTracker extends BaseProvider {
68
+ transactionHashes: `0x${string}`[];
69
+ constructor(provider: EIP1193GenericRequestProvider);
70
+ protected _request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
71
+ }
72
+
15
73
  type Libraries = {
16
74
  readonly [libraryName: string]: EIP1193Account;
17
75
  };
@@ -216,6 +274,8 @@ type Config = {
216
274
  deployments?: string;
217
275
  saveDeployments?: boolean;
218
276
  tags?: string[];
277
+ askBeforeProceeding?: boolean;
278
+ reportGasUse?: boolean;
219
279
  logLevel?: number;
220
280
  gasPricing?: {};
221
281
  };
@@ -229,6 +289,8 @@ type ResolvedConfig = Config & {
229
289
  fork?: boolean;
230
290
  };
231
291
  saveDeployments?: boolean;
292
+ askBeforeProceeding?: boolean;
293
+ reportGasUse?: boolean;
232
294
  };
233
295
  interface Environment<Artifacts extends UnknownArtifacts = UnknownArtifacts, NamedAccounts extends UnresolvedUnknownNamedAccounts = UnresolvedUnknownNamedAccounts, Deployments extends UnknownDeployments = UnknownDeployments> {
234
296
  config: ResolvedConfig;
@@ -238,7 +300,7 @@ interface Environment<Artifacts extends UnknownArtifacts = UnknownArtifacts, Nam
238
300
  tags: {
239
301
  [tag: string]: boolean;
240
302
  };
241
- provider: EIP1193ProviderWithoutEvents;
303
+ provider: TransactionHashTracker;
242
304
  };
243
305
  deployments: Deployments;
244
306
  accounts: ResolvedNamedAccounts<NamedAccounts>;
@@ -325,6 +387,8 @@ type ConfigOptions = {
325
387
  provider?: EIP1193ProviderWithoutEvents | EIP1193GenericRequestProvider;
326
388
  ignoreMissingRPC?: boolean;
327
389
  saveDeployments?: boolean;
390
+ askBeforeProceeding?: boolean;
391
+ reportGasUse?: boolean;
328
392
  };
329
393
  declare function readConfig(options: ConfigOptions): Config;
330
394
  declare function readAndResolveConfig(options: ConfigOptions): ResolvedConfig;
package/dist/index.js CHANGED
@@ -12,7 +12,7 @@ import {
12
12
  readAndResolveConfig,
13
13
  readConfig,
14
14
  resolveConfig
15
- } from "./chunk-4RQLWJEN.js";
15
+ } from "./chunk-5GXGLCHC.js";
16
16
  export {
17
17
  chainById,
18
18
  execute,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "rocketh",
3
- "version": "0.10.0",
3
+ "version": "0.10.2",
4
4
  "description": "deploy smart contract on ethereum-compatible networks",
5
5
  "publishConfig": {
6
6
  "access": "public"
@@ -15,8 +15,9 @@
15
15
  "devDependencies": {
16
16
  "@types/figlet": "^1.5.8",
17
17
  "@types/node": "^20.11.19",
18
+ "@types/prompts": "^2.4.9",
18
19
  "abitype": "^1.0.0",
19
- "eip-1193": "^0.4.7",
20
+ "eip-1193": "^0.5.0",
20
21
  "ipfs-gateway-emulator": "4.2.1-ipfs.2",
21
22
  "rimraf": "^5.0.5",
22
23
  "tsup": "^8.0.2",
@@ -33,6 +34,7 @@
33
34
  "ldenv": "^0.3.9",
34
35
  "named-logs": "^0.2.2",
35
36
  "named-logs-console": "^0.3.0",
37
+ "prompts": "^2.4.2",
36
38
  "viem": "^2.7.11"
37
39
  },
38
40
  "scripts": {
package/src/cli.ts CHANGED
@@ -21,4 +21,4 @@ program
21
21
 
22
22
  const options = program.opts();
23
23
 
24
- loadAndExecuteDeployments({...(options as ConfigOptions), logLevel: 1});
24
+ loadAndExecuteDeployments({...(options as ConfigOptions), logLevel: 1, askBeforeProceeding: true, reportGasUse: true});
@@ -37,6 +37,7 @@ import {ProgressIndicator, log, spin} from '../internal/logging';
37
37
  import {PendingExecution} from './types';
38
38
  import {getChain} from './utils/chains';
39
39
  import {mergeArtifacts} from './utils/artifacts';
40
+ import {TransactionHashTracker} from './providers/TransactionHashTracker';
40
41
 
41
42
  type ReceiptResult = {receipt: EIP1193TransactionReceipt; latestBlockNumber: EIP1193QUANTITY};
42
43
 
@@ -84,11 +85,13 @@ export async function createEnvironment<
84
85
  config: ResolvedConfig,
85
86
  providedContext: ProvidedContext<Artifacts, NamedAccounts>
86
87
  ): Promise<{internal: InternalEnvironment; external: Environment<Artifacts, NamedAccounts, Deployments>}> {
87
- const provider =
88
+ const rawProvider =
88
89
  'provider' in config.network
89
90
  ? config.network.provider
90
91
  : (new JSONRPCHTTPProvider(config.network.nodeUrl) as EIP1193ProviderWithoutEvents);
91
92
 
93
+ const provider = new TransactionHashTracker(rawProvider);
94
+
92
95
  const transport = custom(provider);
93
96
  const viemClient = createPublicClient({transport});
94
97
 
@@ -0,0 +1,114 @@
1
+ import {
2
+ EIP1193Accounts,
3
+ EIP1193AccountsRequest,
4
+ EIP1193AddChainError,
5
+ EIP1193Block,
6
+ EIP1193BlockNumberRequest,
7
+ EIP1193BlockWithTransactions,
8
+ EIP1193CallRequest,
9
+ EIP1193ChainIdRequest,
10
+ EIP1193CoinbaseRequest,
11
+ EIP1193EstimateGasRequest,
12
+ EIP1193GasPriceRequest,
13
+ EIP1193GenericRequest,
14
+ EIP1193GenericRequestProvider,
15
+ EIP1193GetBalanceRequest,
16
+ EIP1193GetBlockByHashRequest,
17
+ EIP1193GetBlockByNumberRequest,
18
+ EIP1193GetCodeRequest,
19
+ EIP1193GetLogsRequest,
20
+ EIP1193GetStorageAtRequest,
21
+ EIP1193GetTransactionByBlockHashAndIndexRequest,
22
+ EIP1193GetTransactionByBlockNumberAndIndexRequest,
23
+ EIP1193GetTransactionByHashRequest,
24
+ EIP1193GetTransactionCountByHashRequest,
25
+ EIP1193GetTransactionCountByNumberRequest,
26
+ EIP1193GetTransactionCountRequest,
27
+ EIP1193GetTransactionReceiptRequest,
28
+ EIP1193GetUncleByBlockHashAndIndexRequest,
29
+ EIP1193GetUncleByBlockNumberAndIndexRequest,
30
+ EIP1193GetUncleCountByBlockHashRequest,
31
+ EIP1193GetUncleCountByBlockNumberRequest,
32
+ EIP1193LegacySignRequest,
33
+ EIP1193Log,
34
+ EIP1193NetListeningRequest,
35
+ EIP1193NetPeerCountRequest,
36
+ EIP1193NetVersionRequest,
37
+ EIP1193PTypedSignRequest,
38
+ EIP1193PTypedSignv4Request,
39
+ EIP1193PersonalSignRequest,
40
+ EIP1193ProtocolVersionRequest,
41
+ EIP1193ProviderWithoutEvents,
42
+ EIP1193RequestAccountsRequest,
43
+ EIP1193SendRawTransactionRequest,
44
+ EIP1193SendTransactionRequest,
45
+ EIP1193SignTransactionRequest,
46
+ EIP1193SubscribeRequest,
47
+ EIP1193SwitchChainError,
48
+ EIP1193SyncingRequest,
49
+ EIP1193SyncingStatus,
50
+ EIP1193Transaction,
51
+ EIP1193TransactionReceipt,
52
+ EIP1193UnsubscribeRequest,
53
+ EIP1193Web3ClientVersionRequest,
54
+ EIP1193Web3SHARequest,
55
+ ERIP1193AddChainRequest,
56
+ ERIP1193SwitchChainRequest,
57
+ } from 'eip-1193';
58
+
59
+ export abstract class BaseProvider implements EIP1193ProviderWithoutEvents {
60
+ constructor(protected provider: EIP1193GenericRequestProvider) {}
61
+ request(args: EIP1193Web3ClientVersionRequest): Promise<string>;
62
+ request(args: EIP1193Web3SHARequest): Promise<`0x${string}`>;
63
+ request(args: EIP1193NetVersionRequest): Promise<`0x${string}`>;
64
+ request(args: EIP1193NetListeningRequest): Promise<boolean>;
65
+ request(args: EIP1193NetPeerCountRequest): Promise<`0x${string}`>;
66
+ request(args: EIP1193ProtocolVersionRequest): Promise<string>;
67
+ request(args: EIP1193SyncingRequest): Promise<false | EIP1193SyncingStatus>;
68
+ request(args: EIP1193CoinbaseRequest): Promise<`0x${string}`>;
69
+ request(args: EIP1193GasPriceRequest): Promise<`0x${string}`>;
70
+ request(args: EIP1193AccountsRequest): Promise<EIP1193Accounts>;
71
+ request(args: EIP1193BlockNumberRequest): Promise<`0x${string}`>;
72
+ request(args: EIP1193GetBalanceRequest): Promise<`0x${string}`>;
73
+ request(args: EIP1193GetStorageAtRequest): Promise<`0x${string}`>;
74
+ request(args: EIP1193GetTransactionCountRequest): Promise<`0x${string}`>;
75
+ request(args: EIP1193GetTransactionCountByHashRequest): Promise<`0x${string}`>;
76
+ request(args: EIP1193GetTransactionCountByNumberRequest): Promise<`0x${string}`>;
77
+ request(args: EIP1193GetUncleCountByBlockHashRequest): Promise<`0x${string}`>;
78
+ request(args: EIP1193GetUncleCountByBlockNumberRequest): Promise<`0x${string}`>;
79
+ request(args: EIP1193GetCodeRequest): Promise<`0x${string}`>;
80
+ request(args: EIP1193LegacySignRequest): Promise<`0x${string}`>;
81
+ request(args: EIP1193SignTransactionRequest): Promise<`0x${string}`>;
82
+ request(args: EIP1193SendTransactionRequest): Promise<`0x${string}`>;
83
+ request(args: EIP1193SendRawTransactionRequest): Promise<`0x${string}`>;
84
+ request(args: EIP1193CallRequest): Promise<`0x${string}`>;
85
+ request(args: EIP1193EstimateGasRequest): Promise<`0x${string}`>;
86
+ request(args: EIP1193GetBlockByHashRequest<false>): Promise<EIP1193Block | null>;
87
+ request(args: EIP1193GetBlockByHashRequest<true>): Promise<EIP1193BlockWithTransactions | null>;
88
+ request(args: EIP1193GetBlockByNumberRequest<false>): Promise<EIP1193Block | null>;
89
+ request(args: EIP1193GetBlockByNumberRequest<true>): Promise<EIP1193BlockWithTransactions | null>;
90
+ request(args: EIP1193GetTransactionByHashRequest): Promise<EIP1193Transaction | null>;
91
+ request(args: EIP1193GetTransactionByBlockHashAndIndexRequest): Promise<EIP1193Transaction | null>;
92
+ request(args: EIP1193GetTransactionByBlockNumberAndIndexRequest): Promise<EIP1193Transaction | null>;
93
+ request(args: EIP1193GetTransactionReceiptRequest): Promise<EIP1193TransactionReceipt | null>;
94
+ request(args: EIP1193GetUncleByBlockHashAndIndexRequest): Promise<EIP1193Block | null>;
95
+ request(args: EIP1193GetUncleByBlockNumberAndIndexRequest): Promise<EIP1193Block | null>;
96
+ request(args: EIP1193GetLogsRequest): Promise<EIP1193Log[]>;
97
+ request(args: EIP1193PersonalSignRequest): Promise<`0x${string}`>;
98
+ request(args: EIP1193PTypedSignv4Request): Promise<`0x${string}`>;
99
+ request(args: EIP1193PTypedSignRequest): Promise<`0x${string}`>;
100
+ request(args: EIP1193ChainIdRequest): Promise<`0x${string}`>;
101
+ request(args: EIP1193RequestAccountsRequest): Promise<EIP1193Accounts>;
102
+ request(args: ERIP1193SwitchChainRequest): Promise<EIP1193SwitchChainError | null>;
103
+ request(args: ERIP1193AddChainRequest): Promise<EIP1193AddChainError | null>;
104
+ request(args: EIP1193SubscribeRequest): Promise<string>;
105
+ request(args: EIP1193UnsubscribeRequest): Promise<boolean>;
106
+ request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T>;
107
+ request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T> {
108
+ return this._request(args);
109
+ }
110
+
111
+ protected abstract _request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(
112
+ args: V
113
+ ): Promise<T>;
114
+ }
@@ -0,0 +1,18 @@
1
+ import {EIP1193GenericRequest, EIP1193GenericRequestProvider} from 'eip-1193';
2
+ import {BaseProvider} from './BaseProvider';
3
+
4
+ export class TransactionHashTracker extends BaseProvider {
5
+ public transactionHashes: `0x${string}`[] = [];
6
+
7
+ constructor(provider: EIP1193GenericRequestProvider) {
8
+ super(provider);
9
+ }
10
+
11
+ protected async _request<T = unknown, V extends EIP1193GenericRequest = EIP1193GenericRequest>(args: V): Promise<T> {
12
+ const response = await this.provider.request<T>(args);
13
+ if (args.method === 'eth_sendRawTransaction' || args.method === 'eth_sendTransaction') {
14
+ this.transactionHashes.push(response as `0x${string}`);
15
+ }
16
+ return response;
17
+ }
18
+ }
@@ -12,6 +12,7 @@ import {Abi, Narrow, AbiError, AbiEvent, AbiConstructor, AbiFallback, AbiFunctio
12
12
  import type {Address, DeployContractParameters} from 'viem';
13
13
  import type {Chain} from 'viem';
14
14
  import {ProgressIndicator} from '../internal/logging';
15
+ import {TransactionHashTracker} from './providers/TransactionHashTracker';
15
16
 
16
17
  export type {Abi, AbiError, AbiEvent, AbiConstructor, AbiFallback, AbiFunction, AbiReceive};
17
18
  export type Libraries = {readonly [libraryName: string]: EIP1193Account};
@@ -232,6 +233,8 @@ export type Config = {
232
233
  saveDeployments?: boolean;
233
234
 
234
235
  tags?: string[];
236
+ askBeforeProceeding?: boolean;
237
+ reportGasUse?: boolean;
235
238
 
236
239
  logLevel?: number;
237
240
  // TODO
@@ -248,6 +251,8 @@ export type ResolvedConfig = Config & {
248
251
  fork?: boolean;
249
252
  };
250
253
  saveDeployments?: boolean;
254
+ askBeforeProceeding?: boolean;
255
+ reportGasUse?: boolean;
251
256
  };
252
257
 
253
258
  export interface Environment<
@@ -260,7 +265,7 @@ export interface Environment<
260
265
  chain: Chain;
261
266
  name: string;
262
267
  tags: {[tag: string]: boolean};
263
- provider: EIP1193ProviderWithoutEvents;
268
+ provider: TransactionHashTracker;
264
269
  };
265
270
  deployments: Deployments;
266
271
  accounts: ResolvedNamedAccounts<NamedAccounts>;
@@ -14,6 +14,9 @@ import {createEnvironment} from '../environment';
14
14
  import {DeployScriptFunction, DeployScriptModule, ProvidedContext} from './types';
15
15
  import {logger, setLogLevel, spin} from '../internal/logging';
16
16
  import {EIP1193GenericRequestProvider, EIP1193ProviderWithoutEvents} from 'eip-1193';
17
+ import {getRoughGasPriceEstimate} from '../utils/eth';
18
+ import prompts from 'prompts';
19
+ import {formatEther} from 'viem';
17
20
 
18
21
  if (!process.env['ROCKETH_SKIP_ESBUILD']) {
19
22
  require('esbuild-register/dist/node').register();
@@ -49,6 +52,8 @@ export type ConfigOptions = {
49
52
  provider?: EIP1193ProviderWithoutEvents | EIP1193GenericRequestProvider;
50
53
  ignoreMissingRPC?: boolean;
51
54
  saveDeployments?: boolean;
55
+ askBeforeProceeding?: boolean;
56
+ reportGasUse?: boolean;
52
57
  };
53
58
 
54
59
  export function readConfig(options: ConfigOptions): Config {
@@ -127,6 +132,8 @@ export function readConfig(options: ConfigOptions): Config {
127
132
  scripts: options.scripts,
128
133
  tags: typeof options.tags === 'undefined' ? undefined : options.tags.split(','),
129
134
  logLevel: options.logLevel,
135
+ askBeforeProceeding: options.askBeforeProceeding,
136
+ reportGasUse: options.reportGasUse,
130
137
  };
131
138
  } else {
132
139
  return {
@@ -141,6 +148,8 @@ export function readConfig(options: ConfigOptions): Config {
141
148
  scripts: options.scripts,
142
149
  tags: typeof options.tags === 'undefined' ? undefined : options.tags.split(','),
143
150
  logLevel: options.logLevel,
151
+ askBeforeProceeding: options.askBeforeProceeding,
152
+ reportGasUse: options.reportGasUse,
144
153
  };
145
154
  }
146
155
  }
@@ -324,6 +333,30 @@ export async function executeDeployScripts<
324
333
  recurseDependencies(scriptFilePath);
325
334
  }
326
335
 
336
+ if (config.askBeforeProceeding) {
337
+ const gasPriceEstimate = await getRoughGasPriceEstimate(external.network.provider);
338
+ const prompt = await prompts({
339
+ type: 'confirm',
340
+ name: 'proceed',
341
+ message: `gas price is currently in this range:
342
+ slow: ${formatEther(gasPriceEstimate.slow.maxFeePerGas)} (priority: ${formatEther(
343
+ gasPriceEstimate.slow.maxPriorityFeePerGas
344
+ )})
345
+ average: ${formatEther(gasPriceEstimate.average.maxFeePerGas)} (priority: ${formatEther(
346
+ gasPriceEstimate.average.maxPriorityFeePerGas
347
+ )})
348
+ fast: ${formatEther(gasPriceEstimate.fast.maxFeePerGas)} (priority: ${formatEther(
349
+ gasPriceEstimate.fast.maxPriorityFeePerGas
350
+ )})
351
+
352
+ Do you want to proceed (note that gas price can change for each tx)`,
353
+ });
354
+
355
+ if (!prompt.proceed) {
356
+ process.exit();
357
+ }
358
+ }
359
+
327
360
  for (const deployScript of scriptsToRun.concat(scriptsToRunAtTheEnd)) {
328
361
  const filename = path.basename(deployScript.filePath);
329
362
  const relativeFilepath = path.relative('.', deployScript.filePath);
@@ -381,5 +414,21 @@ export async function executeDeployScripts<
381
414
  }
382
415
  }
383
416
 
417
+ if (config.reportGasUse) {
418
+ const provider = external.network.provider;
419
+ const transactionHashes = provider.transactionHashes;
420
+
421
+ let totalGasUsed = 0;
422
+ for (const hash of transactionHashes) {
423
+ const transactionReceipt = await provider.request({method: 'eth_getTransactionReceipt', params: [hash]});
424
+ if (transactionReceipt) {
425
+ const gasUsed = Number(transactionReceipt.gasUsed);
426
+ totalGasUsed += gasUsed;
427
+ }
428
+ }
429
+
430
+ console.log({totalGasUsed});
431
+ }
432
+
384
433
  return external;
385
434
  }
@@ -0,0 +1,103 @@
1
+ import {EIP1193BlockTag, EIP1193ProviderWithoutEvents} from 'eip-1193';
2
+
3
+ function avg(arr: bigint[]) {
4
+ const sum = arr.reduce((a: bigint, v: bigint) => a + v);
5
+ return sum / BigInt(arr.length);
6
+ }
7
+
8
+ type EIP1193FeeHistory = {
9
+ oldestBlock: string;
10
+ reward: `0x${string}`[][];
11
+ baseFeePerGas: string[];
12
+ gasUsedRatio: string[];
13
+ };
14
+
15
+ export type EstimateGasPriceOptions = {
16
+ blockCount: number;
17
+ newestBlock: EIP1193BlockTag;
18
+ rewardPercentiles: number[];
19
+ };
20
+
21
+ export type RoughEstimateGasPriceOptions = {
22
+ blockCount: number;
23
+ newestBlock: EIP1193BlockTag;
24
+ rewardPercentiles: [number, number, number];
25
+ };
26
+
27
+ export type GasPrice = {maxFeePerGas: bigint; maxPriorityFeePerGas: bigint};
28
+ export type EstimateGasPriceResult = GasPrice[];
29
+ export type RoughEstimateGasPriceResult = {slow: GasPrice; average: GasPrice; fast: GasPrice};
30
+
31
+ export async function getGasPriceEstimate(
32
+ provider: EIP1193ProviderWithoutEvents,
33
+ options?: Partial<EstimateGasPriceOptions>
34
+ ): Promise<EstimateGasPriceResult> {
35
+ const defaultOptions: EstimateGasPriceOptions = {
36
+ blockCount: 20,
37
+ newestBlock: 'pending',
38
+ rewardPercentiles: [10, 50, 80],
39
+ };
40
+ const optionsResolved = options ? {...defaultOptions, ...options} : defaultOptions;
41
+
42
+ const historicalBlocks = optionsResolved.blockCount;
43
+
44
+ const rawFeeHistory = await provider.request<EIP1193FeeHistory>({
45
+ method: 'eth_feeHistory',
46
+ params: [`0x${historicalBlocks.toString(16)}`, optionsResolved.newestBlock, optionsResolved.rewardPercentiles],
47
+ });
48
+
49
+ let blockNum = Number(rawFeeHistory.oldestBlock);
50
+ const lastBlock = blockNum + rawFeeHistory.reward.length;
51
+ let index = 0;
52
+ const blocksHistory: {number: number; baseFeePerGas: bigint; gasUsedRatio: number; priorityFeePerGas: bigint[]}[] =
53
+ [];
54
+ while (blockNum < lastBlock) {
55
+ blocksHistory.push({
56
+ number: blockNum,
57
+ baseFeePerGas: BigInt(rawFeeHistory.baseFeePerGas[index]),
58
+ gasUsedRatio: Number(rawFeeHistory.gasUsedRatio[index]),
59
+ priorityFeePerGas: rawFeeHistory.reward[index].map((x) => BigInt(x)),
60
+ });
61
+ blockNum += 1;
62
+ index += 1;
63
+ }
64
+
65
+ const percentilePriorityFeeAverages: bigint[] = [];
66
+ for (let i = 0; i < optionsResolved.rewardPercentiles.length; i++) {
67
+ percentilePriorityFeeAverages.push(avg(blocksHistory.map((b) => b.priorityFeePerGas[i])));
68
+ }
69
+
70
+ const baseFeePerGas = BigInt(rawFeeHistory.baseFeePerGas[rawFeeHistory.baseFeePerGas.length - 1]);
71
+
72
+ const result: EstimateGasPriceResult = [];
73
+ for (let i = 0; i < optionsResolved.rewardPercentiles.length; i++) {
74
+ result.push({
75
+ maxFeePerGas: percentilePriorityFeeAverages[i] + baseFeePerGas,
76
+ maxPriorityFeePerGas: percentilePriorityFeeAverages[i],
77
+ });
78
+ }
79
+ return result;
80
+ }
81
+
82
+ export async function getRoughGasPriceEstimate(
83
+ provider: EIP1193ProviderWithoutEvents,
84
+ options?: Partial<RoughEstimateGasPriceOptions>
85
+ ): Promise<RoughEstimateGasPriceResult> {
86
+ const defaultOptions: EstimateGasPriceOptions = {
87
+ blockCount: 20,
88
+ newestBlock: 'pending',
89
+ rewardPercentiles: [10, 50, 80],
90
+ };
91
+ const optionsResolved = options ? {...defaultOptions, ...options} : defaultOptions;
92
+
93
+ if (optionsResolved.rewardPercentiles.length !== 3) {
94
+ throw new Error(`rough gas estimate require 3 percentile, it defaults to [10,50,80]`);
95
+ }
96
+
97
+ const result = await getGasPriceEstimate(provider, optionsResolved);
98
+ return {
99
+ slow: result[0],
100
+ average: result[1],
101
+ fast: result[2],
102
+ };
103
+ }