diff --git a/CHANGELOG.md b/CHANGELOG.md index 7b3bb46d0..8e9d187ef 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +### Changed +- Dry-run result output improvements [1123](https://github.com/paritytech/cargo-contract/pull/1123) + ## [3.0.1] ### Fixed diff --git a/crates/cargo-contract/src/cmd/extrinsics/call.rs b/crates/cargo-contract/src/cmd/extrinsics/call.rs index 2e8bb5dc3..c4de2a244 100644 --- a/crates/cargo-contract/src/cmd/extrinsics/call.rs +++ b/crates/cargo-contract/src/cmd/extrinsics/call.rs @@ -119,13 +119,12 @@ impl CallCommand { match result.result { Ok(ref ret_val) => { let value = transcoder - .decode_return(&self.message, &mut &ret_val.data[..]) + .decode_message_return(&self.message, &mut &ret_val.data[..]) .context(format!( "Failed to decode return value {:?}", &ret_val ))?; let dry_run_result = CallDryRunResult { - result: String::from("Success!"), reverted: ret_val.did_revert(), data: value, gas_consumed: result.gas_consumed, @@ -305,8 +304,6 @@ pub struct CallRequest { /// Result of the contract call #[derive(serde::Serialize)] pub struct CallDryRunResult { - /// Result of a dry run - pub result: String, /// Was the operation reverted pub reverted: bool, pub data: Value, @@ -323,12 +320,11 @@ impl CallDryRunResult { } pub fn print(&self) { - name_value_println!("Result", self.result, DEFAULT_KEY_COL_WIDTH); + name_value_println!("Result", format!("{}", self.data), DEFAULT_KEY_COL_WIDTH); name_value_println!( "Reverted", format!("{:?}", self.reverted), DEFAULT_KEY_COL_WIDTH ); - name_value_println!("Data", format!("{}", self.data), DEFAULT_KEY_COL_WIDTH); } } diff --git a/crates/cargo-contract/src/cmd/extrinsics/instantiate.rs b/crates/cargo-contract/src/cmd/extrinsics/instantiate.rs index 2f0daea20..7dfd68cab 100644 --- a/crates/cargo-contract/src/cmd/extrinsics/instantiate.rs +++ b/crates/cargo-contract/src/cmd/extrinsics/instantiate.rs @@ -45,6 +45,7 @@ use crate::{ }; use anyhow::{ anyhow, + Context, Result, }; use contract_build::{ @@ -52,6 +53,7 @@ use contract_build::{ util::decode_hex, Verbosity, }; +use contract_transcode::Value; use pallet_contracts_primitives::ContractInstantiateResult; @@ -199,11 +201,20 @@ impl Exec { let result = self.instantiate_dry_run().await?; match result.result { Ok(ref ret_val) => { + let value = self + .transcoder + .decode_constructor_return( + &self.args.constructor, + &mut &ret_val.result.data[..], + ) + .context(format!( + "Failed to decode return value {:?}", + &ret_val + ))?; let dry_run_result = InstantiateDryRunResult { - result: String::from("Success!"), + result: value, contract: ret_val.account_id.to_string(), reverted: ret_val.result.did_revert(), - data: ret_val.result.data.clone().into(), gas_consumed: result.gas_consumed, gas_required: result.gas_required, storage_deposit: StorageDeposit::from(&result.storage_deposit), @@ -439,13 +450,12 @@ impl InstantiateResult { /// Result of the contract call #[derive(serde::Serialize)] pub struct InstantiateDryRunResult { - /// Result of a dry run - pub result: String, + /// The decoded result returned from the constructor + pub result: Value, /// contract address pub contract: String, /// Was the operation reverted pub reverted: bool, - pub data: Bytes, pub gas_consumed: Weight, pub gas_required: Weight, /// Storage deposit after the operation @@ -459,14 +469,13 @@ impl InstantiateDryRunResult { } pub fn print(&self) { - name_value_println!("Result", self.result, DEFAULT_KEY_COL_WIDTH); - name_value_println!("Contract", self.contract, DEFAULT_KEY_COL_WIDTH); + name_value_println!("Result", format!("{}", self.result), DEFAULT_KEY_COL_WIDTH); name_value_println!( "Reverted", format!("{:?}", self.reverted), DEFAULT_KEY_COL_WIDTH ); - name_value_println!("Data", format!("{:?}", self.data), DEFAULT_KEY_COL_WIDTH); + name_value_println!("Contract", self.contract, DEFAULT_KEY_COL_WIDTH); name_value_println!( "Gas consumed", self.gas_consumed.to_string(), diff --git a/crates/transcode/src/lib.rs b/crates/transcode/src/lib.rs index 357d084b5..a4287031c 100644 --- a/crates/transcode/src/lib.rs +++ b/crates/transcode/src/lib.rs @@ -349,7 +349,22 @@ impl ContractMessageTranscoder { Ok(Value::Map(map)) } - pub fn decode_return(&self, name: &str, data: &mut &[u8]) -> Result { + pub fn decode_constructor_return( + &self, + name: &str, + data: &mut &[u8], + ) -> Result { + let ctor_spec = self.find_constructor_spec(name).ok_or_else(|| { + anyhow::anyhow!("Failed to find constructor spec with name '{}'", name) + })?; + if let Some(return_ty) = ctor_spec.return_type().opt_type() { + self.decode(return_ty.ty().id, data) + } else { + Ok(Value::Unit) + } + } + + pub fn decode_message_return(&self, name: &str, data: &mut &[u8]) -> Result { let msg_spec = self.find_message_spec(name).ok_or_else(|| { anyhow::anyhow!("Failed to find message spec with name '{}'", name) })?; @@ -674,7 +689,7 @@ mod tests { let encoded = Result::::Ok(true).encode(); let decoded = transcoder - .decode_return("get", &mut &encoded[..]) + .decode_message_return("get", &mut &encoded[..]) .unwrap_or_else(|e| panic!("Error decoding return value {e}")); let expected = Value::Tuple(Tuple::new( @@ -694,7 +709,7 @@ mod tests { let encoded = Result::::Err(LangError::CouldNotReadInput).encode(); let decoded = transcoder - .decode_return("get", &mut &encoded[..]) + .decode_message_return("get", &mut &encoded[..]) .unwrap_or_else(|e| panic!("Error decoding return value {e}")); let expected = Value::Tuple(Tuple::new(