From 59c705fa43d324407956e68fbec0da76400b8f06 Mon Sep 17 00:00:00 2001 From: trantorian <114066155+Trantorian1@users.noreply.github.com> Date: Mon, 20 Jan 2025 09:15:36 +0100 Subject: [PATCH 1/3] fix(l1_receipt): trimmed hash --- crates/madara/primitives/receipt/src/to_starknet_types.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/crates/madara/primitives/receipt/src/to_starknet_types.rs b/crates/madara/primitives/receipt/src/to_starknet_types.rs index caf980a76..a5cd9f512 100644 --- a/crates/madara/primitives/receipt/src/to_starknet_types.rs +++ b/crates/madara/primitives/receipt/src/to_starknet_types.rs @@ -59,7 +59,9 @@ impl L1HandlerTransactionReceipt { finality_status: starknet_types_rpc::TxnFinalityStatus, ) -> starknet_types_rpc::L1HandlerTxnReceipt { starknet_types_rpc::L1HandlerTxnReceipt:: { - message_hash: self.message_hash.to_string(), + // We have to manually convert the H256 bytes to a hex hash as the + // impl of Display for H256 skips the middle bytes. + message_hash: self.message_hash.as_fixed_bytes().into_iter().map(|b| format!("{b:02x}")).collect(), common_receipt_properties: starknet_types_rpc::CommonReceiptProperties { actual_fee: self.actual_fee.into(), events: self.events.into_iter().map(starknet_types_rpc::Event::from).collect(), From 17568a93d831128d922904874f8f1f721c094b9c Mon Sep 17 00:00:00 2001 From: trantorian <114066155+Trantorian1@users.noreply.github.com> Date: Mon, 20 Jan 2025 09:28:08 +0100 Subject: [PATCH 2/3] fix(clippy) --- .../primitives/receipt/src/to_starknet_types.rs | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/crates/madara/primitives/receipt/src/to_starknet_types.rs b/crates/madara/primitives/receipt/src/to_starknet_types.rs index a5cd9f512..3fabc0dfc 100644 --- a/crates/madara/primitives/receipt/src/to_starknet_types.rs +++ b/crates/madara/primitives/receipt/src/to_starknet_types.rs @@ -58,10 +58,20 @@ impl L1HandlerTransactionReceipt { self, finality_status: starknet_types_rpc::TxnFinalityStatus, ) -> starknet_types_rpc::L1HandlerTxnReceipt { + use std::fmt::Write; + + // 32 bytes x 2 (1 hex char = 4 bits) + 2 (for 0x) + let mut acc = String::with_capacity(68); + acc.push_str("0x"); + let message_hash = self.message_hash.as_fixed_bytes().iter().fold(acc, |mut acc, b| { + write!(&mut acc, "{b:02x}").expect("Pre-allocated"); + acc + }); + starknet_types_rpc::L1HandlerTxnReceipt:: { // We have to manually convert the H256 bytes to a hex hash as the // impl of Display for H256 skips the middle bytes. - message_hash: self.message_hash.as_fixed_bytes().into_iter().map(|b| format!("{b:02x}")).collect(), + message_hash, common_receipt_properties: starknet_types_rpc::CommonReceiptProperties { actual_fee: self.actual_fee.into(), events: self.events.into_iter().map(starknet_types_rpc::Event::from).collect(), From 4c8d4790be102a332dffad4a657ddc4256628672 Mon Sep 17 00:00:00 2001 From: trantorian <114066155+Trantorian1@users.noreply.github.com> Date: Tue, 21 Jan 2025 10:14:05 +0100 Subject: [PATCH 3/3] fix(comments) --- .../receipt/src/to_starknet_types.rs | 62 +++++++++++++++---- 1 file changed, 51 insertions(+), 11 deletions(-) diff --git a/crates/madara/primitives/receipt/src/to_starknet_types.rs b/crates/madara/primitives/receipt/src/to_starknet_types.rs index 3fabc0dfc..503c66aac 100644 --- a/crates/madara/primitives/receipt/src/to_starknet_types.rs +++ b/crates/madara/primitives/receipt/src/to_starknet_types.rs @@ -1,3 +1,4 @@ +use primitive_types::H256; use starknet_types_core::felt::Felt; use crate::{ @@ -58,20 +59,10 @@ impl L1HandlerTransactionReceipt { self, finality_status: starknet_types_rpc::TxnFinalityStatus, ) -> starknet_types_rpc::L1HandlerTxnReceipt { - use std::fmt::Write; - - // 32 bytes x 2 (1 hex char = 4 bits) + 2 (for 0x) - let mut acc = String::with_capacity(68); - acc.push_str("0x"); - let message_hash = self.message_hash.as_fixed_bytes().iter().fold(acc, |mut acc, b| { - write!(&mut acc, "{b:02x}").expect("Pre-allocated"); - acc - }); - starknet_types_rpc::L1HandlerTxnReceipt:: { // We have to manually convert the H256 bytes to a hex hash as the // impl of Display for H256 skips the middle bytes. - message_hash, + message_hash: hash_as_string(self.message_hash), common_receipt_properties: starknet_types_rpc::CommonReceiptProperties { actual_fee: self.actual_fee.into(), events: self.events.into_iter().map(starknet_types_rpc::Event::from).collect(), @@ -85,6 +76,23 @@ impl L1HandlerTransactionReceipt { } } +/// Gets the **full** string hex representation of an [H256]. +/// +/// This is necessary as the default implementation of [ToString] for [H256] +/// will keep only the first and last 2 bytes, eliding the rest with '...'. +fn hash_as_string(message_hash: H256) -> String { + use std::fmt::Write; + + // 32 bytes x 2 (1 hex char = 4 bits) + 2 (for 0x) + let mut acc = String::with_capacity(68); + acc.push_str("0x"); + + message_hash.as_fixed_bytes().iter().fold(acc, |mut acc, b| { + write!(&mut acc, "{b:02x}").expect("Pre-allocated"); + acc + }) +} + impl DeclareTransactionReceipt { pub fn to_starknet_types( self, @@ -213,3 +221,35 @@ impl From for starknet_types_rpc::ExecutionStatus { } } } + +#[cfg(test)] +mod test { + use primitive_types::H256; + + use crate::{to_starknet_types::hash_as_string, L1HandlerTransactionReceipt}; + + #[test] + fn test_hash_as_string() { + let mut hash = String::with_capacity(68); + hash.push_str("0x"); + hash.push_str(&"f".repeat(64)); + assert_eq!(hash_as_string(H256::from_slice(&[u8::MAX; 32])), hash); + } + + /// The default implementation of [ToString] for [H256] will keep only the + /// first and last 2 bytes, eliding the rest with '...'. This test makes + /// sure this is not the case and we are using [hash_as_string] instead. + #[test] + fn test_l1_tx_receipt_full_hash() { + let l1_transaction_receipt = + L1HandlerTransactionReceipt { message_hash: H256::from_slice(&[u8::MAX; 32]), ..Default::default() }; + let message_hash = + l1_transaction_receipt.to_starknet_types(starknet_types_rpc::TxnFinalityStatus::L1).message_hash; + + let mut hash = String::with_capacity(68); + hash.push_str("0x"); + hash.push_str(&"f".repeat(64)); + assert_eq!(message_hash, hash); + assert!(!message_hash.contains(".")); + } +}