diff --git a/crates/hotshot/src/traits/election/randomized_committee.rs b/crates/hotshot/src/traits/election/randomized_committee.rs index d664e2a6e8..401a3102e2 100644 --- a/crates/hotshot/src/traits/election/randomized_committee.rs +++ b/crates/hotshot/src/traits/election/randomized_committee.rs @@ -41,6 +41,8 @@ pub struct RandomizedCommittee { } impl Membership for RandomizedCommittee { + type Error = utils::anytrace::Error; + /// Create a new election fn new( eligible_leaders: Vec::SignatureKey>>, @@ -139,7 +141,7 @@ impl Membership for RandomizedCommittee { } /// Index the vector of public keys with the current view number - fn leader( + fn lookup_leader( &self, view_number: TYPES::View, _epoch: ::Epoch, diff --git a/crates/hotshot/src/traits/election/static_committee.rs b/crates/hotshot/src/traits/election/static_committee.rs index acacc51cb6..258a2cfeda 100644 --- a/crates/hotshot/src/traits/election/static_committee.rs +++ b/crates/hotshot/src/traits/election/static_committee.rs @@ -39,6 +39,8 @@ pub struct StaticCommittee { } impl Membership for StaticCommittee { + type Error = utils::anytrace::Error; + /// Create a new election fn new( eligible_leaders: Vec::SignatureKey>>, @@ -137,7 +139,7 @@ impl Membership for StaticCommittee { } /// Index the vector of public keys with the current view number - fn leader( + fn lookup_leader( &self, view_number: TYPES::View, _epoch: ::Epoch, diff --git a/crates/hotshot/src/traits/election/static_committee_leader_two_views.rs b/crates/hotshot/src/traits/election/static_committee_leader_two_views.rs index bb9574e37e..8658744e71 100644 --- a/crates/hotshot/src/traits/election/static_committee_leader_two_views.rs +++ b/crates/hotshot/src/traits/election/static_committee_leader_two_views.rs @@ -39,6 +39,8 @@ pub struct StaticCommitteeLeaderForTwoViews { } impl Membership for StaticCommitteeLeaderForTwoViews { + type Error = utils::anytrace::Error; + /// Create a new election fn new( eligible_leaders: Vec::SignatureKey>>, @@ -137,7 +139,7 @@ impl Membership for StaticCommitteeLeaderForTwoViews::Epoch, diff --git a/crates/types/src/traits/election.rs b/crates/types/src/traits/election.rs index d22f226875..580f06c5a8 100644 --- a/crates/types/src/traits/election.rs +++ b/crates/types/src/traits/election.rs @@ -16,6 +16,9 @@ use crate::{traits::signature_key::SignatureKey, PeerConfig}; pub trait Membership: Clone + Debug + Eq + PartialEq + Send + Sync + Hash + 'static { + /// The error type returned by methods like `lookup_leader`. + type Error: std::fmt::Display; + /// Create a committee fn new( // Note: eligible_leaders is currently a hack because the DA leader == the quorum leader @@ -56,11 +59,30 @@ pub trait Membership: /// See if a node has stake in the committee in a specific epoch fn has_stake(&self, pub_key: &TYPES::SignatureKey, epoch: TYPES::Epoch) -> bool; + /// The leader of the committee for view `view_number` in `epoch`. + /// + /// Note: this function uses a HotShot-internal error type. + /// You should implement `lookup_leader`, rather than implementing this function directly. + /// + /// # Errors + /// Returns an error if the leader cannot be calculated. + fn leader(&self, view: TYPES::View, epoch: TYPES::Epoch) -> Result { + use utils::anytrace::*; + + self.lookup_leader(view, epoch).wrap().context(info!( + "Failed to get leader for view {view} in epoch {epoch}" + )) + } + /// The leader of the committee for view `view_number` in `epoch`. /// /// # Errors /// Returns an error if the leader cannot be calculated - fn leader(&self, view: TYPES::View, epoch: TYPES::Epoch) -> Result; + fn lookup_leader( + &self, + view: TYPES::View, + epoch: TYPES::Epoch, + ) -> std::result::Result; /// Get the network topic for the committee fn committee_topic(&self) -> Topic;