Skip to content

Commit

Permalink
Feature/cosmwasm plus storage (#924)
Browse files Browse the repository at this point in the history
* Upgraded code to be cosmwasm 1.0-beta.2 compatible

* Added cw-storage-plus dependency

* Experimentally replaced storage for config and layers with cw plus Item

* The same for main mixnode storage

* Usingn IndexedMap for mixnodes

* Split delegations from mixnodes into separate module

* MixnodeIndex on Addr directly

* Moved namespace values to constants

* Outdated comment

* [ci skip] Generate TS types

* Removed redundant identity index on mixnodes

* IndexMap for gateways storage

* Moved total delegation into a Map

* Compiling contract code after delegation storage upgrades

Tests dont compile yet and neither, I would assume, the client code

* Delegation type cleanup

* Client fixes

* Migrated delegation tests + fixed them

* Moved Rewarding Status to rewards

* Reward pool

* Rewarding status migrated

* Made clippy happier

* Added explorer API to default workspace members

* Updated delegation types in explorer-api

* Fixed tauri wallet

Co-authored-by: jstuczyn <jstuczyn@users.noreply.github.com>
  • Loading branch information
jstuczyn and jstuczyn authored Nov 30, 2021
1 parent c9315b5 commit 794cfad
Show file tree
Hide file tree
Showing 38 changed files with 1,474 additions and 1,757 deletions.
1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ default-members = [
"service-providers/network-requester",
"mixnode",
"validator-api",
"explorer-api",
]

exclude = ["explorer", "contracts", "tokenomics-py"]
43 changes: 9 additions & 34 deletions common/client-libs/validator-client/src/client.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,10 @@ use mixnet_contract::ContractSettingsParams;

use crate::{validator_api, ValidatorClientError};
use coconut_interface::{BlindSignRequestBody, BlindedSignatureResponse, VerificationKeyResponse};
use mixnet_contract::{GatewayBond, MixNodeBond};
use mixnet_contract::{Delegation, GatewayBond, MixNodeBond};
#[cfg(feature = "nymd-client")]
use mixnet_contract::{
MixnetContractVersion, MixnodeRewardingStatusResponse, RawDelegationData,
RewardingIntervalResponse,
MixnetContractVersion, MixnodeRewardingStatusResponse, RewardingIntervalResponse,
};
use url::Url;

Expand Down Expand Up @@ -312,9 +311,7 @@ impl<C> Client<C> {
Ok(delegations)
}

pub async fn get_all_nymd_mixnode_delegations(
&self,
) -> Result<Vec<mixnet_contract::UnpackedDelegation<RawDelegationData>>, ValidatorClientError>
pub async fn get_all_network_delegations(&self) -> Result<Vec<Delegation>, ValidatorClientError>
where
C: CosmWasmClient + Sync,
{
Expand All @@ -323,7 +320,7 @@ impl<C> Client<C> {
loop {
let mut paged_response = self
.nymd
.get_all_mix_delegations_paged(
.get_all_network_delegations_paged(
start_after.take(),
self.mixnode_delegations_page_limit,
)
Expand All @@ -340,10 +337,10 @@ impl<C> Client<C> {
Ok(delegations)
}

pub async fn get_all_nymd_reverse_mixnode_delegations(
pub async fn get_all_delegator_delegations(
&self,
delegation_owner: &cosmrs::AccountId,
) -> Result<Vec<mixnet_contract::IdentityKey>, ValidatorClientError>
) -> Result<Vec<Delegation>, ValidatorClientError>
where
C: CosmWasmClient + Sync,
{
Expand All @@ -352,13 +349,13 @@ impl<C> Client<C> {
loop {
let mut paged_response = self
.nymd
.get_reverse_mix_delegations_paged(
mixnet_contract::Addr::unchecked(delegation_owner.as_ref()),
.get_delegator_delegations_paged(
delegation_owner.to_string(),
start_after.take(),
self.mixnode_delegations_page_limit,
)
.await?;
delegations.append(&mut paged_response.delegated_nodes);
delegations.append(&mut paged_response.delegations);

if let Some(start_after_res) = paged_response.start_next_after {
start_after = Some(start_after_res)
Expand All @@ -370,28 +367,6 @@ impl<C> Client<C> {
Ok(delegations)
}

pub async fn get_all_nymd_mixnode_delegations_of_owner(
&self,
delegation_owner: &cosmrs::AccountId,
) -> Result<Vec<mixnet_contract::Delegation>, ValidatorClientError>
where
C: CosmWasmClient + Sync,
{
let mut delegations = Vec::new();
for node_identity in self
.get_all_nymd_reverse_mixnode_delegations(delegation_owner)
.await?
{
let delegation = self
.nymd
.get_mix_delegation(node_identity, delegation_owner)
.await?;
delegations.push(delegation);
}

Ok(delegations)
}

pub async fn blind_sign(
&self,
request_body: &BlindSignRequestBody,
Expand Down
44 changes: 21 additions & 23 deletions common/client-libs/validator-client/src/nymd/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,11 @@ use cosmrs::rpc::endpoint::broadcast;
use cosmrs::rpc::{Error as TendermintRpcError, HttpClientUrl};
use cosmwasm_std::{Coin, Uint128};
use mixnet_contract::{
Addr, ContractSettingsParams, Delegation, ExecuteMsg, Gateway, GatewayOwnershipResponse,
IdentityKey, LayerDistribution, MixNode, MixOwnershipResponse, MixnetContractVersion,
MixnodeRewardingStatusResponse, PagedAllDelegationsResponse, PagedGatewayResponse,
PagedMixDelegationsResponse, PagedMixnodeResponse, PagedReverseMixDelegationsResponse,
QueryMsg, RawDelegationData, RewardingIntervalResponse,
ContractSettingsParams, Delegation, ExecuteMsg, Gateway, GatewayOwnershipResponse, IdentityKey,
LayerDistribution, MixNode, MixOwnershipResponse, MixnetContractVersion,
MixnodeRewardingStatusResponse, PagedAllDelegationsResponse, PagedDelegatorDelegationsResponse,
PagedGatewayResponse, PagedMixDelegationsResponse, PagedMixnodeResponse, QueryMsg,
RewardingIntervalResponse,
};
use serde::Serialize;
use std::collections::HashMap;
Expand Down Expand Up @@ -313,7 +313,7 @@ impl<C> NymdClient<C> {
C: CosmWasmClient + Sync,
{
let request = QueryMsg::OwnsMixnode {
address: Addr::unchecked(address.as_ref()),
address: address.to_string(),
};
let response: MixOwnershipResponse = self
.client
Expand All @@ -328,7 +328,7 @@ impl<C> NymdClient<C> {
C: CosmWasmClient + Sync,
{
let request = QueryMsg::OwnsGateway {
address: Addr::unchecked(address.as_ref()),
address: address.to_string(),
};
let response: GatewayOwnershipResponse = self
.client
Expand Down Expand Up @@ -375,14 +375,13 @@ impl<C> NymdClient<C> {
pub async fn get_mix_delegations_paged(
&self,
mix_identity: IdentityKey,
// I really hate mixing cosmwasm and cosmos-sdk types here...
start_after: Option<Addr>,
start_after: Option<String>,
page_limit: Option<u32>,
) -> Result<PagedMixDelegationsResponse, NymdError>
where
C: CosmWasmClient + Sync,
{
let request = QueryMsg::GetMixDelegations {
let request = QueryMsg::GetMixnodeDelegations {
mix_identity: mix_identity.to_owned(),
start_after,
limit: page_limit,
Expand All @@ -393,16 +392,15 @@ impl<C> NymdClient<C> {
}

/// Gets list of all mixnode delegations on particular page.
pub async fn get_all_mix_delegations_paged(
pub async fn get_all_network_delegations_paged(
&self,
// I really hate mixing cosmwasm and cosmos-sdk types here...
start_after: Option<Vec<u8>>,
start_after: Option<(IdentityKey, String)>,
page_limit: Option<u32>,
) -> Result<PagedAllDelegationsResponse<RawDelegationData>, NymdError>
) -> Result<PagedAllDelegationsResponse, NymdError>
where
C: CosmWasmClient + Sync,
{
let request = QueryMsg::GetAllMixDelegations {
let request = QueryMsg::GetAllNetworkDelegations {
start_after,
limit: page_limit,
};
Expand All @@ -412,17 +410,17 @@ impl<C> NymdClient<C> {
}

/// Gets list of all the mixnodes on which a particular address delegated.
pub async fn get_reverse_mix_delegations_paged(
pub async fn get_delegator_delegations_paged(
&self,
delegation_owner: Addr,
delegator: String,
start_after: Option<IdentityKey>,
page_limit: Option<u32>,
) -> Result<PagedReverseMixDelegationsResponse, NymdError>
) -> Result<PagedDelegatorDelegationsResponse, NymdError>
where
C: CosmWasmClient + Sync,
{
let request = QueryMsg::GetReverseMixDelegations {
delegation_owner,
let request = QueryMsg::GetDelegatorDelegations {
delegator,
start_after,
limit: page_limit,
};
Expand All @@ -432,17 +430,17 @@ impl<C> NymdClient<C> {
}

/// Checks value of delegation of given client towards particular mixnode.
pub async fn get_mix_delegation(
pub async fn get_delegation_details(
&self,
mix_identity: IdentityKey,
delegator: &AccountId,
) -> Result<Delegation, NymdError>
where
C: CosmWasmClient + Sync,
{
let request = QueryMsg::GetMixDelegation {
let request = QueryMsg::GetDelegationDetails {
mix_identity,
address: Addr::unchecked(delegator.as_ref()),
delegator: delegator.to_string(),
};
self.client
.query_contract_smart(self.contract_address()?, &request)
Expand Down
104 changes: 42 additions & 62 deletions common/mixnet-contract/src/delegation.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
// Copyright 2021 - Nym Technologies SA <contact@nymtech.net>
// SPDX-License-Identifier: Apache-2.0

// due to code generated by JsonSchema
#![allow(clippy::field_reassign_with_default)]

Expand All @@ -7,58 +10,44 @@ use schemars::JsonSchema;
use serde::{Deserialize, Serialize};
use std::fmt::Display;

#[derive(Clone, Debug, Deserialize, PartialEq, Serialize, JsonSchema)]
pub struct UnpackedDelegation<T> {
#[derive(Clone, Debug, Deserialize, Serialize, PartialEq, JsonSchema)]
pub struct Delegation {
pub owner: Addr,
pub node_identity: IdentityKey,
pub delegation_data: T,
pub amount: Coin,
pub block_height: u64,
}

impl<T> UnpackedDelegation<T> {
pub fn new(owner: Addr, node_identity: IdentityKey, delegation_data: T) -> Self {
UnpackedDelegation {
impl Delegation {
pub fn new(owner: Addr, node_identity: IdentityKey, amount: Coin, block_height: u64) -> Self {
Delegation {
owner,
node_identity,
delegation_data,
}
}
}

#[derive(Clone, Debug, Deserialize, PartialEq, Serialize, JsonSchema)]
pub struct RawDelegationData {
pub amount: Uint128,
pub block_height: u64,
}

impl RawDelegationData {
pub fn new(amount: Uint128, block_height: u64) -> Self {
RawDelegationData {
amount,
block_height,
}
}
}

#[derive(Clone, Debug, Deserialize, PartialEq, Serialize, JsonSchema)]
pub struct Delegation {
owner: Addr,
amount: Coin,
block_height: u64,
}
// TODO: change that to use .joined_key() and return Vec<u8>
pub fn storage_key(&self) -> (IdentityKey, Addr) {
(self.node_identity(), self.owner())
}

impl Delegation {
pub fn new(owner: Addr, amount: Coin, block_height: u64) -> Self {
Delegation {
owner,
amount,
block_height,
pub fn increment_amount(&mut self, amount: Uint128, at_height: Option<u64>) {
self.amount.amount += amount;
if let Some(at_height) = at_height {
self.block_height = at_height;
}
}

pub fn amount(&self) -> &Coin {
&self.amount
}

pub fn node_identity(&self) -> IdentityKey {
self.node_identity.clone()
}

pub fn owner(&self) -> Addr {
self.owner.clone()
}
Expand All @@ -72,65 +61,56 @@ impl Display for Delegation {
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
write!(
f,
"{} {} delegated by {} at block {}",
self.amount.amount, self.amount.denom, self.owner, self.block_height
"{} delegated towards {} by {} at block {}",
self.amount, self.node_identity, self.owner, self.block_height
)
}
}

#[derive(Clone, Debug, Deserialize, PartialEq, Serialize, JsonSchema)]
pub struct PagedMixDelegationsResponse {
pub node_identity: IdentityKey,
pub delegations: Vec<Delegation>,
pub start_next_after: Option<Addr>,
pub start_next_after: Option<String>,
}

impl PagedMixDelegationsResponse {
pub fn new(
node_identity: IdentityKey,
delegations: Vec<Delegation>,
start_next_after: Option<Addr>,
) -> Self {
pub fn new(delegations: Vec<Delegation>, start_next_after: Option<Addr>) -> Self {
PagedMixDelegationsResponse {
node_identity,
delegations,
start_next_after,
start_next_after: start_next_after.map(|s| s.to_string()),
}
}
}

#[derive(Clone, Debug, Deserialize, PartialEq, Serialize, JsonSchema)]
pub struct PagedReverseMixDelegationsResponse {
pub delegation_owner: Addr,
pub delegated_nodes: Vec<IdentityKey>,
pub struct PagedDelegatorDelegationsResponse {
pub delegations: Vec<Delegation>,
pub start_next_after: Option<IdentityKey>,
}

impl PagedReverseMixDelegationsResponse {
pub fn new(
delegation_owner: Addr,
delegated_nodes: Vec<IdentityKey>,
start_next_after: Option<IdentityKey>,
) -> Self {
PagedReverseMixDelegationsResponse {
delegation_owner,
delegated_nodes,
impl PagedDelegatorDelegationsResponse {
pub fn new(delegations: Vec<Delegation>, start_next_after: Option<IdentityKey>) -> Self {
PagedDelegatorDelegationsResponse {
delegations,
start_next_after,
}
}
}

#[derive(Clone, Debug, Deserialize, PartialEq, Serialize, JsonSchema)]
pub struct PagedAllDelegationsResponse<T> {
pub delegations: Vec<UnpackedDelegation<T>>,
pub start_next_after: Option<Vec<u8>>,
pub struct PagedAllDelegationsResponse {
pub delegations: Vec<Delegation>,
pub start_next_after: Option<(IdentityKey, String)>,
}

impl<T> PagedAllDelegationsResponse<T> {
pub fn new(delegations: Vec<UnpackedDelegation<T>>, start_next_after: Option<Vec<u8>>) -> Self {
impl PagedAllDelegationsResponse {
pub fn new(
delegations: Vec<Delegation>,
start_next_after: Option<(IdentityKey, Addr)>,
) -> Self {
PagedAllDelegationsResponse {
delegations,
start_next_after,
start_next_after: start_next_after.map(|(id, addr)| (id, addr.to_string())),
}
}
}
4 changes: 2 additions & 2 deletions common/mixnet-contract/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@ pub const MIXNODE_DELEGATORS_PAGE_LIMIT: usize = 250;

pub use cosmwasm_std::{Addr, Coin};
pub use delegation::{
Delegation, PagedAllDelegationsResponse, PagedMixDelegationsResponse,
PagedReverseMixDelegationsResponse, RawDelegationData, UnpackedDelegation,
Delegation, PagedAllDelegationsResponse, PagedDelegatorDelegationsResponse,
PagedMixDelegationsResponse,
};
pub use gateway::{Gateway, GatewayBond, GatewayOwnershipResponse, PagedGatewayResponse};
pub use mixnode::{Layer, MixNode, MixNodeBond, MixOwnershipResponse, PagedMixnodeResponse};
Expand Down
Loading

0 comments on commit 794cfad

Please sign in to comment.