use super::{TraitItemKind, TraitItemMetrics};
#[derive(Clone, Debug, Eq, PartialEq)]
pub struct TraitMetrics {
trait_name: String,
total_item_count: usize,
required_method_count: usize,
default_method_count: usize,
default_method_cc_sum: usize,
}
impl TraitMetrics {
#[must_use]
pub fn trait_name(&self) -> &str {
&self.trait_name
}
#[must_use]
pub fn total_item_count(&self) -> usize {
self.total_item_count
}
#[must_use]
pub fn required_method_count(&self) -> usize {
self.required_method_count
}
#[must_use]
pub fn default_method_count(&self) -> usize {
self.default_method_count
}
#[must_use]
pub fn default_method_cc_sum(&self) -> usize {
self.default_method_cc_sum
}
#[must_use]
pub fn implementor_burden(&self) -> usize {
self.required_method_count
}
}
#[derive(Clone, Debug, Default)]
pub struct TraitMetricsBuilder {
trait_name: String,
items: Vec<TraitItemMetrics>,
}
impl TraitMetricsBuilder {
#[must_use]
pub fn new(trait_name: impl Into<String>) -> Self {
Self {
trait_name: trait_name.into(),
items: Vec::new(),
}
}
pub fn add_item(&mut self, item: TraitItemMetrics) {
self.items.push(item);
}
pub fn add_required_method(&mut self, name: impl Into<String>) {
self.items.push(TraitItemMetrics::required_method(name));
}
pub fn add_default_method(
&mut self,
name: impl Into<String>,
cognitive_complexity: usize,
is_from_expansion: bool,
) {
if is_from_expansion {
return;
}
self.items
.push(TraitItemMetrics::default_method(name, cognitive_complexity));
}
pub fn add_associated_type(&mut self, name: impl Into<String>) {
self.items.push(TraitItemMetrics::associated_type(name));
}
pub fn add_associated_const(&mut self, name: impl Into<String>) {
self.items.push(TraitItemMetrics::associated_const(name));
}
#[must_use]
pub fn is_empty(&self) -> bool {
self.items.is_empty()
}
#[must_use]
pub fn build(self) -> TraitMetrics {
let (total_item_count, required_method_count, default_method_count, default_method_cc_sum) =
self.items.iter().fold(
(0, 0, 0, 0),
|(
total_item_count,
required_method_count,
default_method_count,
default_method_cc_sum,
),
item| {
let total_item_count = total_item_count + 1;
let (required_method_count, default_method_count, default_method_cc_sum) =
match item.kind() {
TraitItemKind::RequiredMethod => (
required_method_count + 1,
default_method_count,
default_method_cc_sum,
),
TraitItemKind::DefaultMethod => (
required_method_count,
default_method_count + 1,
default_method_cc_sum + item.default_method_cc().unwrap_or(0),
),
TraitItemKind::AssociatedType | TraitItemKind::AssociatedConst => (
required_method_count,
default_method_count,
default_method_cc_sum,
),
};
(
total_item_count,
required_method_count,
default_method_count,
default_method_cc_sum,
)
},
);
TraitMetrics {
trait_name: self.trait_name,
total_item_count,
required_method_count,
default_method_count,
default_method_cc_sum,
}
}
}