Skip to main content

treetop_bundle/
error.rs

1use crate::Diagnostic;
2use std::path::PathBuf;
3
4/// Errors produced while compiling or decoding a bundle.
5#[derive(Debug, thiserror::Error)]
6#[non_exhaustive]
7pub enum BundleError {
8    /// The input was readable but failed content validation.
9    #[error("bundle validation failed")]
10    Validation(Vec<Diagnostic>),
11    /// A manifest could not be decoded.
12    #[error("failed to parse manifest {path}: {message}")]
13    Manifest { path: PathBuf, message: String },
14    /// JSON input could not be decoded.
15    #[error("failed to parse JSON {path}: {message}")]
16    Json { path: String, message: String },
17    /// A filesystem operation failed.
18    #[error("filesystem error for {path}: {source}")]
19    Io {
20        path: PathBuf,
21        #[source]
22        source: std::io::Error,
23    },
24    /// A key could not be loaded or decoded.
25    #[error("key error: {0}")]
26    Key(String),
27    /// Archive framing or structure is invalid.
28    #[error("invalid bundle archive: {0}")]
29    Archive(String),
30    /// A configured size limit was exceeded.
31    #[error("bundle {kind} size exceeds the configured limit of {limit} bytes")]
32    SizeLimit { kind: &'static str, limit: usize },
33    /// Serialization of an internally validated value failed.
34    #[error("serialization failed: {0}")]
35    Serialization(String),
36}
37
38impl BundleError {
39    /// Whether this error represents invalid user-controlled bundle content.
40    pub fn is_validation(&self) -> bool {
41        matches!(
42            self,
43            Self::Validation(_)
44                | Self::Manifest { .. }
45                | Self::Json { .. }
46                | Self::Archive(_)
47                | Self::SizeLimit { .. }
48        )
49    }
50
51    /// Return structured diagnostics when available.
52    pub fn diagnostics(&self) -> &[Diagnostic] {
53        match self {
54            Self::Validation(diagnostics) => diagnostics,
55            _ => &[],
56        }
57    }
58
59    pub(crate) fn io(path: impl Into<PathBuf>, source: std::io::Error) -> Self {
60        Self::Io {
61            path: path.into(),
62            source,
63        }
64    }
65}
66
67pub type Result<T> = std::result::Result<T, BundleError>;