Skip to main content
Sign in
Snippets Groups Projects
Commit dd7b66e7 authored by Hugo Trentesaux's avatar Hugo Trentesaux
Browse files

improve genesis parsing

adds info
parent ecc1c028
No related branches found
No related tags found
1 merge request!168gtest genesis new format
......@@ -9723,9 +9723,9 @@ version = "1.6.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "97fee6b57c6a41524a810daee9286c02d7752c4253064d0b05472833a438f675"
dependencies = [
"cfg-if 0.1.10",
"cfg-if 1.0.0",
"digest 0.10.6",
"rand 0.7.3",
"rand 0.8.5",
"static_assertions",
]
......
......
......@@ -90,6 +90,8 @@ pub fn development_chain_spec() -> Result<ChainSpec, String> {
// custom genesis when DUNITER_GTEST_GENESIS is set
if let Ok(genesis_json_path) = std::env::var("DUNITER_GTEST_GENESIS") {
// log
log::info!("loading genesis from {genesis_json_path}");
// return chainspecs
Ok(ChainSpec::from_genesis(
// Name
......@@ -102,7 +104,7 @@ pub fn development_chain_spec() -> Result<ChainSpec, String> {
move || {
super::gtest_genesis::build_genesis(
// path of json genesis
genesis_json_path.clone(),
&genesis_json_path,
// wasm binary
wasm_binary,
// replace authority by Alice
......@@ -132,6 +134,8 @@ pub fn development_chain_spec() -> Result<ChainSpec, String> {
None,
))
} else {
// log
log::info!("generating genesis");
// generated genesis
Ok(ChainSpec::from_genesis(
// Name
......
......
......@@ -23,7 +23,6 @@ use gtest_runtime::{
SmithMembershipConfig, SudoConfig, SystemConfig, TechnicalCommitteeConfig,
UniversalDividendConfig,
};
use log;
use serde::Deserialize;
use sp_core::{blake2_256, Decode, Encode, H256};
use std::collections::{BTreeMap, HashMap};
......@@ -44,7 +43,7 @@ struct GenesisJson {
first_ud: u64,
first_ud_reeval: u32,
initial_monetary_mass: u64,
wallets: HashMap<AccountId, u64>, // TODO u128
wallets: HashMap<AccountId, u64>, // u128
sudo_key: Option<AccountId>,
technical_committee: Vec<String>,
}
......@@ -63,7 +62,7 @@ struct Identity {
/// block at which the next cert can be emitted
next_cert_issuable_on: u32,
/// balance of the account of this identity
balance: u64, // TODO u128
balance: u64, // u128
/// certs received with their expiration block
certs_received: HashMap<String, u32>,
}
......@@ -93,10 +92,11 @@ fn validate_idty_name(idty_name: &str) -> bool {
.all(|c| c.is_ascii_alphanumeric() || c == '-' || c == '_')
}
/// read genesis data
/// ============================================================================================ ///
/// build genesis from json file
pub fn build_genesis(
// path of genesis config
genesis_config_path: String,
genesis_config_path: &str,
// wasm binary
wasm_binary: &[u8],
// useful to enforce Alice authority when developing
......@@ -138,24 +138,25 @@ pub fn build_genesis(
};
// parse the json file
let genesis_data: GenesisJson = match serde_json::from_slice(&bytes) {
Ok(x) => x,
Err(e) => {
log::error!("Error parsing gen conf file: {}", e);
panic!()
}
};
let genesis_data: GenesisJson = serde_json::from_slice(&bytes)
.map_err(|e| format!("Error parsing gen conf file: {}", e))?;
// declare variables for building genesis
// -------------------------------------
// track if fatal error occured, but let processing continue
let mut fatal = false;
// monetary mass for double check
let mut monetary_mass = 0u64; // TODO u128
let mut monetary_mass = 0u64; // u128
// wallet index to generate random id
let mut wallet_index: u32 = 0;
// counter for online authorities at genesis
let mut online_authorities_counter = 0;
let mut counter_online_authorities = 0;
// track identity index
let mut identity_index = HashMap::new();
// counter for certifications
let mut counter_cert = 0u32;
// counter for smith certifications
let mut counter_smith_cert = 0u32;
// declare variables to fill in genesis
// -------------------------------------
......@@ -182,7 +183,8 @@ pub fn build_genesis(
for (pubkey, balance) in genesis_data.wallets {
// check existential deposit
if balance < EXISTENTIAL_DEPOSIT {
log::warn!("{pubkey} has {balance} which is below {EXISTENTIAL_DEPOSIT}");
log::warn!("wallet {pubkey} has {balance} which is below {EXISTENTIAL_DEPOSIT}");
fatal = true;
}
// double check the monetary mass
......@@ -220,10 +222,18 @@ pub fn build_genesis(
monetary_mass += identity.balance;
// insert identity
// TODO check that index does not already exist
// check that index does not already exist
if let Some(other_name) = identity_index.get(&identity.index) {
log::warn!(
"{other_name} already has identity index {} of {name}",
identity.index
);
fatal = true;
}
identity_index.insert(identity.index, name);
// TODO only add the identity if not expired
// only add the identity if not expired
if identity.membership_expire_on != 0 {
identities.push(GenesisIdty {
index: identity.index,
name: common_runtime::IdtyName::from(name.as_str()),
......@@ -238,12 +248,15 @@ pub fn build_genesis(
owner_key: identity.owner_key.clone(),
// TODO remove the removable_on field of identity
removable_on: 0,
// TODO maybe add a disabled status
status: IdtyStatus::Validated,
},
});
} else {
log::info!("ignoring expired identity {name}");
};
// insert the membershup data
// insert the membershup data (only if not expired)
if identity.membership_expire_on != 0 {
memberships.insert(
identity.index,
MembershipData {
......@@ -251,6 +264,7 @@ pub fn build_genesis(
},
);
}
}
// Technical Comittee //
// NOTE : when changing owner key, the technical committee is not changed
......@@ -272,6 +286,7 @@ pub fn build_genesis(
.ok_or(format!("Identity '{}' not exist", issuer))?
.index;
certs.insert(*issuer_index, Some(expire_on.clone()));
counter_cert += 1;
}
certs_by_receiver.insert(identity.index, certs);
}
......@@ -285,9 +300,9 @@ pub fn build_genesis(
// Initial authorities and session keys
let session_keys_bytes = if let Some(declared_session_keys) = smith_data.session_keys {
online_authorities_counter += 1;
counter_online_authorities += 1;
// insert authority as online
initial_authorities.insert(1, (identity.owner_key.clone(), true));
initial_authorities.insert(identity.index, (identity.owner_key.clone(), true));
// decode session keys or force to given value
match maybe_force_authority {
Some(ref bytes) => bytes.clone(),
......@@ -320,6 +335,7 @@ pub fn build_genesis(
.ok_or(format!("Identity '{}' does not exist", issuer))?
.index;
certs.insert(*issuer_index, Some(GENESIS_SMITH_CERTS_EXPIRE_ON));
counter_smith_cert += 1;
}
smith_certs_by_receiver.insert(identity.index, certs);
......@@ -332,15 +348,20 @@ pub fn build_genesis(
);
}
// Verify certifications coherence
// Verify certifications coherence (can be ignored for old users)
for (idty_index, receiver_certs) in &certs_by_receiver {
if receiver_certs.len() < MIN_CERT as usize {
let name = identity_index.get(idty_index).unwrap();
let identity = genesis_data.identities.get(name.clone()).unwrap();
if identity.membership_expire_on != 0 {
log::warn!(
"{:?} has received only {}/{} certifications)",
identity_index.get(idty_index),
"[{}] has received only {}/{} certifications",
name,
receiver_certs.len(),
MIN_CERT
);
fatal = true;
}
}
}
......@@ -348,25 +369,59 @@ pub fn build_genesis(
for (idty_index, certs) in &smith_certs_by_receiver {
if certs.len() < SMITH_MIN_CERT as usize {
log::warn!(
"{:?} has received only {}/{} smith certifications)",
identity_index.get(idty_index),
"[{}] has received only {}/{} smith certifications",
identity_index.get(idty_index).unwrap(),
certs.len(),
SMITH_MIN_CERT
);
fatal = true;
}
}
// check number of online authorities
if online_authorities_counter != 1 {
log::error!("one and only one smith must be online, not {online_authorities_counter}",);
if counter_online_authorities != 1 {
log::error!("one and only one smith must be online, not {counter_online_authorities}");
}
// check monetary mass
if monetary_mass != genesis_data.initial_monetary_mass {
log::warn!(
"monetary_mass ({monetary_mass}) and initial_monetary_mass ({}) do not match",
"actuel monetary_mass ({monetary_mass}) and initial_monetary_mass ({}) do not match",
genesis_data.initial_monetary_mass
);
fatal = true;
}
// give genesis info
log::info!(
"inserted genesis with:
- {} accounts
- {} members in technical committee
- {} total identities
- {} active identities
- {} memberships
- {} smith memberships
- {} initial autorities
- {} initial online authorities
- {} session keys
- {} certifications
- {} smith certifications",
accounts.len(),
technical_committee_members.len(),
identity_index.len(),
identities.len(),
memberships.len(),
smith_memberships.len(),
initial_authorities.len(),
counter_online_authorities,
session_keys_map.len(),
counter_cert,
counter_smith_cert,
);
// check the logs to see all the fatal error preventing from starting gtest currency
if fatal {
panic!();
}
// return genesis config
......
......
{
"first_ud": 10000,
"first_ud_reeval": 100800,
"initial_monetary_mass": 531345,
"initial_monetary_mass": 531381,
"identities": {
"old_user1": {
"index": 7777,
"owner_key": "5H95G8bwuf4yyNNNa83hDhj7wpYaSRhZiGezZ9TDbyqNdAhY",
"membership_expire_on": 0,
"next_cert_issuable_on": 0,
"balance": 12,
"certs_received": {
"elois": 10
}
},
"old_user2": {
"index": 8888,
"owner_key": "5H95G8bwuf4yyNNNa83hDhj7wpYaSRhZiGezZ9TDbyqNdAhY",
"membership_expire_on": 0,
"next_cert_issuable_on": 0,
"balance": 12,
"certs_received": {
"elois": 10
}
},
"old_user3": {
"index": 6666,
"owner_key": "5H95G8bwuf4yyNNNa83hDhj7wpYaSRhZiGezZ9TDbyqNdAhY",
"membership_expire_on": 0,
"next_cert_issuable_on": 0,
"balance": 12,
"certs_received": {
"elois": 10
}
},
"elois": {
"index": 2,
"owner_key": "5H95G8bwuf4yyNNNa83hDhj7wpYaSRhZiGezZ9TDbyqNdAhY",
......@@ -21,7 +51,8 @@
"kapis": 100,
"DavidB": 100,
"Gamaliel": 100,
"wellno1": 100
"wellno1": 100,
"old_user1": 50
}
},
"HugoTrentesaux": {
......
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please to comment