diff --git a/context/interfaces/src/ident.md b/context/interfaces/src/ident.md index 7d90e60..a3bf7df 100644 --- a/context/interfaces/src/ident.md +++ b/context/interfaces/src/ident.md @@ -9,8 +9,9 @@ ## Public interface ```rust -/// Human-readable mesh name. -pub struct Name(pub Vec); +/// Human-readable mesh name. The label representation is private; construct +/// via `FromStr` so the non-empty invariant always holds. +pub struct Name; /// Name or wildcard authority pattern over mesh names. pub struct NamePattern; diff --git a/src/ident.rs b/src/ident.rs index f5f4bab..d2b84e1 100644 --- a/src/ident.rs +++ b/src/ident.rs @@ -24,7 +24,7 @@ const MAX_LABEL_LENGTH: usize = 63; #[derive( Clone, Hash, PartialEq, Eq, PartialOrd, Ord, Debug, SerializeDisplay, DeserializeFromStr, )] -pub struct Name(pub Vec); +pub struct Name(Vec); impl Name { /// Number of labels in the name (e.g., "vm1.test.mesh" has 3 labels). @@ -38,7 +38,7 @@ impl Name { #[must_use] fn first_label(&self) -> &str { // Labels are stored in reverse order, so the first label is last - self.0.last().expect("Name always has at least one label") + self.0.last().assert() } /// Check if this name starts with the given prefix. diff --git a/src/modules/adhoc.rs b/src/modules/adhoc.rs index 473fae3..9b3f800 100644 --- a/src/modules/adhoc.rs +++ b/src/modules/adhoc.rs @@ -501,7 +501,7 @@ pub(crate) fn is_valid_mesh(pattern: &NamePattern) -> bool { return false; }; - base.0.len() == 2 + base.label_count() == 2 } #[cfg(test)] diff --git a/src/trust_engine_bench/node.rs b/src/trust_engine_bench/node.rs index a908128..2680c58 100644 --- a/src/trust_engine_bench/node.rs +++ b/src/trust_engine_bench/node.rs @@ -57,7 +57,8 @@ impl NodeFactory { trusted: bool, ) -> Node { let id = self.allocate_id(); - let name = child_name(parent_namespace, child_label(id, trusted)); + let label = child_label(id, trusted); + let name = child_name(parent_namespace, &label); Node { id, children: Vec::new(), @@ -83,7 +84,8 @@ impl NodeFactory { trusted: bool, ) -> Node { let id = self.allocate_id(); - let mesh_name = child_name(parent_namespace, child_label(id, trusted)); + let label = child_label(id, trusted); + let mesh_name = child_name(parent_namespace, &label); Node { id, children: Vec::new(), @@ -177,9 +179,7 @@ impl Node { } fn root_identity_name(mesh_name: &Name) -> Name { - let mut labels = mesh_name.0.clone(); - labels.push("root".to_string()); - Name(labels) + format!("root.{mesh_name}").parse().assert() } fn child_label(id: NodeId, trusted: bool) -> String { @@ -190,8 +190,6 @@ fn child_label(id: NodeId, trusted: bool) -> String { } } -fn child_name(parent_namespace: &Name, label: String) -> Name { - let mut labels = parent_namespace.0.clone(); - labels.push(label); - Name(labels) +fn child_name(parent_namespace: &Name, label: &str) -> Name { + format!("{label}.{parent_namespace}").parse().assert() }