Skip to main content

ds_api/
error.rs

1//! Unified error types
2//!
3//! This module uses `thiserror` to provide a unified `ApiError` type for the crate and exports a
4//! convenient `Result<T>` alias. The goal is to centralize disparate error sources (for example,
5//! `Box<dyn Error>`, `reqwest::Error`, `serde_json::Error`) into a single `ApiError` so that `?`
6//! conversions are simpler and error messages are more consistent.
7
8use thiserror::Error;
9
10/// Unified error type covering common error sources and including a generic string variant for easy conversions.
11#[derive(Error, Debug)]
12pub enum ApiError {
13    /// HTTP-level failure (useful when preserving status code and response body text).
14    #[error("HTTP error {status}: {text}")]
15    Http {
16        status: reqwest::StatusCode,
17        text: String,
18    },
19
20    /// Network/request error from reqwest.
21    #[error("Reqwest error: {0}")]
22    Reqwest(#[from] reqwest::Error),
23
24    /// JSON (serde_json) serialization/deserialization error.
25    #[error("JSON error: {0}")]
26    Json(#[from] serde_json::Error),
27
28    /// EventSource / SSE handling error (originating from the `eventsource-stream` crate).
29    /// Stored as a string to avoid depending on the concrete error type signature.
30    #[error("EventSource error: {0}")]
31    EventSource(String),
32
33    /// IO error (fallback).
34    #[error("IO error: {0}")]
35    Io(#[from] std::io::Error),
36
37    /// Generic string error (convenient for converting from `String` / `&str`).
38    #[error("{0}")]
39    Other(String),
40
41    /// Unknown or placeholder error.
42    #[error("Unknown error")]
43    Unknown,
44}
45
46/// Common `Result` alias used throughout the crate.
47pub type Result<T> = std::result::Result<T, ApiError>;
48
49impl ApiError {
50    /// Convenience constructor for the `Http` variant.
51    pub fn http_error(status: reqwest::StatusCode, text: impl Into<String>) -> Self {
52        ApiError::Http {
53            status,
54            text: text.into(),
55        }
56    }
57}
58
59impl From<&str> for ApiError {
60    fn from(s: &str) -> Self {
61        ApiError::Other(s.to_string())
62    }
63}
64
65impl From<String> for ApiError {
66    fn from(s: String) -> Self {
67        ApiError::Other(s)
68    }
69}