diff --git a/src/canister/individual_user_template/can.did b/src/canister/individual_user_template/can.did index 23349b2a..ea254439 100644 --- a/src/canister/individual_user_template/can.did +++ b/src/canister/individual_user_template/can.did @@ -628,6 +628,7 @@ service : (IndividualUserTemplateInitArgs) -> { request_airdrop : (principal, opt blob, nat, principal) -> (Result_21); return_cycles_to_user_index_canister : (opt nat) -> (); save_snapshot_json : () -> (nat32); + send_creator_dao_stats_to_subnet_orchestrator : () -> (); set_controller_as_subnet_orchestrator : (principal) -> (); settle_neurons_fund_participation : ( SettleNeuronsFundParticipationRequest, diff --git a/src/canister/individual_user_template/src/api/cdao/mod.rs b/src/canister/individual_user_template/src/api/cdao/mod.rs index 85c49810..17511b1f 100644 --- a/src/canister/individual_user_template/src/api/cdao/mod.rs +++ b/src/canister/individual_user_template/src/api/cdao/mod.rs @@ -49,6 +49,7 @@ use crate::{ CANISTER_DATA, }; +pub mod send_creator_dao_stats_to_subnet_orchestrator; pub mod upgrade_creator_dao_governance_canisters; #[update] @@ -304,5 +305,12 @@ async fn deploy_cdao_sns( cdata.token_roots.insert(root.0, ()); }); + let send_creator_dao_stats_res = + subnet_orchestrator.send_creator_dao_stats(vec![root.into()].into_iter().collect()); + + if let Err(e) = send_creator_dao_stats_res { + ic_cdk::println!("Error sending creator stats to subnet orchestrator {}", e) + } + Ok(deployed_cans) } diff --git a/src/canister/individual_user_template/src/api/cdao/send_creator_dao_stats_to_subnet_orchestrator.rs b/src/canister/individual_user_template/src/api/cdao/send_creator_dao_stats_to_subnet_orchestrator.rs new file mode 100644 index 00000000..d6f3cc66 --- /dev/null +++ b/src/canister/individual_user_template/src/api/cdao/send_creator_dao_stats_to_subnet_orchestrator.rs @@ -0,0 +1,31 @@ +use std::collections::HashSet; + +use candid::Principal; +use ic_cdk_macros::update; +use shared_utils::common::utils::permissions::is_caller_controller; + +use crate::{util::subnet_orchestrator::SubnetOrchestrator, CANISTER_DATA}; + +#[update(guard = "is_caller_controller")] +fn send_creator_dao_stats_to_subnet_orchestrator() { + let root_canisters: HashSet = CANISTER_DATA.with_borrow(|canister_data| { + canister_data + .cdao_canisters + .iter() + .map(|deployed_canisters| deployed_canisters.root) + .collect() + }); + + let subnet_orchestrator = SubnetOrchestrator::new(); + + if let Ok(subnet_orchestrator) = subnet_orchestrator { + match subnet_orchestrator.send_creator_dao_stats(root_canisters) { + Ok(()) => {} + Err(e) => { + ic_cdk::println!("Error sending creator dao stats to subnet orchestrator {e}") + } + } + } else { + ic_cdk::println!("Subnet Orchestrator canister id not found"); + } +} diff --git a/src/canister/individual_user_template/src/util/subnet_orchestrator.rs b/src/canister/individual_user_template/src/util/subnet_orchestrator.rs index 6acafb69..1ddc6c18 100644 --- a/src/canister/individual_user_template/src/util/subnet_orchestrator.rs +++ b/src/canister/individual_user_template/src/util/subnet_orchestrator.rs @@ -1,4 +1,7 @@ +use std::collections::HashSet; + use candid::Principal; +use ic_cdk::notify; use shared_utils::common::types::known_principal::KnownPrincipalType; use crate::CANISTER_DATA; @@ -28,4 +31,18 @@ impl SubnetOrchestrator { result } + + pub fn send_creator_dao_stats(&self, root_canisters: HashSet) -> Result<(), String> { + notify( + self.canister_id, + "receive_creator_dao_stats_from_individual_canister", + (root_canisters,), + ) + .map_err(|e| { + format!( + "error sending canister stats to subnet orchestrator {:?}", + e + ) + }) + } } diff --git a/src/canister/platform_orchestrator/can.did b/src/canister/platform_orchestrator/can.did index 2e3f61a0..60dd4d61 100644 --- a/src/canister/platform_orchestrator/can.did +++ b/src/canister/platform_orchestrator/can.did @@ -3,6 +3,13 @@ type CanisterUpgradeStatus = record { count : nat64; upgrade_arg : UpgradeCanisterArg; }; +type CreatorDaoTokenStats = record { + total_number_of_creator_dao_tokens : nat64; + creator_dao_token_sns_canisters : vec record { + principal; + IndividualUserCreatorDaoEntry; + }; +}; type HttpRequest = record { url : text; method : text; @@ -14,6 +21,10 @@ type HttpResponse = record { headers : vec record { text; text }; status_code : nat16; }; +type IndividualUserCreatorDaoEntry = record { + deployed_canisters : vec principal; + individual_profile_id : principal; +}; type KnownPrincipalType = variant { CanisterIdUserIndex; CanisterIdPlatformOrchestrator; @@ -71,11 +82,13 @@ type WasmType = variant { }; service : (PlatformOrchestratorInitArgs) -> { add_principal_as_global_admin : (principal) -> (); + collect_creator_dao_stats_in_the_network : () -> (); deposit_cycles_to_canister : (principal, nat) -> (Result); deregister_subnet_orchestrator : (principal, bool) -> (); get_all_available_subnet_orchestrators : () -> (vec principal) query; get_all_global_admins : () -> (vec principal) query; get_all_subnet_orchestrators : () -> (vec principal) query; + get_creator_dao_stats : () -> (CreatorDaoTokenStats) query; get_global_known_principal : (KnownPrincipalType) -> (principal) query; get_subnet_known_principal : (principal, KnownPrincipalType) -> ( principal, @@ -97,6 +110,10 @@ service : (PlatformOrchestratorInitArgs) -> { populate_known_principal_for_all_subnet : () -> (); provision_empty_canisters_in_a_subnet : (principal, nat64) -> (Result_1); provision_subnet_orchestrator_canister : (principal) -> (Result_2); + receive_creator_dao_stats_from_subnet_orchestrator : ( + principal, + vec principal, + ) -> (Result_1); recharge_subnet_orchestrator : () -> (Result_1); register_new_subnet_orchestrator : (principal, bool) -> (Result_1); reinstall_yral_post_cache_canister : () -> (); diff --git a/src/canister/platform_orchestrator/src/api/mod.rs b/src/canister/platform_orchestrator/src/api/mod.rs index 371fe879..18cc4e7a 100644 --- a/src/canister/platform_orchestrator/src/api/mod.rs +++ b/src/canister/platform_orchestrator/src/api/mod.rs @@ -3,3 +3,4 @@ pub mod canister_management; pub mod cycle_management; pub mod generic_proposal; pub mod monitoring; +pub mod stats; diff --git a/src/canister/platform_orchestrator/src/api/stats/collect_creator_dao_stats_in_the_network.rs b/src/canister/platform_orchestrator/src/api/stats/collect_creator_dao_stats_in_the_network.rs new file mode 100644 index 00000000..961bcc25 --- /dev/null +++ b/src/canister/platform_orchestrator/src/api/stats/collect_creator_dao_stats_in_the_network.rs @@ -0,0 +1,29 @@ +use ic_cdk::notify; +use ic_cdk_macros::update; + +use crate::{guard::is_caller::is_caller_global_admin_or_controller, CANISTER_DATA}; + +#[update(guard = "is_caller_global_admin_or_controller")] +pub fn collect_creator_dao_stats_in_the_network() { + CANISTER_DATA.with_borrow(|canister_data| { + canister_data + .all_subnet_orchestrator_canisters_list + .iter() + .for_each(|subnet_orchestrator_canister_id| { + match notify( + *subnet_orchestrator_canister_id, + "collect_creator_dao_stats_in_the_network", + (), + ) { + Err(e) => { + ic_cdk::println!( + "Failed to collect data from {:?}. Error {:?}", + subnet_orchestrator_canister_id, + e + ) + } + _ => {} + } + }); + }) +} diff --git a/src/canister/platform_orchestrator/src/api/stats/get_creator_dao_stats.rs b/src/canister/platform_orchestrator/src/api/stats/get_creator_dao_stats.rs new file mode 100644 index 00000000..46909f08 --- /dev/null +++ b/src/canister/platform_orchestrator/src/api/stats/get_creator_dao_stats.rs @@ -0,0 +1,9 @@ +use ic_cdk_macros::query; +use shared_utils::types::creator_dao_stats::CreatorDaoTokenStats; + +use crate::{guard::is_caller::is_caller_global_admin_or_controller, CANISTER_DATA}; + +#[query(guard = "is_caller_global_admin_or_controller")] +pub fn get_creator_dao_stats() -> CreatorDaoTokenStats { + CANISTER_DATA.with_borrow(|canister_data| canister_data.creator_dao_stats.clone()) +} diff --git a/src/canister/platform_orchestrator/src/api/stats/mod.rs b/src/canister/platform_orchestrator/src/api/stats/mod.rs new file mode 100644 index 00000000..dad176de --- /dev/null +++ b/src/canister/platform_orchestrator/src/api/stats/mod.rs @@ -0,0 +1,3 @@ +pub mod collect_creator_dao_stats_in_the_network; +pub mod get_creator_dao_stats; +pub mod receive_creator_dao_stats_from_subnet_orchestrator; diff --git a/src/canister/platform_orchestrator/src/api/stats/receive_creator_dao_stats_from_subnet_orchestrator.rs b/src/canister/platform_orchestrator/src/api/stats/receive_creator_dao_stats_from_subnet_orchestrator.rs new file mode 100644 index 00000000..b2a3cc48 --- /dev/null +++ b/src/canister/platform_orchestrator/src/api/stats/receive_creator_dao_stats_from_subnet_orchestrator.rs @@ -0,0 +1,23 @@ +use ic_cdk_macros::update; +use std::collections::HashSet; + +use candid::Principal; +use ic_cdk::caller; + +use crate::{utils::registered_subnet_orchestrator::RegisteredSubnetOrchestrator, CANISTER_DATA}; + +#[update] +pub fn receive_creator_dao_stats_from_subnet_orchestrator( + individual_user_profile_id: Principal, + root_canister_ids: HashSet, +) -> Result<(), String> { + let _registered_subnet_orchestrator = RegisteredSubnetOrchestrator::new(caller())?; + CANISTER_DATA.with_borrow_mut(|canister_data| { + canister_data.add_creator_dao_stats_recieved_from_subnet_orchestrator( + individual_user_profile_id, + root_canister_ids, + ); + }); + + Ok(()) +} diff --git a/src/canister/platform_orchestrator/src/data_model/mod.rs b/src/canister/platform_orchestrator/src/data_model/mod.rs index b38605a1..a5387e33 100644 --- a/src/canister/platform_orchestrator/src/data_model/mod.rs +++ b/src/canister/platform_orchestrator/src/data_model/mod.rs @@ -2,18 +2,22 @@ use ciborium::de; use ic_stable_structures::{storable::Bound, StableBTreeMap, StableLog, Storable}; use std::{ borrow::Cow, - collections::HashSet, + collections::{HashMap, HashSet}, time::{SystemTime, UNIX_EPOCH}, }; use candid::{CandidType, Principal}; use serde::{Deserialize, Serialize}; use shared_utils::{ - canister_specific::platform_orchestrator::types::{ - args::UpgradeCanisterArg, well_known_principal::PlatformOrchestratorKnownPrincipal, - SubnetUpgradeReport, + canister_specific::{ + individual_user_template::types::{cdao::DeployedCdaoCanisters, session::SessionType}, + platform_orchestrator::types::{ + args::UpgradeCanisterArg, well_known_principal::PlatformOrchestratorKnownPrincipal, + SubnetUpgradeReport, + }, }, common::types::wasm::{CanisterWasm, WasmType}, + types::creator_dao_stats::CreatorDaoTokenStats, }; use self::memory::{ @@ -47,6 +51,8 @@ pub struct CanisterData { pub subnets_upgrade_report: SubnetUpgradeReport, #[serde(default)] pub state_guard: StateGuard, + #[serde(default)] + pub creator_dao_stats: CreatorDaoTokenStats, } fn _default_wasms() -> StableBTreeMap { @@ -75,6 +81,7 @@ impl Default for CanisterData { platform_global_admins: Default::default(), subnets_upgrade_report: SubnetUpgradeReport::default(), state_guard: StateGuard::default(), + creator_dao_stats: CreatorDaoTokenStats::default(), } } } @@ -131,3 +138,16 @@ impl Default for CanisterUpgradeStatus { } } } + +impl CanisterData { + pub fn add_creator_dao_stats_recieved_from_subnet_orchestrator( + &mut self, + individual_user_profile_id: Principal, + root_canister_ids: HashSet, + ) { + root_canister_ids.iter().for_each(|root_canister_id| { + self.creator_dao_stats + .insert_new_entry(individual_user_profile_id, *root_canister_id); + }); + } +} diff --git a/src/canister/platform_orchestrator/src/lib.rs b/src/canister/platform_orchestrator/src/lib.rs index 4544426c..4642c19c 100644 --- a/src/canister/platform_orchestrator/src/lib.rs +++ b/src/canister/platform_orchestrator/src/lib.rs @@ -1,6 +1,8 @@ use candid::Principal; use std::cell::RefCell; +use std::collections::HashSet; + use crate::api::generic_proposal::{ PlatformOrchestratorGenericArgumentType, PlatformOrchestratorGenericResultType, }; @@ -16,6 +18,7 @@ use shared_utils::{ common::types::http::{HttpRequest, HttpResponse}, common::types::known_principal::KnownPrincipalType, common::types::wasm::WasmType, + types::creator_dao_stats::CreatorDaoTokenStats, }; mod api; diff --git a/src/canister/platform_orchestrator/src/utils/registered_subnet_orchestrator.rs b/src/canister/platform_orchestrator/src/utils/registered_subnet_orchestrator.rs index cec6576f..6de37f92 100644 --- a/src/canister/platform_orchestrator/src/utils/registered_subnet_orchestrator.rs +++ b/src/canister/platform_orchestrator/src/utils/registered_subnet_orchestrator.rs @@ -1,3 +1,5 @@ +use std::collections::HashSet; + use candid::{Nat, Principal}; use ic_cdk::{ api::management_canister::main::{ diff --git a/src/canister/user_index/can.did b/src/canister/user_index/can.did index 58eec460..32c2c4f3 100644 --- a/src/canister/user_index/can.did +++ b/src/canister/user_index/can.did @@ -119,6 +119,7 @@ type UserIndexInitArgs = record { service : (UserIndexInitArgs) -> { allot_empty_canister : () -> (Result); are_signups_enabled : () -> (bool) query; + collect_creator_dao_stats_in_the_network : () -> (); create_pool_of_individual_user_available_canisters : (text, blob) -> ( Result_1, ); @@ -163,6 +164,9 @@ service : (UserIndexInitArgs) -> { blob, ) -> (Result_3); provision_empty_canisters : (nat64) -> (); + receive_creator_dao_stats_from_individual_canister : (vec principal) -> ( + Result_3, + ); recharge_individual_user_canister : () -> (Result_3); reclaim_cycles_from_individual_canisters : () -> (); request_cycles : (nat) -> (Result_3); diff --git a/src/canister/user_index/src/api/mod.rs b/src/canister/user_index/src/api/mod.rs index d7ad43e9..d85524c9 100644 --- a/src/canister/user_index/src/api/mod.rs +++ b/src/canister/user_index/src/api/mod.rs @@ -3,6 +3,7 @@ pub mod canister_management; pub mod cycle_management; pub mod http; pub mod monitoring; +pub mod stats; pub mod upgrade_individual_user_template; pub mod user_record; pub mod user_signup; diff --git a/src/canister/user_index/src/api/stats/collect_creator_dao_stats_in_the_network.rs b/src/canister/user_index/src/api/stats/collect_creator_dao_stats_in_the_network.rs new file mode 100644 index 00000000..e66e40d4 --- /dev/null +++ b/src/canister/user_index/src/api/stats/collect_creator_dao_stats_in_the_network.rs @@ -0,0 +1,30 @@ +use ic_cdk::notify; +use ic_cdk_macros::update; +use shared_utils::common::utils::permissions::is_caller_controller; + +use crate::CANISTER_DATA; + +#[update(guard = "is_caller_controller")] +pub fn collect_creator_dao_stats_in_the_network() { + CANISTER_DATA.with_borrow(|canister_data| { + canister_data + .user_principal_id_to_canister_id_map + .iter() + .for_each(|(_, user_canister)| { + match notify( + *user_canister, + "send_creator_dao_stats_to_subnet_orchestrator", + (), + ) { + Err(e) => { + ic_cdk::println!( + "Failed to collect data from {:?}. Error {:?}", + user_canister, + e + ) + } + _ => {} + } + }); + }) +} diff --git a/src/canister/user_index/src/api/stats/mod.rs b/src/canister/user_index/src/api/stats/mod.rs new file mode 100644 index 00000000..da75260c --- /dev/null +++ b/src/canister/user_index/src/api/stats/mod.rs @@ -0,0 +1,2 @@ +pub mod collect_creator_dao_stats_in_the_network; +pub mod receive_creator_dao_stats_from_individual_canister; diff --git a/src/canister/user_index/src/api/stats/receive_creator_dao_stats_from_individual_canister.rs b/src/canister/user_index/src/api/stats/receive_creator_dao_stats_from_individual_canister.rs new file mode 100644 index 00000000..4e64325c --- /dev/null +++ b/src/canister/user_index/src/api/stats/receive_creator_dao_stats_from_individual_canister.rs @@ -0,0 +1,34 @@ +use std::collections::HashSet; + +use ic_cdk::{caller, notify}; +use ic_cdk_macros::update; + +use candid::Principal; +use shared_utils::common::types::known_principal::KnownPrincipalType; + +use crate::{util::types::individual_user_canister::IndividualUserCanister, CANISTER_DATA}; + +#[update] +pub fn receive_creator_dao_stats_from_individual_canister( + root_canister_ids: HashSet, +) -> Result<(), String> { + let individual_user = IndividualUserCanister::new(caller())?; + + let platform_orchestrator_canister_id = CANISTER_DATA.with_borrow(|canister_data| { + canister_data + .configuration + .known_principal_ids + .get(&KnownPrincipalType::CanisterIdPlatformOrchestrator) + .copied() + }); + + let platform_orchestrator_canister_id = + platform_orchestrator_canister_id.ok_or("Platform Orchestrator Canister Id not found")?; + + notify( + platform_orchestrator_canister_id, + "receive_creator_dao_stats_from_subnet_orchestrator", + (individual_user.profile_id, root_canister_ids), + ) + .map_err(|e| format!("failed to notify platform orchestrator {:?}", e)) +} diff --git a/src/canister/user_index/src/lib.rs b/src/canister/user_index/src/lib.rs index 086cf58f..c3a35907 100644 --- a/src/canister/user_index/src/lib.rs +++ b/src/canister/user_index/src/lib.rs @@ -1,4 +1,5 @@ use std::cell::RefCell; +use std::collections::HashSet; use candid::Principal; use data_model::CanisterData; diff --git a/src/canister/user_index/src/util/types/individual_user_canister.rs b/src/canister/user_index/src/util/types/individual_user_canister.rs index e66be619..1d5400eb 100644 --- a/src/canister/user_index/src/util/types/individual_user_canister.rs +++ b/src/canister/user_index/src/util/types/individual_user_canister.rs @@ -14,6 +14,7 @@ use crate::CANISTER_DATA; #[derive(Clone, Copy)] pub struct IndividualUserCanister { pub canister_id: Principal, + pub profile_id: Principal, } impl IndividualUserCanister { @@ -23,12 +24,13 @@ impl IndividualUserCanister { .user_principal_id_to_canister_id_map .iter() .find(move |(_, &user_canister)| user_canister == canister_id) - .map(|(_, user_canister_id)| *user_canister_id) + .map(|entry| (*entry.0, *entry.1)) }); - if let Some(user_canister_id) = res { + if let Some((user_profile_id, user_canister_id)) = res { Ok(Self { canister_id: user_canister_id, + profile_id: user_profile_id, }) } else { Err(format!("Canister Id {canister_id} not found in the subnet")) diff --git a/src/lib/integration_tests/tests/creator_dao/main.rs b/src/lib/integration_tests/tests/creator_dao/main.rs index 79d5af0d..d3165152 100644 --- a/src/lib/integration_tests/tests/creator_dao/main.rs +++ b/src/lib/integration_tests/tests/creator_dao/main.rs @@ -18,11 +18,13 @@ use ic_sns_swap::pb::v1::{ NewSaleTicketResponse, RefreshBuyerTokensRequest, RefreshBuyerTokensResponse, }; use sha2::{Digest, Sha256}; +use shared_utils::canister_specific::individual_user_template::types::arg::IndividualUserTemplateInitArgs; use shared_utils::canister_specific::individual_user_template::types::error::AirdropError; use shared_utils::constant::{ SNS_TOKEN_ARCHIVE_MODULE_HASH, SNS_TOKEN_GOVERNANCE_MODULE_HASH, SNS_TOKEN_INDEX_MODULE_HASH, SNS_TOKEN_LEDGER_MODULE_HASH, SNS_TOKEN_ROOT_MODULE_HASH, SNS_TOKEN_SWAP_MODULE_HASH, }; +use shared_utils::types::creator_dao_stats::CreatorDaoTokenStats; use std::time::{Duration, UNIX_EPOCH}; use std::{collections::HashMap, fmt::Debug, str::FromStr, time::SystemTime, vec}; use test_utils::setup::test_constants::get_mock_user_bob_principal_id; @@ -827,4 +829,57 @@ fn creator_dao_tests() { ic_cdk::println!("🧪 SNS token Balance of alice canister: {:?}", alice_bal); assert!(bob_bal == Nat::from(100u64) * 10u64.pow(decimals.into())); + + for _ in 0..5 { + pocket_ic.tick(); + } + + let creator_dao_stats = pocket_ic + .query_call( + platform_canister_id, + charlie_global_admin, + "get_creator_dao_stats", + candid::encode_one(()).unwrap(), + ) + .map(|wasm_result| { + let result: CreatorDaoTokenStats = match wasm_result { + WasmResult::Reply(payload) => candid::decode_one(&payload).unwrap(), + WasmResult::Reject(e) => panic!("\n failed to get creator dao stats {}", e), + }; + result + }) + .unwrap(); + + assert_eq!(creator_dao_stats.total_number_of_creator_dao_tokens, 1); + + pocket_ic + .update_call( + platform_canister_id, + charlie_global_admin, + "collect_creator_dao_stats_in_the_network", + candid::encode_one(()).unwrap(), + ) + .unwrap(); + + for _ in 0..5 { + pocket_ic.tick(); + } + + let creator_dao_stats = pocket_ic + .query_call( + platform_canister_id, + charlie_global_admin, + "get_creator_dao_stats", + candid::encode_one(()).unwrap(), + ) + .map(|wasm_result| { + let result: CreatorDaoTokenStats = match wasm_result { + WasmResult::Reply(payload) => candid::decode_one(&payload).unwrap(), + WasmResult::Reject(e) => panic!("\n failed to get creator dao stats {}", e), + }; + result + }) + .unwrap(); + + assert_eq!(creator_dao_stats.total_number_of_creator_dao_tokens, 1); } diff --git a/src/lib/shared_utils/src/types/creator_dao_stats.rs b/src/lib/shared_utils/src/types/creator_dao_stats.rs new file mode 100644 index 00000000..c371322a --- /dev/null +++ b/src/lib/shared_utils/src/types/creator_dao_stats.rs @@ -0,0 +1,50 @@ +use std::collections::{HashMap, HashSet}; + +use candid::{CandidType, Principal}; +use serde::{Deserialize, Serialize}; + +type IndividualProfileId = Principal; +type RootCanisterId = Principal; + +#[derive(Default, Debug, Serialize, Deserialize, CandidType, Clone)] +pub struct CreatorDaoTokenStats { + creator_dao_token_sns_canisters: HashMap, + pub total_number_of_creator_dao_tokens: u64, +} + +#[derive(CandidType, Serialize, Deserialize, Debug, Clone)] +struct IndividualUserCreatorDaoEntry { + individual_profile_id: IndividualProfileId, + deployed_canisters: HashSet, +} + +impl CreatorDaoTokenStats { + pub fn insert_new_entry( + &mut self, + individual_user_profile_id: IndividualProfileId, + root_canister_id: RootCanisterId, + ) { + let individual_user_creator_dao_entry = self + .creator_dao_token_sns_canisters + .get_mut(&individual_user_profile_id); + + if let Some(individual_user_creator_dao_entry) = individual_user_creator_dao_entry { + if individual_user_creator_dao_entry + .deployed_canisters + .insert(root_canister_id) + { + self.total_number_of_creator_dao_tokens += 1; + } + } else { + self.creator_dao_token_sns_canisters.insert( + individual_user_profile_id, + IndividualUserCreatorDaoEntry { + individual_profile_id: individual_user_profile_id, + deployed_canisters: vec![root_canister_id].into_iter().collect(), + }, + ); + + self.total_number_of_creator_dao_tokens += 1; + } + } +} diff --git a/src/lib/shared_utils/src/types/mod.rs b/src/lib/shared_utils/src/types/mod.rs index 7c293205..5100d911 100644 --- a/src/lib/shared_utils/src/types/mod.rs +++ b/src/lib/shared_utils/src/types/mod.rs @@ -1 +1,2 @@ pub mod canister_specific; +pub mod creator_dao_stats;