1use std::error;
4use std::fmt;
5
6use serde::Deserialize;
7
8use crate::ErrorResponse;
9
10#[derive(Debug, Deserialize)]
11#[non_exhaustive]
12#[serde(rename_all = "snake_case")]
13pub enum ErrorType {
14 RequestError,
15 ApiError,
16}
17
18#[derive(Debug, Deserialize)]
19pub struct ValidationError {
20 pub field: String,
21 pub message: String,
22}
23
24#[derive(Debug, Deserialize)]
25pub struct PaddleError {
26 #[serde(rename = "type")]
27 pub error_type: ErrorType,
28 pub code: String,
29 pub detail: String,
30 pub documentation_url: String,
31 pub errors: Option<Vec<ValidationError>>,
32}
33
34#[derive(Debug)]
35pub enum Error {
36 Request(reqwest::Error),
37 Url(url::ParseError),
38 Paddle(ErrorResponse),
39 QueryString(serde_qs::Error),
40}
41
42impl fmt::Display for Error {
43 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
44 match self {
45 Self::Request(err) => write!(f, "Request error: {}", err),
46 Self::Url(err) => write!(f, "URL error: {}", err),
47 Self::Paddle(err) => write!(f, "Paddle error: {}", err.error.detail),
48 Self::QueryString(err) => write!(f, "Query string error: {}", err),
49 }
50 }
51}
52
53impl error::Error for Error {
54 fn source(&self) -> Option<&(dyn error::Error + 'static)> {
55 match self {
56 Self::Request(err) => Some(err),
57 Self::Url(err) => Some(err),
58 Self::Paddle(_) => None,
59 Self::QueryString(err) => Some(err),
60 }
61 }
62}
63
64impl From<reqwest::Error> for Error {
65 fn from(err: reqwest::Error) -> Self {
66 Self::Request(err)
67 }
68}
69
70impl From<url::ParseError> for Error {
71 fn from(err: url::ParseError) -> Self {
72 Self::Url(err)
73 }
74}
75
76impl From<serde_qs::Error> for Error {
77 fn from(err: serde_qs::Error) -> Self {
78 Self::QueryString(err)
79 }
80}