1use crate::{
2 build_graph::BuildGraphError,
3 compile::CompileError,
4 infrastructure::{CommandError, ConsoleError, DatabaseError, FileError},
5 ir::Build,
6 module_dependency::ModuleDependencyError,
7 parse::ParseError,
8};
9use alloc::sync::Arc;
10use core::{
11 error::Error,
12 fmt::{self, Display, Formatter},
13};
14use tokio::{io, sync::AcquireError, task::JoinError};
15
16#[derive(Clone, Debug, Eq, PartialEq)]
18pub enum BuildError {
19 Acquire(String),
21 Build,
23 BuildGraph(BuildGraphError),
25 Command(CommandError),
27 Compile(CompileError),
29 Console(ConsoleError),
31 Database(DatabaseError),
33 DefaultOutputNotFound(Arc<str>),
35 DynamicDependencyNotFound(Arc<Build>),
37 File(FileError),
39 FileNotFound(String),
41 InputNotBuilt(String),
43 InputNotFound(String),
45 Io(String),
47 Join(String),
49 ModuleDependency(ModuleDependencyError),
51 OutputNotFound(String),
53 Parse(ParseError),
55}
56
57impl Error for BuildError {}
58
59impl Display for BuildError {
60 fn fmt(&self, formatter: &mut Formatter) -> fmt::Result {
61 match self {
62 Self::Acquire(message) | Self::Io(message) | Self::Join(message) => {
63 write!(formatter, "{message}")
64 }
65 Self::Build => write!(formatter, "build failed"),
66 Self::Command(error) => write!(formatter, "{error}"),
67 Self::Compile(error) => write!(formatter, "{error}"),
68 Self::Console(error) => write!(formatter, "{error}"),
69 Self::Database(error) => write!(formatter, "{error}"),
70 Self::DefaultOutputNotFound(output) => {
71 write!(formatter, "default output \"{output}\" not found")
72 }
73 Self::DynamicDependencyNotFound(build) => {
74 write!(
75 formatter,
76 "outputs {} not found in dynamic dependency file {}",
77 build.outputs().join(", "),
78 build.dynamic_module().unwrap()
79 )
80 }
81 Self::File(error) => write!(formatter, "{error}"),
82 Self::FileNotFound(path) => write!(formatter, "file \"{path}\" not found"),
83 Self::InputNotBuilt(input) => {
84 write!(formatter, "input \"{input}\" not built yet")
85 }
86 Self::InputNotFound(input) => {
87 write!(formatter, "input \"{input}\" not found")
88 }
89 Self::ModuleDependency(error) => {
90 write!(formatter, "{error}")
91 }
92 Self::OutputNotFound(output) => {
93 write!(formatter, "output \"{output}\" not found")
94 }
95 Self::Parse(error) => write!(formatter, "{error}"),
96 Self::BuildGraph(error) => write!(formatter, "{error}"),
97 }
98 }
99}
100
101impl From<AcquireError> for BuildError {
102 fn from(error: AcquireError) -> Self {
103 Self::Acquire(error.to_string())
104 }
105}
106
107impl From<CommandError> for BuildError {
108 fn from(error: CommandError) -> Self {
109 Self::Command(error)
110 }
111}
112
113impl From<CompileError> for BuildError {
114 fn from(error: CompileError) -> Self {
115 Self::Compile(error)
116 }
117}
118
119impl From<ConsoleError> for BuildError {
120 fn from(error: ConsoleError) -> Self {
121 Self::Console(error)
122 }
123}
124
125impl From<DatabaseError> for BuildError {
126 fn from(error: DatabaseError) -> Self {
127 Self::Database(error)
128 }
129}
130
131impl From<FileError> for BuildError {
132 fn from(error: FileError) -> Self {
133 Self::File(error)
134 }
135}
136
137impl From<io::Error> for BuildError {
138 fn from(error: io::Error) -> Self {
139 Self::Io(error.to_string())
140 }
141}
142
143impl From<JoinError> for BuildError {
144 fn from(error: JoinError) -> Self {
145 Self::Join(error.to_string())
146 }
147}
148
149impl From<ModuleDependencyError> for BuildError {
150 fn from(error: ModuleDependencyError) -> Self {
151 Self::ModuleDependency(error)
152 }
153}
154
155impl From<ParseError> for BuildError {
156 fn from(error: ParseError) -> Self {
157 Self::Parse(error)
158 }
159}
160
161impl From<BuildGraphError> for BuildError {
162 fn from(error: BuildGraphError) -> Self {
163 Self::BuildGraph(error)
164 }
165}
166
167#[cfg(test)]
168mod tests {
169 use super::*;
170
171 #[test]
172 fn display_acquire() {
173 assert_eq!(
174 BuildError::Acquire("semaphore closed".into()).to_string(),
175 "semaphore closed"
176 );
177 }
178
179 #[test]
180 fn display_io() {
181 assert_eq!(
182 BuildError::Io("permission denied".into()).to_string(),
183 "permission denied"
184 );
185 }
186
187 #[test]
188 fn display_join() {
189 assert_eq!(
190 BuildError::Join("task cancelled".into()).to_string(),
191 "task cancelled"
192 );
193 }
194}