chore: remove support for legacy mixnode within the performance contract (#6205)

This commit is contained in:
Jędrzej Stuczyński
2025-11-14 15:04:59 +00:00
committed by GitHub
parent 440aadf124
commit d73b7b7127
3 changed files with 6 additions and 238 deletions
+1 -22
View File
@@ -3,7 +3,7 @@
use cosmwasm_std::{from_json, Binary, CustomQuery, QuerierWrapper, StdError, StdResult};
use cw_storage_plus::{Key, Namespace, Path, PrimaryKey};
use nym_mixnet_contract_common::{Interval, MixNodeBond, NymNodeBond};
use nym_mixnet_contract_common::{Interval, NymNodeBond};
use nym_performance_contract_common::{EpochId, NodeId};
use serde::de::DeserializeOwned;
use std::ops::Deref;
@@ -51,15 +51,10 @@ pub(crate) trait MixnetContractQuerier {
fn check_node_existence(&self, address: impl Into<String>, node_id: NodeId) -> StdResult<bool> {
let mixnet_contract_address = address.into();
// 1. check if it's a nym-node
if let Some(nym_node) = self.query_nymnode_bond(mixnet_contract_address.clone(), node_id)? {
return Ok(!nym_node.is_unbonding);
}
// 2. try a legacy mixnode
if let Some(nym_node) = self.query_mixnode_bond(mixnet_contract_address, node_id)? {
return Ok(!nym_node.is_unbonding);
}
Ok(false)
}
@@ -78,22 +73,6 @@ pub(crate) trait MixnetContractQuerier {
self.query_mixnet_contract_storage_value(address, storage_key)
}
fn query_mixnode_bond(
&self,
address: impl Into<String>,
node_id: NodeId,
) -> StdResult<Option<MixNodeBond>> {
// construct proper map key
let pk_namespace = "mnn";
let path: Path<MixNodeBond> = Path::new(
Namespace::from_static_str(pk_namespace).as_slice(),
&node_id.key().iter().map(Key::as_ref).collect::<Vec<_>>(),
);
let storage_key = path.deref();
self.query_mixnet_contract_storage_value(address, storage_key)
}
}
impl<C> MixnetContractQuerier for QuerierWrapper<'_, C>
-105
View File
@@ -1261,28 +1261,6 @@ mod tests {
}
);
// bonded legacy mix-node
let node_id = tester.bond_dummy_legacy_mixnode()?;
let perf = NodePerformance {
node_id,
performance: Default::default(),
};
let res =
storage.submit_performance_data(tester.deps_mut(), env.clone(), &nm, 0, perf);
assert!(res.is_ok());
// unbonded
tester.unbond_legacy_mixnode(node_id)?;
let res = storage
.submit_performance_data(tester.deps_mut(), env.clone(), &nm, 0, dummy_perf)
.unwrap_err();
assert_eq!(
res,
NymPerformanceContractError::NodeNotBonded {
node_id: dummy_perf.node_id
}
);
Ok(())
}
}
@@ -1984,11 +1962,6 @@ mod tests {
tester.unbond_nymnode(nym_node_between)?;
let nym_node2 = tester.bond_dummy_nymnode()?;
let mix_node1 = tester.bond_dummy_legacy_mixnode()?;
let mixnode_between = tester.bond_dummy_legacy_mixnode()?;
tester.unbond_legacy_mixnode(mixnode_between)?;
let mix_node2 = tester.bond_dummy_legacy_mixnode()?;
let env = tester.env();
// single id - nothing bonded
@@ -2053,84 +2026,6 @@ mod tests {
assert_eq!(res.accepted_scores, 2);
assert_eq!(res.non_existent_nodes, vec![2, nym_node_between]);
// MIXNODES
// one bonded mixnode, one not bonded
let res = storage.batch_submit_performance_results(
tester.deps_mut(),
env.clone(),
&nm,
3,
vec![
NodePerformance {
node_id: mix_node1,
performance: Default::default(),
},
NodePerformance {
node_id: 999999,
performance: Default::default(),
},
],
)?;
assert_eq!(res.accepted_scores, 1);
assert_eq!(res.non_existent_nodes, vec![999999]);
// not-bonded, bonded, not-bonded, bonded
let res = storage.batch_submit_performance_results(
tester.deps_mut(),
env.clone(),
&nm,
4,
vec![
NodePerformance {
node_id: 2,
performance: Default::default(),
},
NodePerformance {
node_id: mix_node1,
performance: Default::default(),
},
NodePerformance {
node_id: mixnode_between,
performance: Default::default(),
},
NodePerformance {
node_id: mix_node2,
performance: Default::default(),
},
],
)?;
assert_eq!(res.accepted_scores, 2);
assert_eq!(res.non_existent_nodes, vec![2, mixnode_between]);
// nym-node, not bonded, mixnode
let res = storage.batch_submit_performance_results(
tester.deps_mut(),
env.clone(),
&nm,
5,
vec![
NodePerformance {
node_id: 3,
performance: Default::default(),
},
NodePerformance {
node_id: nym_node1,
performance: Default::default(),
},
NodePerformance {
node_id: nym_node_between,
performance: Default::default(),
},
NodePerformance {
node_id: mix_node2,
performance: Default::default(),
},
],
)?;
assert_eq!(res.accepted_scores, 2);
assert_eq!(res.non_existent_nodes, vec![3, nym_node_between]);
Ok(())
}
}
+5 -111
View File
@@ -6,10 +6,9 @@ use crate::helpers::MixnetContractQuerier;
use crate::storage::NYM_PERFORMANCE_CONTRACT_STORAGE;
use cosmwasm_std::testing::{message_info, mock_env, MockApi};
use cosmwasm_std::{
coin, coins, Addr, Binary, ContractInfo, Deps, DepsMut, Env, MessageInfo, QuerierWrapper,
StdError, StdResult,
coin, coins, Addr, ContractInfo, Deps, DepsMut, Env, MessageInfo, QuerierWrapper, StdError,
StdResult,
};
use cw_storage_plus::PrimaryKey;
use mixnet_contract::testable_mixnet_contract::MixnetContract;
use nym_contracts_common::signing::{ContractMessageContent, MessageSignature};
use nym_contracts_common::Percent;
@@ -22,9 +21,8 @@ use nym_contracts_common_testing::{
use nym_crypto::asymmetric::ed25519;
use nym_mixnet_contract_common::nym_node::{NodeDetailsResponse, NodeOwnershipResponse, Role};
use nym_mixnet_contract_common::{
CurrentIntervalResponse, EpochId, Interval, MixNode, MixNodeBond, MixnodeDetailsResponse,
NodeCostParams, NodeRewarding, NymNode, NymNodeBondingPayload, RoleAssignment,
SignableNymNodeBondingMsg, DEFAULT_INTERVAL_OPERATING_COST_AMOUNT,
CurrentIntervalResponse, EpochId, Interval, NodeCostParams, NymNode, NymNodeBondingPayload,
RoleAssignment, SignableNymNodeBondingMsg, DEFAULT_INTERVAL_OPERATING_COST_AMOUNT,
DEFAULT_PROFIT_MARGIN_PERCENT,
};
use nym_performance_contract_common::constants::storage_keys;
@@ -33,7 +31,7 @@ use nym_performance_contract_common::{
NymPerformanceContractError, QueryMsg,
};
use serde::de::DeserializeOwned;
use serde::{Deserialize, Serialize};
use serde::Serialize;
use std::str::FromStr;
pub struct PerformanceContract;
@@ -499,110 +497,6 @@ pub(crate) trait PerformanceContractTesterExt:
self.advance_mixnet_epoch()?;
Ok(())
}
fn bond_dummy_legacy_mixnode(&mut self) -> Result<NodeId, NymPerformanceContractError> {
#[derive(Deserialize, Serialize)]
pub(crate) struct UniqueRef<T> {
// note, we collapse the pk - combining everything under the namespace - even if it is composite
pk: Binary,
value: T,
}
// there's no proper Execute flow for this anymore, so we have to "hack" the storage a bit,
// ensuring all invariants still hold
let owner = self.generate_account_with_balance();
let mixnode = MixNode {
host: "1.2.3.4".to_string(),
mix_port: 123,
verloc_port: 123,
http_api_port: 123,
sphinx_key: "aaaa".to_string(),
identity_key: "bbbbb".to_string(),
version: "ccc".to_string(),
};
let cost_params = NodeCostParams {
profit_margin_percent: Percent::from_percentage_value(DEFAULT_PROFIT_MARGIN_PERCENT)
.unwrap(),
interval_operating_cost: coin(DEFAULT_INTERVAL_OPERATING_COST_AMOUNT, TEST_DENOM),
};
// adjust node counter
let node_id_counter: u32 = self.read_from_mixnet_contract_storage("nic")?;
let node_id = node_id_counter + 1;
self.write_to_mixnet_contract_storage_value("nic", &node_id)?;
let current_epoch = self.current_mixnet_epoch()?;
let pledge = coin(100_000000, TEST_DENOM);
let mixnode_rewarding =
NodeRewarding::initialise_new(cost_params, &pledge, current_epoch).unwrap();
let env = self.env();
let mixnode_bond = MixNodeBond {
mix_id: node_id,
owner,
original_pledge: pledge,
mix_node: mixnode,
proxy: None,
bonding_height: env.block.height,
is_unbonding: false,
};
// save to the main mixnode storage
self.set_contract_map_value(
self.mixnet_contract_address()?,
"mnn",
node_id,
&mixnode_bond,
)?;
// update indices
let pk = node_id.joined_key();
let unique_ref = UniqueRef {
pk: pk.into(),
value: mixnode_bond.clone(),
};
// owner index
let idx = mixnode_bond.owner.clone();
self.set_contract_map_value(self.mixnet_contract_address()?, "mno", idx, &unique_ref)?;
// identity key index
let idx = mixnode_bond.mix_node.identity_key.clone();
self.set_contract_map_value(self.mixnet_contract_address()?, "mni", idx, &unique_ref)?;
// sphinx key index
let idx = mixnode_bond.mix_node.sphinx_key.clone();
self.set_contract_map_value(self.mixnet_contract_address()?, "mns", idx, &unique_ref)?;
// update rewarding data
self.set_contract_map_value(
self.mixnet_contract_address()?,
"mnr",
node_id,
&mixnode_rewarding,
)?;
Ok(node_id)
}
fn unbond_legacy_mixnode(
&mut self,
node_id: NodeId,
) -> Result<(), NymPerformanceContractError> {
let bond: MixnodeDetailsResponse = self.query_arbitrary_contract(
self.mixnet_contract_address()?,
&nym_mixnet_contract_common::QueryMsg::GetMixnodeDetails { mix_id: node_id },
)?;
let node_owner = bond.mixnode_details.unwrap().bond_information.owner;
self.execute_mixnet_contract(
message_info(&node_owner, &[]),
&nym_mixnet_contract_common::ExecuteMsg::UnbondMixnode {},
)?;
self.advance_mixnet_epoch()?;
Ok(())
}
}
impl PerformanceContractTesterExt for ContractTester<PerformanceContract> {}