@@ -77,10 +77,12 @@ def __init_subclass__(cls) -> None:
7777
7878 def post_request (
7979 self ,
80+ * ,
8081 method : str ,
81- * params : Any ,
82+ params : Any | None = None ,
8283 extra_headers : Dict | None = None ,
8384 request_id : int | str | None = None ,
85+ timeout : int | None = None ,
8486 ) -> Any :
8587 """Send JSON-RPC POST request to the client RPC server at port defined in the url."""
8688 if extra_headers is None :
@@ -90,7 +92,8 @@ def post_request(
9092 next_request_id_counter = next (self .request_id_counter )
9193 if request_id is None :
9294 request_id = next_request_id_counter
93- payload = {
95+
96+ json = {
9497 "jsonrpc" : "2.0" ,
9598 "method" : f"{ self .namespace } _{ method } " ,
9699 "params" : params ,
@@ -101,7 +104,9 @@ def post_request(
101104 }
102105 headers = base_header | self .extra_headers | extra_headers
103106
104- response = requests .post (self .url , json = payload , headers = headers )
107+ print (f"Sending RPC request to { self .url } , timeout is set to { timeout } ..." )
108+ # WHY IS TIMEOUT ALWAYS NONE IT SHOULD HAVE RECEIVED AN ACTUAL VALUE
109+ response = requests .post (self .url , json = json , headers = headers , timeout = timeout )
105110 response .raise_for_status ()
106111 response_json = response .json ()
107112
@@ -139,53 +144,79 @@ def __init__(
139144 )
140145 self .transaction_wait_timeout = transaction_wait_timeout
141146
142- def config (self ):
147+ def config (self , timeout : int | None = None ):
143148 """`eth_config`: Returns information about a fork configuration of the client."""
144149 try :
145- response = self .post_request ("config" )
150+ response = self .post_request (method = "config" , timeout = timeout )
146151 if response is None :
152+ print ("eth_config request: failed to get response" )
147153 return None
148154 return EthConfigResponse .model_validate (
149155 response , context = self .response_validation_context
150156 )
151157 except ValidationError as e :
152158 pprint (e .errors ())
153159 raise e
160+ except Exception as e :
161+ print (f"exception occurred when sending JSON-RPC request: { e } " )
162+ raise e
154163
155164 def chain_id (self ) -> int :
156165 """`eth_chainId`: Returns the current chain id."""
157- return int (self .post_request ("chainId" ), 16 )
166+ response = self .post_request (method = "chainId" )
167+
168+ return int (response , 16 )
158169
159170 def get_block_by_number (self , block_number : BlockNumberType = "latest" , full_txs : bool = True ):
160171 """`eth_getBlockByNumber`: Returns information about a block by block number."""
161172 block = hex (block_number ) if isinstance (block_number , int ) else block_number
162- return self .post_request ("getBlockByNumber" , block , full_txs )
173+ params = [block , full_txs ]
174+ response = self .post_request (method = "getBlockByNumber" , params = params )
175+
176+ return response
163177
164178 def get_block_by_hash (self , block_hash : Hash , full_txs : bool = True ):
165179 """`eth_getBlockByHash`: Returns information about a block by hash."""
166- return self .post_request ("getBlockByHash" , f"{ block_hash } " , full_txs )
180+ params = [f"{ block_hash } " , full_txs ]
181+ response = self .post_request (method = "getBlockByHash" , params = params )
182+
183+ return response
167184
168185 def get_balance (self , address : Address , block_number : BlockNumberType = "latest" ) -> int :
169186 """`eth_getBalance`: Returns the balance of the account of given address."""
170187 block = hex (block_number ) if isinstance (block_number , int ) else block_number
171- return int (self .post_request ("getBalance" , f"{ address } " , block ), 16 )
188+ params = [f"{ address } " , block ]
189+
190+ response = self .post_request (method = "getBalance" , params = params )
191+
192+ return int (response , 16 )
172193
173194 def get_code (self , address : Address , block_number : BlockNumberType = "latest" ) -> Bytes :
174195 """`eth_getCode`: Returns code at a given address."""
175196 block = hex (block_number ) if isinstance (block_number , int ) else block_number
176- return Bytes (self .post_request ("getCode" , f"{ address } " , block ))
197+ params = [f"{ address } " , block ]
198+
199+ response = self .post_request (method = "getCode" , params = params )
200+
201+ return Bytes (response )
177202
178203 def get_transaction_count (
179204 self , address : Address , block_number : BlockNumberType = "latest"
180205 ) -> int :
181206 """`eth_getTransactionCount`: Returns the number of transactions sent from an address."""
182207 block = hex (block_number ) if isinstance (block_number , int ) else block_number
183- return int (self .post_request ("getTransactionCount" , f"{ address } " , block ), 16 )
208+ params = [f"{ address } " , block ]
209+
210+ response = self .post_request (method = "getTransactionCount" , params = params )
211+
212+ return int (response , 16 )
184213
185214 def get_transaction_by_hash (self , transaction_hash : Hash ) -> TransactionByHashResponse | None :
186215 """`eth_getTransactionByHash`: Returns transaction details."""
187216 try :
188- response = self .post_request ("getTransactionByHash" , f"{ transaction_hash } " )
217+ response = self .post_request (
218+ method = "getTransactionByHash" , params = f"{ transaction_hash } "
219+ )
189220 if response is None :
190221 return None
191222 return TransactionByHashResponse .model_validate (
@@ -200,37 +231,45 @@ def get_storage_at(
200231 ) -> Hash :
201232 """`eth_getStorageAt`: Returns the value from a storage position at a given address."""
202233 block = hex (block_number ) if isinstance (block_number , int ) else block_number
203- return Hash (self .post_request ("getStorageAt" , f"{ address } " , f"{ position } " , block ))
234+ params = [f"{ address } " , f"{ position } " , block ]
235+
236+ response = self .post_request (method = "getStorageAt" , params = params )
237+ return Hash (response )
204238
205239 def gas_price (self ) -> int :
206240 """`eth_gasPrice`: Returns the number of transactions sent from an address."""
207- return int (self .post_request ("gasPrice" ), 16 )
241+ response = self .post_request (method = "gasPrice" )
242+
243+ return int (response , 16 )
208244
209245 def send_raw_transaction (
210246 self , transaction_rlp : Bytes , request_id : int | str | None = None
211247 ) -> Hash :
212248 """`eth_sendRawTransaction`: Send a transaction to the client."""
213249 try :
214- result_hash = Hash (
215- self . post_request (
216- "sendRawTransaction" , f"{ transaction_rlp .hex ()} " , request_id = request_id
217- ),
250+ response = self . post_request (
251+ method = "sendRawTransaction" ,
252+ params = f"{ transaction_rlp .hex ()} " ,
253+ request_id = request_id , # noqa: E501
218254 )
255+
256+ result_hash = Hash (response )
219257 assert result_hash is not None
220258 return result_hash
221259 except Exception as e :
222260 raise SendTransactionExceptionError (str (e ), tx_rlp = transaction_rlp ) from e
223261
224262 def send_transaction (self , transaction : Transaction ) -> Hash :
225263 """`eth_sendRawTransaction`: Send a transaction to the client."""
264+ # TODO: is this a copypaste error from above?
226265 try :
227- result_hash = Hash (
228- self .post_request (
229- "sendRawTransaction" ,
230- f"{ transaction .rlp ().hex ()} " ,
231- request_id = transaction .metadata_string (),
232- )
266+ response = self .post_request (
267+ method = "sendRawTransaction" ,
268+ params = f"{ transaction .rlp ().hex ()} " ,
269+ request_id = transaction .metadata_string (), # noqa: E501
233270 )
271+
272+ result_hash = Hash (response )
234273 assert result_hash == transaction .hash
235274 assert result_hash is not None
236275 return transaction .hash
@@ -322,7 +361,8 @@ class DebugRPC(EthRPC):
322361
323362 def trace_call (self , tr : dict [str , str ], block_number : str ):
324363 """`debug_traceCall`: Returns pre state required for transaction."""
325- return self .post_request ("traceCall" , tr , block_number , {"tracer" : "prestateTracer" })
364+ params = [tr , block_number , {"tracer" : "prestateTracer" }]
365+ return self .post_request (method = "traceCall" , params = params )
326366
327367
328368class EngineRPC (BaseRPC ):
@@ -333,10 +373,12 @@ class EngineRPC(BaseRPC):
333373
334374 def post_request (
335375 self ,
376+ * ,
336377 method : str ,
337- * params : Any ,
378+ params : Any | None = None ,
338379 extra_headers : Dict | None = None ,
339380 request_id : int | str | None = None ,
381+ timeout : int | None = None ,
340382 ) -> Any :
341383 """Send JSON-RPC POST request to the client RPC server at port defined in the url."""
342384 if extra_headers is None :
@@ -349,14 +391,22 @@ def post_request(
349391 extra_headers = {
350392 "Authorization" : f"Bearer { jwt_token } " ,
351393 } | extra_headers
394+
352395 return super ().post_request (
353- method , * params , extra_headers = extra_headers , request_id = request_id
396+ method = method ,
397+ params = params ,
398+ extra_headers = extra_headers ,
399+ timeout = timeout ,
400+ request_id = request_id ,
354401 )
355402
356403 def new_payload (self , * params : Any , version : int ) -> PayloadStatus :
357404 """`engine_newPayloadVX`: Attempts to execute the given payload on an execution client."""
405+ method = f"newPayloadV{ version } "
406+ params_list = [to_json (param ) for param in params ]
407+
358408 return PayloadStatus .model_validate (
359- self .post_request (f"newPayloadV { version } " , * [ to_json ( param ) for param in params ] ),
409+ self .post_request (method = method , params = params_list ),
360410 context = self .response_validation_context ,
361411 )
362412
@@ -368,11 +418,17 @@ def forkchoice_updated(
368418 version : int ,
369419 ) -> ForkchoiceUpdateResponse :
370420 """`engine_forkchoiceUpdatedVX`: Updates the forkchoice state of the execution client."""
421+ method = f"forkchoiceUpdatedV{ version } "
422+
423+ if payload_attributes is None :
424+ params = [to_json (forkchoice_state )]
425+ else :
426+ params = [to_json (forkchoice_state ), to_json (payload_attributes )]
427+
371428 return ForkchoiceUpdateResponse .model_validate (
372429 self .post_request (
373- f"forkchoiceUpdatedV{ version } " ,
374- to_json (forkchoice_state ),
375- to_json (payload_attributes ) if payload_attributes is not None else None ,
430+ method = method ,
431+ params = params ,
376432 ),
377433 context = self .response_validation_context ,
378434 )
@@ -387,10 +443,12 @@ def get_payload(
387443 `engine_getPayloadVX`: Retrieves a payload that was requested through
388444 `engine_forkchoiceUpdatedVX`.
389445 """
446+ method = f"getPayloadV{ version } "
447+
390448 return GetPayloadResponse .model_validate (
391449 self .post_request (
392- f"getPayloadV { version } " ,
393- f"{ payload_id } " ,
450+ method = method ,
451+ params = f"{ payload_id } " ,
394452 ),
395453 context = self .response_validation_context ,
396454 )
@@ -402,10 +460,13 @@ def get_blobs(
402460 version : int ,
403461 ) -> GetBlobsResponse :
404462 """`engine_getBlobsVX`: Retrieves blobs from an execution layers tx pool."""
463+ method = f"getBlobsV{ version } "
464+ params = [f"{ h } " for h in versioned_hashes ]
465+
405466 return GetBlobsResponse .model_validate (
406467 self .post_request (
407- f"getBlobsV { version } " ,
408- [ f" { h } " for h in versioned_hashes ] ,
468+ method = method ,
469+ params = params ,
409470 ),
410471 context = self .response_validation_context ,
411472 )
@@ -416,7 +477,7 @@ class NetRPC(BaseRPC):
416477
417478 def peer_count (self ) -> int :
418479 """`net_peerCount`: Get the number of peers connected to the client."""
419- response = self .post_request ("peerCount" )
480+ response = self .post_request (method = "peerCount" )
420481 return int (response , 16 ) # hex -> int
421482
422483
@@ -425,4 +486,4 @@ class AdminRPC(BaseRPC):
425486
426487 def add_peer (self , enode : str ) -> bool :
427488 """`admin_addPeer`: Add a peer by enode URL."""
428- return self .post_request ("addPeer" , enode )
489+ return self .post_request (method = "addPeer" , params = enode )
0 commit comments