russel 0.0.3

A simple static site builder I built for myself.
Documentation
//! Error types for the application

use thiserror::Error;

/// Main error type for the application
#[derive(Debug, Error)]
pub enum RussError {
    /// File system errors
    #[error("File system error: {0}")]
    Io(#[from] std::io::Error),

    /// Configuration related errors
    #[error("Configuration error: {message}")]
    Config {
        message: String,
        #[source]
        source: Option<Box<dyn std::error::Error + Send + Sync>>,
    },

    /// Build process errors
    #[error("Build error: {message}")]
    Build {
        message: String,
        #[source]
        source: Option<Box<dyn std::error::Error + Send + Sync>>,
    },

    /// Development server errors
    #[error("Development server error: {message}")]
    Dev {
        message: String,
        #[source]
        source: Option<Box<dyn std::error::Error + Send + Sync>>,
    },

    /// Resource generation errors
    #[error("Generation error: {message}")]
    Generate {
        message: String,
        #[source]
        source: Option<Box<dyn std::error::Error + Send + Sync>>,
    },

    /// Project creation errors
    #[error("Project creation error: {message}")]
    NewProject {
        message: String,
        #[source]
        source: Option<Box<dyn std::error::Error + Send + Sync>>,
    },

    /// Template rendering errors
    #[error("Template error: {message}")]
    Template {
        message: String,
        #[source]
        source: Option<Box<dyn std::error::Error + Send + Sync>>,
    },

    /// Validation errors
    #[error("Validation error: {message}")]
    Validation { message: String },

    /// Generic error with message
    #[error("{0}")]
    Other(String),
}

/// Helper functions for creating specific error variants
impl RussError {
    /// Create a new config error
    pub fn config<S: Into<String>>(message: S) -> Self {
        RussError::Config {
            message: message.into(),
            source: None,
        }
    }

    /// Create a new config error with source
    pub fn config_with_source<S, E>(message: S, source: E) -> Self
    where
        S: Into<String>,
        E: std::error::Error + Send + Sync + 'static,
    {
        RussError::Config {
            message: message.into(),
            source: Some(Box::new(source)),
        }
    }

    /// Create a new build error
    pub fn build<S: Into<String>>(message: S) -> Self {
        RussError::Build {
            message: message.into(),
            source: None,
        }
    }

    /// Create a new build error with source
    pub fn build_with_source<S, E>(message: S, source: E) -> Self
    where
        S: Into<String>,
        E: std::error::Error + Send + Sync + 'static,
    {
        RussError::Build {
            message: message.into(),
            source: Some(Box::new(source)),
        }
    }

    /// Create a new development error
    pub fn dev<S: Into<String>>(message: S) -> Self {
        RussError::Dev {
            message: message.into(),
            source: None,
        }
    }

    /// Create a new generation error
    pub fn generate<S: Into<String>>(message: S) -> Self {
        RussError::Generate {
            message: message.into(),
            source: None,
        }
    }

    /// Create a new project creation error
    pub fn new_project<S: Into<String>>(message: S) -> Self {
        RussError::NewProject {
            message: message.into(),
            source: None,
        }
    }

    /// Create a new project creation error with source
    pub fn new_project_with_source<S, E>(message: S, source: E) -> Self
    where
        S: Into<String>,
        E: std::error::Error + Send + Sync + 'static,
    {
        RussError::NewProject {
            message: message.into(),
            source: Some(Box::new(source)),
        }
    }

    /// Create a new validation error
    pub fn validation<S: Into<String>>(message: S) -> Self {
        RussError::Validation {
            message: message.into(),
        }
    }
}

// impl ToString for RussError {
//     fn to_string(&self) -> String {
//         match self {
//             RussError::Io(error) => &error.to_string(),
//             RussError::Config { message, source } => message,
//             RussError::Build { message, source } => message,
//             RussError::Dev { message, source } => message,
//             RussError::Generate { message, source } => message,
//             RussError::NewProject { message, source } => message,
//             RussError::Template { message, source } => message,
//             RussError::Validation { message } => message,
//             RussError::Other(_) => &"Failed to run command".to_string(),
//         }
//         .to_string()
//     }
// }

/// Custom result type alias for the application
pub type Result<T> = std::result::Result<T, RussError>;