Skip to content

Commit

Permalink
fix: remove support for Ada in smart-contracts reserve commands (#389)
Browse files Browse the repository at this point in the history
  • Loading branch information
LGLO authored Jan 15, 2025
1 parent 5159a40 commit e1cd808
Show file tree
Hide file tree
Showing 7 changed files with 80 additions and 97 deletions.
10 changes: 5 additions & 5 deletions toolkit/cli/smart-contracts-commands/src/reserve.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ use partner_chains_cardano_offchain::{
init::init_reserve_management,
},
};
use sidechain_domain::{ScriptHash, TokenId, UtxoId};
use sidechain_domain::{AssetId, ScriptHash, UtxoId};

#[derive(Clone, Debug, clap::Subcommand)]
#[allow(clippy::large_enum_variant)]
Expand Down Expand Up @@ -73,9 +73,9 @@ pub struct CreateReserveCmd {
/// Initial amount of tokens to deposit. They must be present in the payment wallet.
#[arg(long)]
initial_deposit_amount: u64,
/// Use either "Ada" or encoded asset id in form <policy_id_hex>.<asset_name_hex>.
/// Reserve token asset id encoded in form <policy_id_hex>.<asset_name_hex>.
#[arg(long)]
token: TokenId,
token: AssetId,
}

impl CreateReserveCmd {
Expand Down Expand Up @@ -108,9 +108,9 @@ pub struct DepositReserveCmd {
/// Genesis UTXO of the partner-chain.
#[arg(long, short('c'))]
genesis_utxo: UtxoId,
/// Use either "Ada" or encoded asset id in form <policy_id_hex>.<asset_name_hex>.
/// Reserve token asset id encoded in form <policy_id_hex>.<asset_name_hex>.
#[arg(long)]
token: TokenId,
token: AssetId,
/// Amount of tokens to deposit. They must be present in the payment wallet.
#[arg(long)]
amount: u64,
Expand Down
25 changes: 13 additions & 12 deletions toolkit/offchain/src/reserve/create.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
//! * 1 Governance Policy Token (using reference script)
//! 2. The transaction should have two outputs:
//! * Reserve Validator output that:
//! * * has Reward Tokens (or ada)
//! * * has Reward Tokens
//! * * has Plutus Data (in our "versioned format"): `[[[Int(t0), <Encoded Token>], [Bytes(v_function_hash), Int(initial_incentive)], [Int(0)]], Constr(0, []), Int(0)]`,
//! where `<Encoded Token>` is `Constr(0, [Bytes(policy_id), Bytes(asset_name)])`.
//! * Change output that keeps the Governance Token and change of other tokens
Expand Down Expand Up @@ -39,7 +39,7 @@ use ogmios_client::{
use partner_chains_plutus_data::reserve::{
ReserveDatum, ReserveImmutableSettings, ReserveMutableSettings, ReserveStats,
};
use sidechain_domain::{McTxHash, PolicyId, TokenId, UtxoId};
use sidechain_domain::{AssetId, McTxHash, PolicyId, UtxoId};
use std::collections::HashMap;

pub async fn create_reserve_utxo<
Expand Down Expand Up @@ -98,7 +98,7 @@ pub async fn create_reserve_utxo<
pub struct ReserveParameters {
pub initial_incentive: u64,
pub total_accrued_function_script_hash: PolicyId,
pub token: TokenId,
pub token: AssetId,
pub initial_deposit: u64,
}

Expand Down Expand Up @@ -195,15 +195,16 @@ fn reserve_validator_output(
let mut assets = Assets::new();
assets.insert(&empty_asset_name(), &1u64.into());
ma.insert(&scripts.auth_policy.csl_script_hash(), &assets);
if let TokenId::AssetId { policy_id, asset_name } = parameters.token.clone() {
let mut assets = Assets::new();
assets.insert(
&cardano_serialization_lib::AssetName::new(asset_name.0.to_vec())
.expect("AssetName has a valid length"),
&parameters.initial_deposit.into(),
);
ma.insert(&policy_id.0.into(), &assets);
};

let AssetId { policy_id, asset_name } = parameters.token.clone();
let mut assets = Assets::new();
assets.insert(
&cardano_serialization_lib::AssetName::new(asset_name.0.to_vec())
.expect("AssetName has a valid length"),
&parameters.initial_deposit.into(),
);
ma.insert(&policy_id.0.into(), &assets);

let output = amount_builder.with_coin_and_asset(&0u64.into(), &ma).build()?;
let min_ada = MinOutputAdaCalculator::new(
&output,
Expand Down
62 changes: 26 additions & 36 deletions toolkit/offchain/src/reserve/deposit.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,10 @@ use ogmios_client::{
types::OgmiosUtxo,
};
use partner_chains_plutus_data::reserve::{ReserveDatum, ReserveRedeemer};
use sidechain_domain::{McTxHash, TokenId, UtxoId};
use sidechain_domain::{AssetId, McTxHash, UtxoId};

pub struct TokenAmount {
pub token: TokenId,
pub token: AssetId,
pub amount: u64,
}

Expand Down Expand Up @@ -106,7 +106,7 @@ pub async fn deposit_to_reserve<

async fn get_utxo_with_tokens<T: QueryLedgerState>(
scripts: &ReserveScripts,
token_id: &TokenId,
token_id: &AssetId,
ctx: &TransactionContext,
client: &T,
) -> Result<Option<OgmiosUtxo>, anyhow::Error> {
Expand All @@ -131,19 +131,16 @@ fn decode_reserve_datum(datum: ogmios_client::types::Datum) -> Option<ReserveDat
.and_then(|plutus_data| ReserveDatum::try_from(plutus_data).ok())
}

fn get_token_amount(utxo: &OgmiosUtxo, token_id: &TokenId) -> u64 {
match token_id {
TokenId::Ada => utxo.value.lovelace,
TokenId::AssetId { policy_id, asset_name } => utxo
.value
.native_tokens
.get(&policy_id.0)
.and_then(|assets| assets.iter().find(|asset| asset.name == asset_name.0.to_vec()))
.map(|asset| asset.amount)
.unwrap_or(0) // Token can be not found if the reserve was created with the initial deposit of 0 tokens
.try_into()
.expect("Token amount in an UTXO always fits u64"),
}
fn get_token_amount(utxo: &OgmiosUtxo, token: &AssetId) -> u64 {
let AssetId { policy_id, asset_name } = token;
utxo.value
.native_tokens
.get(&policy_id.0)
.and_then(|assets| assets.iter().find(|asset| asset.name == asset_name.0.to_vec()))
.map(|asset| asset.amount)
.unwrap_or(0) // Token can be not found if the reserve was created with the initial deposit of 0 tokens
.try_into()
.expect("Token amount in an UTXO always fits u64")
}

fn deposit_to_reserve_tx(
Expand Down Expand Up @@ -254,27 +251,20 @@ fn validator_output(
let mut assets = Assets::new();
assets.insert(&empty_asset_name(), &1u64.into());
ma.insert(&scripts.auth_policy.csl_script_hash(), &assets);
if let TokenId::AssetId { policy_id, asset_name } = token_amount.token.clone() {
let mut assets = Assets::new();
assets.insert(
&AssetName::new(asset_name.0.to_vec()).expect("AssetName has a valid length"),
&token_amount.amount.into(),
);
ma.insert(&policy_id.0.into(), &assets);
};
let AssetId { policy_id, asset_name } = token_amount.token.clone();
let mut assets = Assets::new();
assets.insert(
&AssetName::new(asset_name.0.to_vec()).expect("AssetName has a valid length"),
&token_amount.amount.into(),
);
ma.insert(&policy_id.0.into(), &assets);
let output = amount_builder.with_coin_and_asset(&0u64.into(), &ma).build()?;

let current_ada = current_utxo.value.lovelace;
let ada = if let TokenId::Ada = token_amount.token {
(current_ada + token_amount.amount).into()
} else {
MinOutputAdaCalculator::new(
&output,
&DataCost::new_coins_per_byte(
&ctx.protocol_parameters.min_utxo_deposit_coefficient.into(),
),
)
.calculate_ada()?
};
let ada = MinOutputAdaCalculator::new(
&output,
&DataCost::new_coins_per_byte(&ctx.protocol_parameters.min_utxo_deposit_coefficient.into()),
)
.calculate_ada()?;

amount_builder.with_coin_and_asset(&ada, &ma).build()
}
4 changes: 2 additions & 2 deletions toolkit/offchain/src/reserve/update_settings.rs
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ mod tests {
use hex_literal::hex;
use ogmios_client::types::{OgmiosTx, OgmiosUtxo};
use partner_chains_plutus_data::reserve::ReserveDatum;
use sidechain_domain::{AssetName, PolicyId, TokenId};
use sidechain_domain::{AssetId, AssetName, PolicyId};

use super::update_reserve_settings_tx;
use crate::{
Expand All @@ -123,7 +123,7 @@ mod tests {
let parameters = crate::reserve::create::ReserveParameters {
initial_incentive: 100,
total_accrued_function_script_hash: PolicyId([233u8; 28]),
token: TokenId::AssetId {
token: AssetId {
policy_id: REWARDS_TOKEN_POLICY_ID,
asset_name: AssetName::from_hex_unsafe(REWARDS_TOKEN_ASSET_NAME_STR),
},
Expand Down
11 changes: 6 additions & 5 deletions toolkit/offchain/tests/integration_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,10 @@ use partner_chains_cardano_offchain::{
reserve, scripts_data, update_governance,
};
use sidechain_domain::{
AdaBasedStaking, AssetName, AuraPublicKey, CandidateRegistration, DParameter, GrandpaPublicKey,
MainchainAddressHash, MainchainPrivateKey, MainchainPublicKey, MainchainSignature, McTxHash,
PermissionedCandidateData, PolicyId, SidechainPublicKey, SidechainSignature, TokenId, UtxoId,
AdaBasedStaking, AssetId, AssetName, AuraPublicKey, CandidateRegistration, DParameter,
GrandpaPublicKey, MainchainAddressHash, MainchainPrivateKey, MainchainPublicKey,
MainchainSignature, McTxHash, PermissionedCandidateData, PolicyId, SidechainPublicKey,
SidechainSignature, UtxoId,
};
use std::time::Duration;
use testcontainers::{clients::Cli, Container, GenericImage};
Expand Down Expand Up @@ -298,7 +299,7 @@ async fn run_create_reserve_management<
reserve::create::ReserveParameters {
initial_incentive: 100,
total_accrued_function_script_hash: PolicyId([233u8; 28]),
token: TokenId::AssetId {
token: AssetId {
policy_id: REWARDS_TOKEN_POLICY_ID,
asset_name: AssetName::from_hex_unsafe(REWARDS_TOKEN_ASSET_NAME_STR),
},
Expand All @@ -321,7 +322,7 @@ async fn run_deposit_to_reserve<
) -> () {
reserve::deposit::deposit_to_reserve(
reserve::deposit::TokenAmount {
token: TokenId::AssetId {
token: AssetId {
policy_id: REWARDS_TOKEN_POLICY_ID,
asset_name: AssetName::from_hex_unsafe(REWARDS_TOKEN_ASSET_NAME_STR),
},
Expand Down
34 changes: 16 additions & 18 deletions toolkit/primitives/domain/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -207,30 +207,28 @@ pub const MAX_ASSET_NAME_LEN: u32 = 32;
pub struct AssetName(pub BoundedVec<u8, ConstU32<MAX_ASSET_NAME_LEN>>);

#[derive(Clone, Debug, PartialEq, Eq)]
pub enum TokenId {
Ada,
AssetId { policy_id: PolicyId, asset_name: AssetName },
pub struct AssetId {
pub policy_id: PolicyId,
pub asset_name: AssetName,
}

#[cfg(feature = "std")]
impl FromStr for TokenId {
impl FromStr for AssetId {
type Err = String;

fn from_str(s: &str) -> Result<Self, Self::Err> {
if s.to_lowercase() == "ada" {
Ok(Self::Ada)
} else {
match s.split_once(".") {
Some((policy_id, asset_name)) => {
let policy_id = PolicyId::from_str(policy_id)
.map_err(|e| format!("{} is invalid Policy ID: {}", policy_id, e))?;
let asset_name = AssetName::from_str(asset_name)
.map_err(|e| format!("{} is invalid Asset Name: {}", asset_name, e))?;
Ok(Self::AssetId { policy_id, asset_name })
},
None => Err("AssetID should be <hex encoded Policy ID>.<hex encoded Asset Name>"
.to_string()),
}
match s.split_once(".") {
Some((policy_id, asset_name)) => {
let policy_id = PolicyId::from_str(policy_id)
.map_err(|e| format!("{} is invalid Policy ID: {}", policy_id, e))?;
let asset_name = AssetName::from_str(asset_name)
.map_err(|e| format!("{} is invalid Asset Name: {}", asset_name, e))?;
Ok(Self { policy_id, asset_name })
},
None => {
Err("AssetId should be <hex encoded Policy ID>.<hex encoded Asset Name>"
.to_string())
},
}
}
}
Expand Down
31 changes: 12 additions & 19 deletions toolkit/primitives/plutus-data/src/reserve.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ use crate::{
VersionedDatum, VersionedGenericDatumShape,
};
use cardano_serialization_lib::{BigInt, BigNum, ConstrPlutusData, PlutusData, PlutusList};
use sidechain_domain::{AssetName, PolicyId, TokenId};
use sidechain_domain::{AssetId, AssetName, PolicyId};

#[derive(Debug, Clone)]
pub enum ReserveRedeemer {
Expand All @@ -22,7 +22,7 @@ pub struct ReserveDatum {

#[derive(Debug, Clone, PartialEq)]
pub struct ReserveImmutableSettings {
pub token: TokenId,
pub token: AssetId,
}

#[derive(Debug, Clone, PartialEq)]
Expand Down Expand Up @@ -73,13 +73,10 @@ impl From<ReserveDatum> for PlutusData {
// Not configurable anymore, hardcoded to 0. If users need "t0" for their V-function, they are responsible for storing it somewhere.
let t0 = PlutusData::new_integer(&BigInt::zero());
immutable_settings.add(&t0);
let (policy_id_bytes, asset_name_bytes) =
match value.immutable_settings.token.clone() {
TokenId::Ada => (vec![], vec![]),
TokenId::AssetId { policy_id, asset_name } => {
(policy_id.0.to_vec(), asset_name.0.to_vec())
},
};
let (policy_id_bytes, asset_name_bytes) = {
let AssetId { policy_id, asset_name } = value.immutable_settings.token.clone();
(policy_id.0.to_vec(), asset_name.0.to_vec())
};
let token_data: PlutusData = {
let mut asset_data = PlutusList::new();
asset_data.add(&PlutusData::new_bytes(policy_id_bytes));
Expand Down Expand Up @@ -175,22 +172,18 @@ fn decode_v0_reserve_datum(datum: &PlutusData) -> Option<ReserveDatum> {
})
}

fn decode_token_id_datum(pd: &PlutusData) -> Option<TokenId> {
fn decode_token_id_datum(pd: &PlutusData) -> Option<AssetId> {
let token_id_list = pd
.as_constr_plutus_data()
.filter(|constr| constr.alternative() == BigNum::zero())
.map(|constr| constr.data())?;
let mut token_id_list_iter = token_id_list.into_iter();
let policy_id = token_id_list_iter.next()?.as_bytes()?.to_vec();
let asset_name = token_id_list_iter.next()?.as_bytes()?.to_vec();
if policy_id.is_empty() && asset_name.is_empty() {
Some(TokenId::Ada)
} else {
Some(TokenId::AssetId {
policy_id: PolicyId(policy_id.try_into().ok()?),
asset_name: AssetName(asset_name.try_into().ok()?),
})
}
Some(AssetId {
policy_id: PolicyId(policy_id.try_into().ok()?),
asset_name: AssetName(asset_name.try_into().ok()?),
})
}

#[cfg(test)]
Expand All @@ -206,7 +199,7 @@ mod tests {
fn test_datum() -> ReserveDatum {
ReserveDatum {
immutable_settings: ReserveImmutableSettings {
token: sidechain_domain::TokenId::AssetId {
token: sidechain_domain::AssetId {
policy_id: PolicyId([0; 28]),
asset_name: AssetName::from_hex_unsafe("aabbcc"),
},
Expand Down

0 comments on commit e1cd808

Please sign in to comment.