diff --git a/toolkit/offchain/src/csl.rs b/toolkit/offchain/src/csl.rs index 7d0d42ce5..92af781be 100644 --- a/toolkit/offchain/src/csl.rs +++ b/toolkit/offchain/src/csl.rs @@ -11,6 +11,7 @@ use ogmios_client::{ types::{OgmiosUtxo, OgmiosValue}, }; use sidechain_domain::NetworkType; +use std::collections::HashMap; pub(crate) fn plutus_script_hash(script_bytes: &[u8], language: LanguageKind) -> [u8; 28] { // Before hashing the script, we need to prepend with byte denoting the language. @@ -168,31 +169,38 @@ pub(crate) fn get_first_validator_budget( #[derive(Debug, Clone, PartialEq)] pub struct ScriptExUnits { - pub mint_ex_units: Vec, - pub spend_ex_units: Vec, + pub mint_ex_units: HashMap, + pub spend_ex_units: HashMap, } impl ScriptExUnits { pub fn new() -> Self { - ScriptExUnits { mint_ex_units: Vec::new(), spend_ex_units: Vec::new() } + ScriptExUnits { mint_ex_units: HashMap::new(), spend_ex_units: HashMap::new() } } - pub fn with_mint_ex_units(self, mint_ex_units: Vec) -> Self { + pub fn with_mint_ex_units(self, mint_ex_units: HashMap) -> Self { Self { mint_ex_units, ..self } } - pub fn with_spend_ex_units(self, spend_ex_units: Vec) -> Self { + pub fn with_spend_ex_units(self, spend_ex_units: HashMap) -> Self { Self { spend_ex_units, ..self } } } pub(crate) fn get_validator_budgets( - mut responses: Vec, + responses: Vec, ) -> Result { - responses.sort_by_key(|r| r.validator.index); - let (mint_ex_units, spend_ex_units) = responses - .into_iter() - .partition::, _>(|response| response.validator.purpose == "mint"); - let mint_ex_units = mint_ex_units.into_iter().map(ex_units_from_response).collect(); - let spend_ex_units = spend_ex_units.into_iter().map(ex_units_from_response).collect(); + let mut spend_ex_units = HashMap::new(); + let mut mint_ex_units = HashMap::new(); + for r in responses { + println!("Validator: {:?}", r); + match r.validator.purpose.as_str() { + "mint" => mint_ex_units.insert(r.validator.index, ex_units_from_response(r)), + "spend" => spend_ex_units.insert(r.validator.index, ex_units_from_response(r)), + _ => return Err(JsError::from_str(&format!( + "Internal error: unexpected validator purpose '{}'", + r.validator.purpose + ))), + }; + }; Ok(ScriptExUnits { mint_ex_units, spend_ex_units }) } @@ -331,6 +339,7 @@ pub(crate) trait TransactionBuilderExt { &mut self, script: &PlutusScript, ex_units: ExUnits, + script_index: u32, ) -> Result<(), JsError>; /// Adds minting of 1 token (with empty asset name) for the given script using reference input @@ -339,6 +348,7 @@ pub(crate) trait TransactionBuilderExt { script: &PlutusScript, ref_input: &TransactionInput, ex_units: ExUnits, + script_index: u32, ) -> Result<(), JsError>; /// Sets fields required by the most of partner-chains smart contract transactions. @@ -399,6 +409,7 @@ impl TransactionBuilderExt for TransactionBuilder { &mut self, script: &PlutusScript, ex_units: ExUnits, + script_index: u32, ) -> Result<(), JsError> { let mut mint_builder = self.get_mint_builder().unwrap_or(MintBuilder::new()); @@ -407,7 +418,7 @@ impl TransactionBuilderExt for TransactionBuilder { &validator_source, &Redeemer::new( &RedeemerTag::new_mint(), - &0u32.into(), + &script_index.into(), &PlutusData::new_empty_constr_plutus_data(&0u32.into()), &ex_units, ), @@ -422,6 +433,7 @@ impl TransactionBuilderExt for TransactionBuilder { script: &PlutusScript, ref_input: &TransactionInput, ex_units: ExUnits, + script_index: u32, ) -> Result<(), JsError> { let mut mint_builder = self.get_mint_builder().unwrap_or(MintBuilder::new()); @@ -435,7 +447,7 @@ impl TransactionBuilderExt for TransactionBuilder { &validator_source, &Redeemer::new( &RedeemerTag::new_mint(), - &0u32.into(), + &script_index.into(), &PlutusData::new_empty_constr_plutus_data(&0u32.into()), &ex_units, ), @@ -510,6 +522,7 @@ pub(crate) trait InputsBuilderExt: Sized { utxo: &OgmiosUtxo, script: &PlutusScript, ex_units: ExUnits, + script_index: u32, ) -> Result<(), JsError>; /// Adds ogmios inputs to the tx inputs builder. @@ -525,6 +538,7 @@ impl InputsBuilderExt for TxInputsBuilder { utxo: &OgmiosUtxo, script: &PlutusScript, ex_units: ExUnits, + script_index: u32, ) -> Result<(), JsError> { let input = utxo.to_csl_tx_input(); let amount = convert_value(&utxo.value)?; @@ -533,7 +547,7 @@ impl InputsBuilderExt for TxInputsBuilder { &Redeemer::new( &RedeemerTag::new_spend(), // CSL will set redeemer index for the index of script input after sorting transaction inputs - &0u32.into(), + &script_index.into(), &PlutusData::new_empty_constr_plutus_data(&0u32.into()), &ex_units, ), @@ -704,33 +718,33 @@ mod tests { fn get_validator_budgets_works() { let result = get_validator_budgets(vec![ OgmiosEvaluateTransactionResponse { - validator: OgmiosValidatorIndex::new(1, "mint"), + validator: OgmiosValidatorIndex::new(0, "mint"), budget: OgmiosBudget::new(11, 21), }, OgmiosEvaluateTransactionResponse { validator: OgmiosValidatorIndex::new(0, "spend"), - budget: OgmiosBudget::new(10, 20), + budget: OgmiosBudget::new(12, 22), }, OgmiosEvaluateTransactionResponse { - validator: OgmiosValidatorIndex::new(3, "mint"), + validator: OgmiosValidatorIndex::new(1, "mint"), budget: OgmiosBudget::new(13, 23), }, OgmiosEvaluateTransactionResponse { - validator: OgmiosValidatorIndex::new(2, "spend"), - budget: OgmiosBudget::new(12, 22), + validator: OgmiosValidatorIndex::new(1, "spend"), + budget: OgmiosBudget::new(14, 24), }, ]) .expect("Should succeed"); let expected = ScriptExUnits { - mint_ex_units: vec![ - ExUnits::new(&11u64.into(), &21u64.into()), - ExUnits::new(&13u64.into(), &23u64.into()), - ], - spend_ex_units: vec![ - ExUnits::new(&10u64.into(), &20u64.into()), - ExUnits::new(&12u64.into(), &22u64.into()), - ], + mint_ex_units: HashMap::from([ + (0, ExUnits::new(&11u64.into(), &21u64.into())), + (1, ExUnits::new(&13u64.into(), &23u64.into())), + ]), + spend_ex_units: HashMap::from([ + (0, ExUnits::new(&12u64.into(), &22u64.into())), + (1, ExUnits::new(&14u64.into(), &24u64.into())), + ]), }; assert_eq!(result, expected); @@ -769,6 +783,7 @@ mod prop_tests { .add_mint_one_script_token( &test_policy(), ExUnits::new(&BigNum::zero(), &BigNum::zero()), + 0, ) .unwrap(); tx_builder diff --git a/toolkit/offchain/src/d_param/mod.rs b/toolkit/offchain/src/d_param/mod.rs index 0458700e9..762b45709 100644 --- a/toolkit/offchain/src/d_param/mod.rs +++ b/toolkit/offchain/src/d_param/mod.rs @@ -20,6 +20,7 @@ use ogmios_client::{ }; use partner_chains_plutus_data::d_param::{d_parameter_to_plutus_data, DParamDatum}; use sidechain_domain::{DParameter, McTxHash, UtxoId}; +use std::collections::HashMap; #[cfg(test)] mod tests; @@ -120,11 +121,11 @@ where C: Transactions, { let zero_ex_units = ScriptExUnits { - mint_ex_units: vec![ - ExUnits::new(&0u64.into(), &0u64.into()), - ExUnits::new(&0u64.into(), &0u64.into()), - ], - spend_ex_units: vec![], + mint_ex_units: HashMap::from([ + (0, ExUnits::new(&0u64.into(), &0u64.into())), + (1, ExUnits::new(&0u64.into(), &0u64.into())), + ]), + spend_ex_units: HashMap::new(), }; let gov_utxo = crate::init_governance::get_governance_utxo(genesis_utxo, client) @@ -146,14 +147,13 @@ where hex::encode(tx.to_bytes()) ) })?; - let mut mint_witness_ex_units = get_validator_budgets(evaluate_response)?; - mint_witness_ex_units.mint_ex_units.reverse(); + let ex_units = get_validator_budgets(evaluate_response)?; let tx = mint_d_param_token_tx( validator, policy, d_parameter, &ctx, - mint_witness_ex_units, + ex_units, gov_utxo, )?; let signed_tx = ctx.sign(&tx).to_bytes(); @@ -182,8 +182,8 @@ where C: Transactions, { let zero_ex_units = ScriptExUnits { - mint_ex_units: vec![ExUnits::new(&0u64.into(), &0u64.into())], - spend_ex_units: vec![ExUnits::new(&0u64.into(), &0u64.into())], + mint_ex_units: HashMap::from([(0, ExUnits::new(&0u64.into(), &0u64.into()))]), + spend_ex_units: HashMap::from([(0, ExUnits::new(&0u64.into(), &0u64.into()))]), }; let gov_utxo = crate::init_governance::get_governance_utxo(genesis_utxo, client) @@ -206,7 +206,7 @@ where hex::encode(tx.to_bytes()) ) })?; - let spend_ex_units = get_validator_budgets(evaluate_response)?; + let ex_units = get_validator_budgets(evaluate_response)?; let tx = update_d_param_tx( validator, @@ -214,7 +214,7 @@ where d_parameter, current_utxo, &ctx, - spend_ex_units, + ex_units, gov_utxo.clone(), )?; let signed_tx = ctx.sign(&tx).to_bytes(); @@ -235,7 +235,7 @@ fn mint_d_param_token_tx( policy: &PlutusScript, d_parameter: &DParameter, ctx: &TransactionContext, - mut ex_units: ScriptExUnits, + ex_units: ScriptExUnits, gov_utxo: OgmiosUtxo, ) -> Result { let mut tx_builder = TransactionBuilder::new(&get_builder_config(ctx)?); @@ -244,8 +244,10 @@ fn mint_d_param_token_tx( policy, ex_units .mint_ex_units - .pop() - .unwrap_or_else(|| panic!("Mint ex units not found")), + .get(&0) + .unwrap_or_else(|| panic!("Mint ex units not found")) + .clone(), + 0, )?; tx_builder.add_output_with_one_script_token( validator, @@ -268,8 +270,10 @@ fn mint_d_param_token_tx( &gov_tx_input, ex_units .mint_ex_units - .pop() - .unwrap_or_else(|| panic!("Mint ex units not found")), + .get(&1) + .unwrap_or_else(|| panic!("Mint ex units not found")) + .clone(), + 1, )?; let tx_hash = TransactionHash::from_bytes(gov_utxo.transaction.id.into())?; @@ -285,7 +289,7 @@ fn update_d_param_tx( d_parameter: &DParameter, script_utxo: &OgmiosUtxo, ctx: &TransactionContext, - mut ex_units: ScriptExUnits, + ex_units: ScriptExUnits, gov_utxo: OgmiosUtxo, ) -> Result { let config = crate::csl::get_builder_config(ctx)?; @@ -297,8 +301,10 @@ fn update_d_param_tx( validator, ex_units .spend_ex_units - .pop() - .unwrap_or_else(|| panic!("Spend ex units not found")), + .get(&0) + .unwrap_or_else(|| panic!("Spend ex units not found")) + .clone(), + 0, )?; tx_builder.set_inputs(&inputs); @@ -323,8 +329,10 @@ fn update_d_param_tx( &gov_tx_input, ex_units .mint_ex_units - .pop() - .unwrap_or_else(|| panic!("Mint ex units not found")), + .get(&0) + .unwrap_or_else(|| panic!("Mint ex units not found")) + .clone(), + 0, )?; let tx_hash = TransactionHash::from_bytes(gov_utxo.transaction.id.into())?; diff --git a/toolkit/offchain/src/d_param/tests.rs b/toolkit/offchain/src/d_param/tests.rs index 0d90fed13..7f2136cb5 100644 --- a/toolkit/offchain/src/d_param/tests.rs +++ b/toolkit/offchain/src/d_param/tests.rs @@ -12,6 +12,7 @@ use ogmios_client::types::{Asset as OgmiosAsset, OgmiosTx, OgmiosUtxo, OgmiosVal use ogmios_client::types::{OgmiosScript, PlutusScript}; use partner_chains_plutus_data::d_param::d_parameter_to_plutus_data; use sidechain_domain::DParameter; +use std::collections::HashMap; mod mint_tx { use super::*; @@ -21,7 +22,7 @@ mod mint_tx { ExUnits::new(&10000u32.into(), &200u32.into()) } fn ex_units() -> ScriptExUnits { - ScriptExUnits::new().with_mint_ex_units(vec![mint_ex_units(), mint_ex_units()]) + ScriptExUnits::new().with_mint_ex_units(HashMap::from([(0, mint_ex_units()), (1, mint_ex_units())])) } fn mint_d_param_tx() -> Transaction { mint_d_param_token_tx( @@ -185,8 +186,8 @@ mod update_d_parameter { } fn ex_units() -> ScriptExUnits { ScriptExUnits::new() - .with_spend_ex_units(vec![spend_ex_units()]) - .with_mint_ex_units(vec![mint_ex_units()]) + .with_spend_ex_units(HashMap::from([(0, spend_ex_units())])) + .with_mint_ex_units(HashMap::from([(0, mint_ex_units())])) } fn update_d_param_tx() -> Transaction { diff --git a/toolkit/offchain/src/permissioned_candidates.rs b/toolkit/offchain/src/permissioned_candidates.rs index 603c096df..0dcad62e7 100644 --- a/toolkit/offchain/src/permissioned_candidates.rs +++ b/toolkit/offchain/src/permissioned_candidates.rs @@ -8,7 +8,7 @@ //! `[sidechain_public_key, aura_public_key, grandpa_publicKey]`. use crate::csl::{ - get_builder_config, get_first_validator_budget, InputsBuilderExt, TransactionBuilderExt, + get_builder_config, get_validator_budgets, InputsBuilderExt, TransactionBuilderExt, TransactionContext, }; use crate::plutus_script::PlutusScript; @@ -24,6 +24,8 @@ use partner_chains_plutus_data::permissioned_candidates::{ permissioned_candidates_to_plutus_data, PermissionedCandidateDatums, }; use sidechain_domain::{McTxHash, PermissionedCandidateData, UtxoId}; +use std::collections::HashMap; +use crate::csl::ScriptExUnits; pub async fn upsert_permissioned_candidates( genesis_utxo: UtxoId, @@ -111,7 +113,14 @@ async fn insert_permissioned_candidates( where C: Transactions, { - let zero_ex_units = ExUnits::new(&0u64.into(), &0u64.into()); + let zero_ex_units = ScriptExUnits { + mint_ex_units: HashMap::from([ + (0, ExUnits::new(&0u64.into(), &0u64.into())), + (1, ExUnits::new(&0u64.into(), &0u64.into())), + ]), + spend_ex_units: HashMap::new(), + }; + let tx = mint_permissioned_candidates_token_tx(validator, policy, candidates, &ctx, zero_ex_units)?; let evaluate_response = client.evaluate_transaction(&tx.to_bytes()).await.map_err(|e| { @@ -121,13 +130,13 @@ where hex::encode(tx.to_bytes()) ) })?; - let mint_witness_ex_units = get_first_validator_budget(evaluate_response)?; + let ex_units = get_validator_budgets(evaluate_response)?; let tx = mint_permissioned_candidates_token_tx( validator, policy, candidates, &ctx, - mint_witness_ex_units, + ex_units, )?; let signed_tx = ctx.sign(&tx).to_bytes(); let res = client.submit_transaction(&signed_tx).await.map_err(|e| { @@ -153,7 +162,10 @@ async fn update_permissioned_candidates( where C: Transactions, { - let zero_ex_units = ExUnits::new(&0u64.into(), &0u64.into()); + let zero_ex_units = ScriptExUnits { + mint_ex_units: HashMap::from([(0, ExUnits::new(&0u64.into(), &0u64.into()))]), + spend_ex_units: HashMap::from([(0, ExUnits::new(&0u64.into(), &0u64.into()))]), + }; let tx = update_permissioned_candidates_tx( validator, policy, @@ -169,7 +181,7 @@ where hex::encode(tx.to_bytes()) ) })?; - let spend_ex_units = get_first_validator_budget(evaluate_response)?; + let ex_units = get_validator_budgets(evaluate_response)?; let tx = update_permissioned_candidates_tx( validator, @@ -177,7 +189,7 @@ where candidates, current_utxo, &ctx, - spend_ex_units, + ex_units, )?; let signed_tx = ctx.sign(&tx).to_bytes(); let res = client.submit_transaction(&signed_tx).await.map_err(|e| { @@ -197,11 +209,18 @@ fn mint_permissioned_candidates_token_tx( policy: &PlutusScript, permissioned_candidates: &[PermissionedCandidateData], ctx: &TransactionContext, - mint_witness_ex_units: ExUnits, + ex_units: ScriptExUnits, ) -> Result { let mut tx_builder = TransactionBuilder::new(&get_builder_config(ctx)?); // The essence of transaction: mint token and set output with it - tx_builder.add_mint_one_script_token(policy, mint_witness_ex_units)?; + tx_builder.add_mint_one_script_token( + policy, + ex_units.mint_ex_units + .get(&0) + .unwrap_or_else(|| panic!("Mint ex units not found")) + .clone(), + 0, + )?; tx_builder.add_output_with_one_script_token( validator, policy, @@ -218,13 +237,20 @@ fn update_permissioned_candidates_tx( permissioned_candidates: &[PermissionedCandidateData], script_utxo: &OgmiosUtxo, ctx: &TransactionContext, - validator_redeemer_ex_units: ExUnits, + ex_units: ScriptExUnits, ) -> Result { let config = crate::csl::get_builder_config(ctx)?; let mut tx_builder = TransactionBuilder::new(&config); let mut inputs = TxInputsBuilder::new(); - inputs.add_script_utxo_input(script_utxo, policy, validator_redeemer_ex_units)?; + inputs.add_script_utxo_input( + script_utxo, policy, + ex_units.spend_ex_units + .get(&0) + .unwrap_or_else(|| panic!("Mint ex units not found")) + .clone(), + 0, + )?; tx_builder.set_inputs(&inputs); tx_builder.add_output_with_one_script_token( @@ -264,11 +290,15 @@ mod tests { UtxoId, }; use std::str::FromStr; + use crate::permissioned_candidates::{ScriptExUnits, HashMap}; #[test] fn mint_permissioned_candiates_token_tx_regression_test() { // We know the expected values were obtained with the correct code - let ex_units = ExUnits::new(&10000u32.into(), &200u32.into()); + let ex_units = ScriptExUnits { + mint_ex_units: HashMap::from([(0, ExUnits::new(&10000u32.into(), &200u32.into()))]), + spend_ex_units: HashMap::new(), + }; let tx = mint_permissioned_candidates_token_tx( &test_validator(), @@ -338,7 +368,7 @@ mod tests { assert_eq!(redeemer.tag(), RedeemerTag::new_mint()); assert_eq!(redeemer.index(), 0u64.into()); assert_eq!(redeemer.data(), PlutusData::new_empty_constr_plutus_data(&0u64.into())); - assert_eq!(redeemer.ex_units(), ex_units); + assert_eq!(redeemer.ex_units(), ex_units.mint_ex_units.get(&0).unwrap().clone()); // script_data_hash check assert_eq!( tx.body().script_data_hash().unwrap().to_hex(), @@ -374,7 +404,10 @@ mod tests { ..Default::default() }; - let ex_units = ExUnits::new(&10000u32.into(), &200u32.into()); + let ex_units = ScriptExUnits { + mint_ex_units: HashMap::from([(0, ExUnits::new(&10000u32.into(), &200u32.into()))]), + spend_ex_units: HashMap::from([(0, ExUnits::new(&10000u32.into(), &200u32.into()))]), + }; let tx = update_permissioned_candidates_tx( &test_validator(), @@ -437,7 +470,7 @@ mod tests { // Index is 1 because the script input is the 2nd input, if it was the 3rd input it would be 2, etc. assert_eq!(redeemer.index(), 1u64.into()); assert_eq!(redeemer.data(), PlutusData::new_empty_constr_plutus_data(&0u64.into())); - assert_eq!(redeemer.ex_units(), ex_units); + assert_eq!(redeemer.ex_units(), ex_units.spend_ex_units.get(&0).unwrap().clone()); // script_data_hash check assert_eq!( tx.body().script_data_hash().unwrap().to_hex(), diff --git a/toolkit/offchain/src/register.rs b/toolkit/offchain/src/register.rs index 22431ed5f..e427da0e8 100644 --- a/toolkit/offchain/src/register.rs +++ b/toolkit/offchain/src/register.rs @@ -1,7 +1,7 @@ #![allow(dead_code)] use crate::csl::{ - get_first_validator_budget, InputsBuilderExt, OgmiosUtxoExt, TransactionBuilderExt, + get_validator_budgets, InputsBuilderExt, OgmiosUtxoExt, TransactionBuilderExt, TransactionContext, }; use crate::{ @@ -24,6 +24,9 @@ use partner_chains_plutus_data::registered_candidates::{ candidate_registration_to_plutus_data, RegisterValidatorDatum, }; use sidechain_domain::*; +use crate::csl::ScriptExUnits; +use std::collections::HashMap; + pub trait Register { #[allow(async_fn_in_trait)] @@ -90,7 +93,20 @@ pub async fn run_register< } let own_registration_utxos = own_registrations.iter().map(|r| r.0.clone()).collect::>(); - let zero_ex_units = ExUnits::new(&0u64.into(), &0u64.into()); + let spend_ex_units = own_registration_utxos + .iter() + .enumerate() + .map(|(index, _)| (index as u32, ExUnits::new(&0u32.into(), &0u32.into()))) + .collect::>(); + + let zero_ex_units = ScriptExUnits { + mint_ex_units: HashMap::new(), + spend_ex_units, + }; + + + + let mut tx = register_tx( &validator, candidate_registration, @@ -109,14 +125,14 @@ pub async fn run_register< hex::encode(tx.to_bytes()) ) })?; - let validator_redeemer_ex_units = get_first_validator_budget(evaluate_response)?; + let ex_units = get_validator_budgets(evaluate_response)?; tx = register_tx( &validator, candidate_registration, registration_utxo, &own_registration_utxos, &ctx, - validator_redeemer_ex_units, + ex_units, )?; } @@ -171,18 +187,22 @@ fn register_tx( registration_utxo: &OgmiosUtxo, own_registration_utxos: &[OgmiosUtxo], ctx: &TransactionContext, - validator_redeemer_ex_units: ExUnits, + ex_units: ScriptExUnits, ) -> Result { let config = crate::csl::get_builder_config(ctx)?; let mut tx_builder = TransactionBuilder::new(&config); { let mut inputs = TxInputsBuilder::new(); - for own_registration_utxo in own_registration_utxos { + for (index, own_registration_utxo) in own_registration_utxos.into_iter().enumerate() { inputs.add_script_utxo_input( own_registration_utxo, validator, - validator_redeemer_ex_units.clone(), + ex_units.spend_ex_units + .get(&(index as u32)) + .unwrap_or_else(|| panic!("Spend ex units not found")) + .clone(), + index as u32, )?; } inputs.add_key_inputs(&[registration_utxo.clone()], &ctx.payment_key_hash())?; @@ -216,7 +236,7 @@ mod tests { use crate::csl::{OgmiosUtxoExt, TransactionContext}; use crate::test_values::{self, *}; use cardano_serialization_lib::{ - Address, BigNum, ExUnits, NetworkIdKind, Transaction, TransactionInputs, + Address, ExUnits, NetworkIdKind, Transaction, TransactionInputs, }; use ogmios_client::types::OgmiosValue; use ogmios_client::types::{OgmiosTx, OgmiosUtxo}; @@ -226,6 +246,7 @@ mod tests { collection::{hash_set, vec}, prelude::*, }; + use crate::register::{ScriptExUnits, HashMap}; use sidechain_domain::{ AdaBasedStaking, AuraPublicKey, CandidateRegistration, GrandpaPublicKey, @@ -277,7 +298,10 @@ mod tests { #[test] fn register_tx_regression_test() { - let ex_units = ExUnits::new(&0u32.into(), &0u32.into()); + let ex_units = ScriptExUnits { + mint_ex_units: HashMap::new(), + spend_ex_units: HashMap::from([(0, ExUnits::new(&0u32.into(), &0u32.into()))]), + }; let payment_key_utxos = vec![lesser_payment_utxo(), greater_payment_utxo(), registration_utxo()]; let ctx = TransactionContext { @@ -339,13 +363,18 @@ mod tests { } else { Vec::new() }; + + let ex_units = ScriptExUnits::new().with_spend_ex_units( + HashMap::from([(0, ExUnits::new(&0u32.into(), &0u32.into()))]) + ); + let tx = register_tx( &test_values::test_validator(), &candidate_registration, registration_utxo, &own_registration_utxos, &ctx, - ExUnits::new(&BigNum::zero(), &BigNum::zero()), + ex_units, ) .unwrap();