busbar_sf_agentscript/graph/
error.rs1use super::nodes::Span;
4use thiserror::Error;
5
6#[derive(Debug, Error)]
8pub enum GraphBuildError {
9 #[error("Missing required element: {element}")]
11 MissingElement { element: String },
12
13 #[error("Duplicate {kind} definition: {name} at {span:?}")]
15 DuplicateDefinition {
16 kind: String,
17 name: String,
18 span: Span,
19 },
20}
21
22#[derive(Debug, Clone, PartialEq, Eq)]
24pub enum ValidationError {
25 UnresolvedReference {
27 reference: String,
29 namespace: String,
31 span: Span,
33 context: String,
35 },
36
37 CycleDetected {
39 path: Vec<String>,
41 },
42
43 UnreachableTopic {
45 name: String,
47 span: Span,
49 },
50
51 UnusedActionDef {
53 name: String,
55 topic: String,
57 span: Span,
59 },
60
61 UnusedVariable {
63 name: String,
65 span: Span,
67 },
68
69 UninitializedVariable {
71 name: String,
73 read_span: Span,
75 },
76}
77
78impl ValidationError {
79 pub fn span(&self) -> Option<Span> {
81 match self {
82 ValidationError::UnresolvedReference { span, .. }
83 | ValidationError::UnreachableTopic { span, .. }
84 | ValidationError::UnusedActionDef { span, .. }
85 | ValidationError::UnusedVariable { span, .. }
86 | ValidationError::UninitializedVariable {
87 read_span: span, ..
88 } => Some(*span),
89 ValidationError::CycleDetected { .. } => None,
90 }
91 }
92
93 pub fn message(&self) -> String {
95 match self {
96 ValidationError::UnresolvedReference {
97 reference, context, ..
98 } => {
99 format!("Unresolved reference '{}' in {}", reference, context)
100 }
101 ValidationError::CycleDetected { path } => {
102 format!("Cycle detected in topic transitions: {}", path.join(" -> "))
103 }
104 ValidationError::UnreachableTopic { name, .. } => {
105 format!("Topic '{}' is unreachable from start_agent", name)
106 }
107 ValidationError::UnusedActionDef { name, topic, .. } => {
108 format!("Action '{}' in topic '{}' is never invoked", name, topic)
109 }
110 ValidationError::UnusedVariable { name, .. } => {
111 format!("Variable '{}' is never read", name)
112 }
113 ValidationError::UninitializedVariable { name, .. } => {
114 format!("Variable '{}' is read but never written", name)
115 }
116 }
117 }
118
119 pub fn is_unresolved_reference(&self) -> bool {
121 matches!(self, ValidationError::UnresolvedReference { .. })
122 }
123
124 pub fn is_cycle(&self) -> bool {
126 matches!(self, ValidationError::CycleDetected { .. })
127 }
128
129 pub fn is_unused(&self) -> bool {
131 matches!(
132 self,
133 ValidationError::UnusedActionDef { .. } | ValidationError::UnusedVariable { .. }
134 )
135 }
136}