Skip to content

Commit

Permalink
refactored FtTransfer
Browse files Browse the repository at this point in the history
  • Loading branch information
FroVolod committed Mar 1, 2025
1 parent 98d2034 commit 8c1e589
Show file tree
Hide file tree
Showing 2 changed files with 62 additions and 29 deletions.
17 changes: 5 additions & 12 deletions src/commands/tokens/send_ft/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -80,18 +80,11 @@ pub fn get_prepopulated_transaction(
deposit: &crate::types::near_token::NearToken,
gas: &crate::common::NearGas,
) -> color_eyre::eyre::Result<crate::commands::PrepopulatedTransaction> {
let args_ft_transfer = serde_json::to_vec(&json!({
"receiver_id": receiver_account_id,
"amount": amount_ft.amount().to_string(),
"memo": memo.as_ref().and_then(|s| {
let trimmed = s.trim();
if trimmed.is_empty() {
None
} else {
Some(trimmed.to_string())
}
})
}))?;
let args_ft_transfer = serde_json::to_vec(&crate::types::ft_properties::FtTransfer {
receiver_id: receiver_account_id.clone(),
amount: amount_ft.amount(),
memo: memo.clone(),
})?;

let action_ft_transfer = near_primitives::transaction::Action::FunctionCall(Box::new(
near_primitives::transaction::FunctionCallAction {
Expand Down
74 changes: 57 additions & 17 deletions src/types/ft_properties.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use color_eyre::eyre::{Context, ContextCompat};
use serde::de::{Deserialize, Deserializer};
use serde::ser::{Serialize, Serializer};

use crate::common::CallResultExt;
use crate::common::JsonRpcClientExt;
Expand Down Expand Up @@ -219,6 +220,32 @@ pub fn params_ft_metadata(
Ok(ft_metadata)
}

#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
pub struct FtTransfer {
pub receiver_id: near_primitives::types::AccountId,
#[serde(deserialize_with = "parse_u128_string", serialize_with = "to_string")]
pub amount: u128,
#[serde(skip_serializing_if = "Option::is_none")]
pub memo: Option<String>,
}

fn parse_u128_string<'de, D>(deserializer: D) -> color_eyre::eyre::Result<u128, D::Error>
where
D: Deserializer<'de>,
{
String::deserialize(deserializer)?
.parse::<u128>()
.map_err(serde::de::Error::custom)
}

fn to_string<S, T: ToString>(value: &T, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
let s = value.to_string();
String::serialize(&s, serializer)
}

#[cfg(test)]
mod tests {
use super::*;
Expand Down Expand Up @@ -270,21 +297,34 @@ mod tests {
assert_eq!(ft_transfer_amount.to_string(), "all".to_string());
assert_eq!(ft_transfer_amount, FungibleTokenTransferAmount::MaxAmount);
}
}

#[derive(Debug, Clone, serde::Deserialize)]
pub struct FtTransfer {
pub receiver_id: String,
#[serde(deserialize_with = "parse_u128_string")]
pub amount: u128,
pub memo: Option<String>,
}

fn parse_u128_string<'de, D>(deserializer: D) -> color_eyre::eyre::Result<u128, D::Error>
where
D: Deserializer<'de>,
{
String::deserialize(deserializer)?
.parse::<u128>()
.map_err(serde::de::Error::custom)
#[test]
fn ft_transfer_with_memo_to_vec_u8() {
let ft_transfer = serde_json::to_vec(&crate::types::ft_properties::FtTransfer {
receiver_id: "fro_volod.testnet".parse().unwrap(),
amount: FungibleToken::from_str("0.123456 USDC").unwrap().amount(),
memo: Some("Memo".to_string()),
})
.unwrap();
assert_eq!(
serde_json::from_slice::<serde_json::Value>(&ft_transfer)
.unwrap()
.to_string(),
"{\"amount\":\"123456\",\"memo\":\"Memo\",\"receiver_id\":\"fro_volod.testnet\"}"
);
}
#[test]
fn ft_transfer_without_memo_to_vec_u8() {
let ft_transfer = serde_json::to_vec(&crate::types::ft_properties::FtTransfer {
receiver_id: "fro_volod.testnet".parse().unwrap(),
amount: FungibleToken::from_str("0.123456 USDC").unwrap().amount(),
memo: None,
})
.unwrap();
assert_eq!(
serde_json::from_slice::<serde_json::Value>(&ft_transfer)
.unwrap()
.to_string(),
"{\"amount\":\"123456\",\"receiver_id\":\"fro_volod.testnet\"}"
);
}
}

0 comments on commit 8c1e589

Please sign in to comment.