trakt-core 0.2.1

Core library for trakt-rs
Documentation
//! Error types for the API.

use http::{header::InvalidHeaderValue, StatusCode};

#[derive(Debug, thiserror::Error)]
pub enum ApiError {
    #[error("Bad Request")]
    BadRequest,
    #[error("Unauthorized")]
    Unauthorized,
    #[error("Forbidden")]
    Forbidden,
    #[error("Not Found")]
    NotFound,
    #[error("Resource Already Exists")]
    AlreadyExists,
    #[error("Resource Expired")]
    Expired,
    #[error("Invalid Content-Type")]
    InvalidContentType,
    #[error("User denied the request")]
    Denied,
    #[error("Account limit exceeded")]
    AccountLimitExceeded,
    #[error("Validation Error")]
    ValidationError,
    #[error("Locked User Account")]
    LockedUserAccount,
    #[error("VIP Only")]
    VipOnly,
    #[error("Rate Limit Exceeded")]
    RateLimitExceeded,
    #[error("Server Error")]
    ServerError,
    #[error("Service Unavailable")]
    ServiceUnavailable,
    #[error("Cloudflare Error")]
    CloudflareError,
    #[error("Unknown Error: {0}")]
    UnknownError(StatusCode),
}

impl From<StatusCode> for ApiError {
    fn from(value: StatusCode) -> Self {
        match value.as_u16() {
            400 => Self::BadRequest,
            401 => Self::Unauthorized,
            403 => Self::Forbidden,
            404 => Self::NotFound,
            409 => Self::AlreadyExists,
            410 => Self::Expired,
            412 => Self::InvalidContentType,
            418 => Self::Denied,
            420 => Self::AccountLimitExceeded,
            422 => Self::ValidationError,
            423 => Self::LockedUserAccount,
            426 => Self::VipOnly,
            429 => Self::RateLimitExceeded,
            500 => Self::ServerError,
            502..=504 => Self::ServiceUnavailable,
            520..=522 => Self::CloudflareError,
            _ => Self::UnknownError(value),
        }
    }
}

/// Error type for converting a request into an HTTP request.
#[derive(Debug, thiserror::Error)]
pub enum IntoHttpError {
    #[error("JSON Error: {0}")]
    Json(#[from] serde_json::Error),
    #[error("Invalid Header Value: {0}")]
    Header(#[from] InvalidHeaderValue),
    #[error("HTTP Error: {0}")]
    Http(#[from] http::Error),
    #[error("Url params error: {0}")]
    UrlParams(#[from] UrlError),
    #[error("Query params error: {0}")]
    QueryParams(#[from] serde_urlencoded::ser::Error),
    #[error("Missing oauth token")]
    MissingToken,
    #[error("Validation Error: {0}")]
    Validation(String),
}

#[derive(Debug, thiserror::Error)]
pub enum FromHttpError {
    #[error("API Error: {0}")]
    Api(#[from] ApiError),
    #[error("Deserialize Error: {0}")]
    Deserialize(#[from] DeserializeError),
}

#[derive(Debug, thiserror::Error)]
pub enum DeserializeError {
    #[error("JSON Error: {0}")]
    Json(#[from] serde_json::Error),
    #[error("Header Error: {0}")]
    Header(#[from] HeaderError),
    #[error("Integer Parse Error: {0}")]
    ParseInt(#[from] std::num::ParseIntError),
}

#[derive(Debug, thiserror::Error)]
pub enum HeaderError {
    #[error("Invalid Header Value: {0}")]
    ToStrError(#[from] http::header::ToStrError),
    #[error("Missing Header")]
    MissingHeader,
}

#[derive(Debug, PartialEq, Eq, thiserror::Error)]
pub enum UrlError {
    #[error("{0}")]
    Message(String),
    #[error("Top level serializer only supports structs")]
    TopLevel,
    #[error("Invalid endpoint")]
    InvalidEndpoint,
    #[error("Value not supported")]
    ValueNotSupported,
    #[error("Key not found: {0}")]
    KeyNotFound(&'static str),
    #[error("Unfilled field: {0}")]
    UnfilledField(String),
}

impl serde::ser::Error for UrlError {
    fn custom<T: std::fmt::Display>(msg: T) -> Self {
        Self::Message(msg.to_string())
    }
}