1use std::time::Duration;
2
3pub type Result<T> = std::result::Result<T, Error>;
5
6#[derive(Clone, Debug, Eq, PartialEq)]
9pub struct RequestContext {
10 pub url: String,
11}
12
13impl std::fmt::Display for RequestContext {
14 fn fmt(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
15 formatter.write_str(&self.url)
16 }
17}
18
19#[derive(Clone, Copy, Debug, Eq, PartialEq)]
21pub enum ApiErrorKind {
22 Authentication,
23 PlanRestricted,
24 RateLimited,
25 HttpStatus,
26 Provider,
27}
28
29#[derive(Debug, thiserror::Error)]
33#[error("{message}")]
34pub struct JsonDecodeError {
35 pub message: String,
36 pub line: usize,
37 pub column: usize,
38}
39
40#[derive(Debug, thiserror::Error)]
42pub enum Error {
43 #[error("invalid SDK configuration: {reason}")]
44 Configuration { reason: String },
45 #[error("cannot construct GET {request}: {source}")]
46 Request {
47 request: RequestContext,
48 #[source]
49 source: reqwest::Error,
50 },
51 #[error("GET {request} failed in transport: {source}")]
52 Transport {
53 request: RequestContext,
54 #[source]
55 source: reqwest::Error,
56 },
57 #[error("GET {request} returned HTTP {status}, but its body could not be read: {source}")]
58 ResponseBody {
59 request: RequestContext,
60 status: u16,
61 #[source]
62 source: reqwest::Error,
63 },
64 #[error("GET {request} failed ({kind:?}, HTTP {status}): {body}")]
65 Api {
66 request: RequestContext,
67 kind: ApiErrorKind,
68 status: u16,
69 body: String,
70 retry_after: Option<Duration>,
71 },
72 #[error("GET {request} returned invalid JSON/schema (HTTP {status}): {source}; body: {body}")]
73 Decode {
74 request: RequestContext,
75 status: u16,
76 body: String,
77 #[source]
78 source: JsonDecodeError,
79 },
80 #[error("GET {request} returned non-UTF-8 text (HTTP {status}): {source}")]
81 Encoding {
82 request: RequestContext,
83 status: u16,
84 #[source]
85 source: std::str::Utf8Error,
86 },
87 #[error(
88 "GET {request} returned an invalid {header} header (HTTP {status}): {reason}; body: {body}"
89 )]
90 ResponseHeader {
91 request: RequestContext,
92 status: u16,
93 header: &'static str,
94 reason: String,
95 body: String,
96 },
97}