#![doc(
html_logo_url = "https://raw.githubusercontent.com/maidsafe/QA/master/Images/maidsafe_logo.png",
html_favicon_url = "https://maidsafe.net/img/favicon.ico",
test(attr(forbid(warnings)))
)]
#![forbid(unsafe_code)]
#![warn(
// TODO: add missing debug implementations for structs?
// missing_debug_implementations,
missing_docs,
trivial_casts,
trivial_numeric_casts,
unused_extern_crates,
unused_import_braces,
unused_qualifications,
unused_results
)]
#![recursion_limit = "128"]
pub use crate::{
accumulation::Accumulation,
calculation::{RewardAlgo, StorageRewards},
utils::RewardCounterSet,
};
use sn_data_types::{AccountId, Money, RewardCounter, Work};
use std::collections::HashMap;
pub mod accumulation;
pub mod calculation;
pub mod utils;
mod example;
#[derive(Clone, Eq, PartialEq, Debug)]
pub enum AccumulationEvent {
AccountAdded(AccountAdded),
RewardsAccumulated(RewardsAccumulated),
RewardsClaimed(RewardsClaimed),
}
#[derive(Clone, Eq, PartialEq, Debug)]
pub struct AccountAdded {
pub id: AccountId,
pub work: Work,
}
#[derive(Clone, Eq, PartialEq, Debug)]
pub struct RewardsAccumulated {
pub id: Vec<u8>,
pub distribution: HashMap<AccountId, Money>,
}
#[derive(Clone, Eq, PartialEq, PartialOrd, Debug)]
pub struct RewardsClaimed {
pub account: AccountId,
pub rewards: RewardCounter,
}
#[cfg(test)]
mod test {
use super::{Accumulation, AccumulationEvent};
use sn_data_types::{Error, Money, PublicKey, Result};
use threshold_crypto::SecretKey;
macro_rules! hashmap {
($( $key: expr => $val: expr ),*) => {{
let mut map = ::std::collections::HashMap::new();
$( let _ = map.insert($key, $val); )*
map
}}
}
#[test]
fn when_data_was_not_previously_rewarded_reward_accumulates() -> Result<()> {
let mut acc = Accumulation::new(Default::default(), Default::default());
let account = get_random_pk();
let data_hash = vec![1, 2, 3];
let reward = Money::from_nano(10);
let distribution = hashmap![account => reward];
let e = acc.accumulate(data_hash, distribution)?;
assert!(e.distribution.len() == 1);
assert!(e.distribution.contains_key(&account));
assert_eq!(&reward, e.distribution.get(&account).unwrap());
acc.apply(AccumulationEvent::RewardsAccumulated(e));
match acc.get(&account) {
None => return Err(Error::NoSuchKey),
Some(accumulated) => assert_eq!(accumulated.reward, reward),
};
Ok(())
}
fn get_random_pk() -> PublicKey {
PublicKey::from(SecretKey::random().public_key())
}
}