Skip to main content

goud_engine/assets/loader/
error.rs

1//! Asset loading error types.
2
3use std::error::Error;
4use std::fmt;
5use std::path::Path;
6
7/// Errors that can occur during asset loading.
8#[derive(Debug, Clone)]
9pub enum AssetLoadError {
10    /// The asset file was not found.
11    NotFound {
12        /// The path to the asset that was not found.
13        path: String,
14    },
15
16    /// Failed to read the asset file.
17    IoError {
18        /// The path to the asset that failed to load.
19        path: String,
20        /// The I/O error message.
21        message: String,
22    },
23
24    /// Failed to decode/parse the asset data.
25    DecodeFailed(
26        /// The decoding error message.
27        String,
28    ),
29
30    /// The asset format is not supported.
31    UnsupportedFormat {
32        /// The unsupported file extension.
33        extension: String,
34    },
35
36    /// A dependency asset failed to load.
37    DependencyFailed {
38        /// The path of the asset with the failed dependency.
39        asset_path: String,
40        /// The path of the dependency that failed to load.
41        dependency_path: String,
42        /// The error message from the dependency failure.
43        message: String,
44    },
45
46    /// A custom loader-specific error occurred.
47    Custom(
48        /// The custom error message.
49        String,
50    ),
51}
52
53impl AssetLoadError {
54    /// Creates a NotFound error from a path.
55    pub fn not_found(path: impl AsRef<Path>) -> Self {
56        Self::NotFound {
57            path: path.as_ref().display().to_string(),
58        }
59    }
60
61    /// Creates an IoError from a path and error.
62    pub fn io_error(path: impl AsRef<Path>, error: impl Error) -> Self {
63        Self::IoError {
64            path: path.as_ref().display().to_string(),
65            message: error.to_string(),
66        }
67    }
68
69    /// Creates a DecodeFailed error from a message.
70    pub fn decode_failed(message: impl Into<String>) -> Self {
71        Self::DecodeFailed(message.into())
72    }
73
74    /// Creates an UnsupportedFormat error from an extension.
75    pub fn unsupported_format(extension: impl Into<String>) -> Self {
76        Self::UnsupportedFormat {
77            extension: extension.into(),
78        }
79    }
80
81    /// Creates a DependencyFailed error.
82    pub fn dependency_failed(
83        asset_path: impl Into<String>,
84        dependency_path: impl Into<String>,
85        message: impl Into<String>,
86    ) -> Self {
87        Self::DependencyFailed {
88            asset_path: asset_path.into(),
89            dependency_path: dependency_path.into(),
90            message: message.into(),
91        }
92    }
93
94    /// Creates a Custom error from a message.
95    pub fn custom(message: impl Into<String>) -> Self {
96        Self::Custom(message.into())
97    }
98
99    /// Returns true if this is a NotFound error.
100    pub fn is_not_found(&self) -> bool {
101        matches!(self, Self::NotFound { .. })
102    }
103
104    /// Returns true if this is an IoError.
105    pub fn is_io_error(&self) -> bool {
106        matches!(self, Self::IoError { .. })
107    }
108
109    /// Returns true if this is a DecodeFailed error.
110    pub fn is_decode_failed(&self) -> bool {
111        matches!(self, Self::DecodeFailed(_))
112    }
113
114    /// Returns true if this is an UnsupportedFormat error.
115    pub fn is_unsupported_format(&self) -> bool {
116        matches!(self, Self::UnsupportedFormat { .. })
117    }
118
119    /// Returns true if this is a DependencyFailed error.
120    pub fn is_dependency_failed(&self) -> bool {
121        matches!(self, Self::DependencyFailed { .. })
122    }
123
124    /// Returns true if this is a Custom error.
125    pub fn is_custom(&self) -> bool {
126        matches!(self, Self::Custom(_))
127    }
128}
129
130impl fmt::Display for AssetLoadError {
131    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
132        match self {
133            Self::NotFound { path } => write!(f, "Asset not found: {}", path),
134            Self::IoError { path, message } => {
135                write!(f, "I/O error loading asset '{}': {}", path, message)
136            }
137            Self::DecodeFailed(msg) => write!(f, "Failed to decode asset: {}", msg),
138            Self::UnsupportedFormat { extension } => {
139                write!(f, "Unsupported asset format: '.{}'", extension)
140            }
141            Self::DependencyFailed {
142                asset_path,
143                dependency_path,
144                message,
145            } => write!(
146                f,
147                "Dependency '{}' of asset '{}' failed to load: {}",
148                dependency_path, asset_path, message
149            ),
150            Self::Custom(msg) => write!(f, "Asset loading error: {}", msg),
151        }
152    }
153}
154
155impl Error for AssetLoadError {}