Skip to content

Commit

Permalink
Added initial support for feature #1433
Browse files Browse the repository at this point in the history
  • Loading branch information
adizere committed Oct 7, 2021
1 parent 82dd5b6 commit d101430
Show file tree
Hide file tree
Showing 5 changed files with 77 additions and 5 deletions.
9 changes: 8 additions & 1 deletion relayer-cli/src/commands.rs
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,14 @@ impl Configurable<Config> for CliCmd {
///
/// This can be safely deleted if you don't want to override config
/// settings from command-line options.
fn process_config(&self, config: Config) -> Result<Config, FrameworkError> {
fn process_config(&self, mut config: Config) -> Result<Config, FrameworkError> {
// Alter the memo for all chains to include a suffix with Hermes build details
let web = "https://hermes.informal.systems";
let suffix = format!("{} {} ({})", CliCmd::name(), CliCmd::version(), web);
for ccfg in config.chains.iter_mut() {
ccfg.memo.apply_suffix(&suffix);
}

match self {
CliCmd::Tx(cmd) => cmd.override_config(config),
// CliCmd::Help(cmd) => cmd.override_config(config),
Expand Down
11 changes: 8 additions & 3 deletions relayer/src/chain/cosmos.rs
Original file line number Diff line number Diff line change
Expand Up @@ -229,7 +229,7 @@ impl CosmosSdkChain {

debug!("[{}] default fee: {}", self.id(), PrettyFee(&default_fee));

let (body, body_buf) = tx_body_and_bytes(proto_msgs)?;
let (body, body_buf) = tx_body_and_bytes(proto_msgs, self.tx_memo())?;

let (auth_info, auth_buf) = auth_info_and_bytes(signer_info.clone(), default_fee.clone())?;
let signed_doc = self.signed_doc(body_buf.clone(), auth_buf, account_seq)?;
Expand Down Expand Up @@ -644,6 +644,11 @@ impl CosmosSdkChain {
.trusting_period
.unwrap_or(2 * unbonding_period / 3)
}

/// Returns the preconfigured memo to be used for every submitted transaction
fn tx_memo(&self) -> String {
self.config.memo.clone().into()
}
}

fn empty_event_present(events: &[IbcEvent]) -> bool {
Expand Down Expand Up @@ -1991,11 +1996,11 @@ fn auth_info_and_bytes(signer_info: SignerInfo, fee: Fee) -> Result<(AuthInfo, V
Ok((auth_info, auth_buf))
}

fn tx_body_and_bytes(proto_msgs: Vec<Any>) -> Result<(TxBody, Vec<u8>), Error> {
fn tx_body_and_bytes(proto_msgs: Vec<Any>, memo: String) -> Result<(TxBody, Vec<u8>), Error> {
// Create TxBody
let body = TxBody {
messages: proto_msgs.to_vec(),
memo: "".to_string(),
memo,
timeout_height: 0_u64,
extension_options: Vec::<Any>::new(),
non_critical_extension_options: Vec::<Any>::new(),
Expand Down
1 change: 1 addition & 0 deletions relayer/src/chain/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -438,6 +438,7 @@ pub mod test_utils {
trust_threshold: Default::default(),
packet_filter: PacketFilter::default(),
address_type: AddressType::default(),
memo: Default::default(),
}
}
}
4 changes: 3 additions & 1 deletion relayer/src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ use tendermint_light_client::types::TrustThreshold;
use ibc::ics24_host::identifier::{ChainId, ChannelId, PortId};
use ibc::timestamp::ZERO_DURATION;

use crate::config::types::{MaxMsgNum, MaxTxSize};
use crate::config::types::{MaxMsgNum, MaxTxSize, Memo};
use crate::error::Error;

#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
Expand Down Expand Up @@ -320,6 +320,8 @@ pub struct ChainConfig {
pub clock_drift: Duration,
#[serde(with = "humantime_serde")]
pub trusting_period: Option<Duration>,
#[serde(default)]
pub memo: Memo,

// these two need to be last otherwise we run into `ValueAfterTable` error when serializing to TOML
#[serde(default)]
Expand Down
57 changes: 57 additions & 0 deletions relayer/src/config/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -99,3 +99,60 @@ impl From<MaxTxSize> for usize {
m.0
}
}

#[derive(Debug, Clone)]
pub struct Memo(String);

impl Memo {
const DEFAULT: &'static str = "";
const MAX_LEN: usize = 50;

pub fn apply_suffix(&mut self, suffix: &str) {
// Add a separator if the memo
// is pre-populated with some content already.
if !self.0.is_empty() {
self.0.push_str(" | ");
}

self.0.push_str(suffix);
}
}

impl Default for Memo {
fn default() -> Self {
Self(Self::DEFAULT.to_string())
}
}

impl<'de> Deserialize<'de> for Memo {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
let m = String::deserialize(deserializer)?;

if m.len() > Self::MAX_LEN {
return Err(D::Error::invalid_length(
m.len(),
&format!("a string length of at most {}", Self::MAX_LEN).as_str(),
));
}

Ok(Memo(m))
}
}

impl Serialize for Memo {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
self.0.serialize(serializer)
}
}

impl From<Memo> for String {
fn from(m: Memo) -> Self {
m.0
}
}

0 comments on commit d101430

Please sign in to comment.