1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
//! HierarchyService — application port over `HierarchyRepository`.
//!
//! Read-only ancestor-chain lookup for the three hierarchical entities. No business rules — the
//! service exists so the presentation layer depends on an application service, not a domain port
//! directly (per the 4-layer convention).
//!
//! Tenancy (ADR-0029): the `company_id` param is the legacy twin — kept so unstripped callers
//! compile and run unchanged; the adapter keys no statement on it and the composing service's
//! tenancy decorator scopes the read.
use std::sync::Arc;
use uuid::Uuid;
use crate::domain::repositories::hierarchy_repository::{
HierarchyNode, HierarchyRepository, HierarchyTable,
};
#[derive(Clone)]
pub struct HierarchyService {
repo: Arc<dyn HierarchyRepository>,
}
impl HierarchyService {
pub fn new(repo: Arc<dyn HierarchyRepository>) -> Self {
Self { repo }
}
/// Ancestor chain root → `id` for the given entity kind.
pub async fn ancestors(
&self,
table: HierarchyTable,
id: Uuid,
) -> anyhow::Result<Vec<HierarchyNode>> {
self.repo.ancestors(table, id).await
}
}