email/imap/
error.rs

1use std::{any::Any, collections::HashSet, result};
2
3use imap_client::{
4    client::tokio::ClientError,
5    imap_next::{
6        client::Error as ClientFlowError,
7        imap_types::{auth::AuthMechanism, error::ValidationError},
8    },
9    stream::Error as StreamError,
10};
11use thiserror::Error;
12use tokio::task::JoinError;
13
14use crate::{account, AnyBoxedError, AnyError};
15
16/// The global `Result` alias of the module.
17pub type Result<T> = result::Result<T, Error>;
18
19/// The global `Error` enum of the module.
20#[derive(Debug, Error)]
21pub enum Error {
22    #[error("cannot build IMAP client: missing TLS provider")]
23    BuildTlsClientMissingProvider,
24    #[error("cannot build IMAP client")]
25    JoinClientError(#[source] JoinError),
26    #[error("cannot build IMAP client")]
27    BuildClientError(#[source] Box<Error>),
28    #[error("cannot connect to IMAP server {1}:{2} using TCP")]
29    BuildInsecureClientError(#[source] ClientError, String, u16),
30    #[error("cannot connect to IMAP server {1}:{2} using STARTTLS")]
31    BuildStartTlsClientError(#[source] ClientError, String, u16),
32    #[error("cannot connect to IMAP server {1}:{2} using SSL/TLS")]
33    BuildTlsClientError(#[source] ClientError, String, u16),
34
35    #[error("cannot get imap password from global keyring")]
36    GetPasswdImapError(#[source] secret::Error),
37    #[error("cannot get imap password: password is empty")]
38    GetPasswdEmptyImapError,
39    #[error("cannot reset imap password")]
40    ResetPasswordError(#[source] account::Error),
41    #[error("cannot reset oauth secrets")]
42    ResetOAuthSecretsError(#[source] account::Error),
43    #[error("cannot refresh oauth access token")]
44    RefreshAccessTokenError(#[source] account::Error),
45    #[error("cannot get access token: {0}")]
46    AccessTokenNotAvailable(#[source] account::Error),
47    #[error("replacing unidentified to keyring failed: {0}")]
48    ReplacingUnidentifiedFailed(#[source] secret::Error),
49
50    #[error("cannot execute imap action after 3 retries")]
51    ExecuteActionRetryError(#[source] AnyBoxedError),
52    #[error("cannot execute imap action due to password authentication failure")]
53    ExecuteActionPasswordError(#[source] AnyBoxedError),
54    #[error("cannot execute imap action due to oauth authorization failure")]
55    ExecuteActionOAuthError(#[source] AnyBoxedError),
56
57    // ================ v2
58
59    // parse
60    #[error("cannot parse IMAP mailbox {1}")]
61    ParseMailboxError(#[source] ValidationError, String),
62    #[error("cannot find UID of appended IMAP message")]
63    FindAppendedMessageUidError,
64
65    #[error("cannot send IMAP request")]
66    RequestRetryError(#[source] ClientError),
67    #[error("cannot send IMAP request")]
68    ClientRetryError(#[source] ClientError),
69    #[error("cannot send IMAP request: request timed out after 3 attempts")]
70    RequestRetryTimeoutError,
71    #[error("cannot enable IMAP capability")]
72    EnableCapabilityError(#[source] ClientError),
73    #[error("cannot authenticate to IMAP server: no valid auth mechanism found")]
74    AuthenticateError(#[source] ClientError),
75    #[error("cannot authenticate to IMAP server using LOGIN mechanism")]
76    LoginError(#[source] ClientError),
77    #[error("cannot authenticate to IMAP server using SASL PLAIN mechanism")]
78    AuthenticatePlainError(#[source] ClientError),
79    #[error("cannot authenticate to IMAP server using SASL XOAUTH2 mechanism")]
80    AuthenticateXOauth2Error(#[source] ClientError),
81    #[error("cannot authenticate to IMAP server using SASL OAUTHBEARER mechanism")]
82    AuthenticateOAuthBearerError(#[source] ClientError),
83
84    #[error("cannot create IMAP mailbox")]
85    CreateMailboxError(#[source] ClientError),
86    #[error("cannot create IMAP mailbox: request timed out")]
87    CreateMailboxTimedOutError,
88
89    #[error("cannot select IMAP mailbox")]
90    SelectMailboxError(#[source] ClientError),
91    #[error("cannot select IMAP mailbox: request timed out")]
92    SelectMailboxTimedOutError,
93
94    #[error("cannot examine IMAP mailbox")]
95    ExamineMailboxError(#[source] ClientError),
96    #[error("cannot examine IMAP mailbox: request timed out")]
97    ExamineMailboxTimedOutError,
98
99    #[error("cannot list IMAP mailboxes")]
100    ListMailboxesError(#[source] ClientError),
101    #[error("cannot list IMAP mailboxes: request timed out")]
102    ListMailboxesTimedOutError,
103
104    #[error("cannot expunge selected IMAP mailbox")]
105    ExpungeMailboxError(#[source] ClientError),
106    #[error("cannot expunge selected IMAP mailbox: request timed out")]
107    ExpungeMailboxTimedOutError,
108
109    #[error("cannot delete IMAP mailbox")]
110    DeleteMailboxError(#[source] ClientError),
111    #[error("cannot delete IMAP mailbox: request timed out")]
112    DeleteMailboxTimedOutError,
113
114    #[error("cannot fetch IMAP messages")]
115    FetchMessagesError(#[source] ClientError),
116    #[error("cannot fetch IMAP messages: request timed out")]
117    FetchMessagesTimedOutError,
118
119    #[error("cannot thread IMAP messages")]
120    ThreadMessagesError(#[source] ClientError),
121    #[error("cannot thread IMAP messages: request timed out")]
122    ThreadMessagesTimedOutError,
123
124    #[error("cannot store IMAP flag(s)")]
125    StoreFlagsError(#[source] ClientError),
126    #[error("cannot store IMAP flag(s): request timed out")]
127    StoreFlagsTimedOutError,
128    #[error("cannot add IMAP message")]
129    AddMessageError(#[source] ClientError),
130    #[error("cannot add IMAP message: request timed out")]
131    AddMessageTimedOutError,
132    #[error("cannot copy IMAP message(s)")]
133    CopyMessagesError(#[source] ClientError),
134    #[error("cannot copy IMAP message(s): request timed out")]
135    CopyMessagesTimedOutError,
136    #[error("cannot move IMAP message(s)")]
137    MoveMessagesError(#[source] ClientError),
138    #[error("cannot move IMAP message(s): request timed out")]
139    MoveMessagesTimedOutError,
140    #[error("cannot execute no-operation")]
141    NoOpError(#[source] ClientError),
142    #[error("cannot execute no-operation: request timed out")]
143    NoOpTimedOutError,
144
145    #[error("cannot exchange IMAP client/server ids")]
146    ExchangeIdsError(#[source] ClientError),
147    #[error("cannot search IMAP messages")]
148    SearchMessagesError(#[source] ClientError),
149    #[error("cannot sort IMAP messages")]
150    SortMessagesError(#[source] ClientError),
151    #[error("cannot sort IMAP envelope UIDs")]
152    SortUidsError(#[source] ClientError),
153    #[error("cannot sort IMAP envelope UIDs: request timed out")]
154    SortUidsTimedOutError,
155    #[error("cannot search IMAP envelope UIDs")]
156    SearchUidsError(#[source] ClientError),
157    #[error("cannot search IMAP envelope UIDs: request timed out")]
158    SearchUidsTimedOutError,
159    #[error("cannot start IMAP IDLE mode")]
160    StartIdleError(#[source] StreamError<ClientFlowError>),
161    #[error("cannot stop IMAP IDLE mode")]
162    StopIdleError(#[source] StreamError<ClientFlowError>),
163    #[error("IMAP IDLE mode interrupted")]
164    IdleInterruptedError,
165    #[error("cannot append IMAP message")]
166    AppendMessageError(#[source] ClientError),
167    #[error("cannot execute IMAP no-op after append")]
168    ExecuteNoOpAfterAppendError(#[source] ClientError),
169    #[error("cannot execute IMAP check after append")]
170    ExecuteCheckAfterAppendError(#[source] ClientError),
171    #[error("cannot execute IMAP no-op")]
172    ExecuteNoOpError(#[source] ClientError),
173
174    // flow
175    #[error("cannot receive IMAP greeting")]
176    ReceiveGreetingTaskError(#[source] ClientFlowError),
177    #[error("login not supported")]
178    LoginNotSupportedError,
179    #[error("plain authentication not supported (available: {0:?})")]
180    AuthenticatePlainNotSupportedError(HashSet<AuthMechanism<'static>>),
181    #[error("XOAuth2 authentication not supported (available: {0:?})")]
182    AuthenticateXOAuth2NotSupportedError(HashSet<AuthMechanism<'static>>),
183    #[error("OAuthBearer authentication not supported (available: {0:?})")]
184    AuthenticateOAuthBearerNotSupportedError(HashSet<AuthMechanism<'static>>),
185
186    // tasks
187    #[error("cannot execute IMAP action")]
188    ExecuteActionV2Error(#[source] AnyBoxedError),
189
190    #[error("cannot build IMAP session after {0} attempts, aborting")]
191    BuildSessionRetryError(u8),
192}
193
194impl AnyError for Error {
195    fn as_any(&self) -> &dyn Any {
196        self
197    }
198}
199
200impl From<Error> for AnyBoxedError {
201    fn from(err: Error) -> Self {
202        Box::new(err)
203    }
204}