1use crate::util::progress::ProgressSendError;
4
5#[derive(Debug, thiserror::Error)]
7pub enum GetError {
8 #[error("Hash not found")]
10 NotFound(#[source] anyhow::Error),
11 #[error("Remote has reset the connection")]
13 RemoteReset(#[source] anyhow::Error),
14 #[error("Remote behaved in a non-compliant way")]
16 NoncompliantNode(#[source] anyhow::Error),
17
18 #[error("A network or IO operation failed")]
20 Io(#[source] anyhow::Error),
21
22 #[error("Our download request is invalid")]
24 BadRequest(#[source] anyhow::Error),
25 #[error("Operation failed on the local node")]
27 LocalFailure(#[source] anyhow::Error),
28}
29
30impl From<ProgressSendError> for GetError {
31 fn from(value: ProgressSendError) -> Self {
32 Self::LocalFailure(value.into())
33 }
34}
35
36impl From<quinn::ConnectionError> for GetError {
37 fn from(value: quinn::ConnectionError) -> Self {
38 match value {
40 e @ quinn::ConnectionError::VersionMismatch => {
41 GetError::NoncompliantNode(e.into())
44 }
45 e @ quinn::ConnectionError::TransportError(_) => {
46 GetError::NoncompliantNode(e.into())
49 }
50 e @ quinn::ConnectionError::ConnectionClosed(_) => {
51 GetError::Io(e.into())
54 }
55 e @ quinn::ConnectionError::ApplicationClosed(_) => {
56 GetError::Io(e.into())
59 }
60 e @ quinn::ConnectionError::Reset => {
61 GetError::RemoteReset(e.into())
63 }
64 e @ quinn::ConnectionError::TimedOut => {
65 GetError::Io(e.into())
67 }
68 e @ quinn::ConnectionError::LocallyClosed => {
69 GetError::Io(e.into())
72 }
73 }
74 }
75}
76
77impl From<quinn::ReadError> for GetError {
78 fn from(value: quinn::ReadError) -> Self {
79 match value {
80 e @ quinn::ReadError::Reset(_) => GetError::RemoteReset(e.into()),
81 quinn::ReadError::ConnectionLost(conn_error) => conn_error.into(),
82 quinn::ReadError::UnknownStream
83 | quinn::ReadError::IllegalOrderedRead
84 | quinn::ReadError::ZeroRttRejected => {
85 GetError::Io(value.into())
87 }
88 }
89 }
90}
91
92impl From<quinn::WriteError> for GetError {
93 fn from(value: quinn::WriteError) -> Self {
94 match value {
95 e @ quinn::WriteError::Stopped(_) => GetError::RemoteReset(e.into()),
96 quinn::WriteError::ConnectionLost(conn_error) => conn_error.into(),
97 quinn::WriteError::UnknownStream | quinn::WriteError::ZeroRttRejected => {
98 GetError::Io(value.into())
100 }
101 }
102 }
103}
104
105impl From<crate::get::fsm::ConnectedNextError> for GetError {
106 fn from(value: crate::get::fsm::ConnectedNextError) -> Self {
107 use crate::get::fsm::ConnectedNextError::*;
108 match value {
109 e @ PostcardSer(_) => {
110 GetError::BadRequest(e.into())
112 }
113 e @ RequestTooBig => {
114 GetError::BadRequest(e.into())
116 }
117 Write(e) => e.into(),
118 e @ Io(_) => {
119 GetError::Io(e.into())
121 }
122 }
123 }
124}
125
126impl From<crate::get::fsm::AtBlobHeaderNextError> for GetError {
127 fn from(value: crate::get::fsm::AtBlobHeaderNextError) -> Self {
128 use crate::get::fsm::AtBlobHeaderNextError::*;
129 match value {
130 e @ NotFound => {
131 GetError::NotFound(e.into())
134 }
135 Read(e) => e.into(),
136 e @ Io(_) => {
137 GetError::Io(e.into())
139 }
140 }
141 }
142}
143
144impl From<crate::get::fsm::DecodeError> for GetError {
145 fn from(value: crate::get::fsm::DecodeError) -> Self {
146 use crate::get::fsm::DecodeError::*;
147
148 match value {
149 e @ NotFound => GetError::NotFound(e.into()),
150 e @ ParentNotFound(_) => GetError::NotFound(e.into()),
151 e @ LeafNotFound(_) => GetError::NotFound(e.into()),
152 e @ ParentHashMismatch(_) => {
153 GetError::NoncompliantNode(e.into())
156 }
157 e @ LeafHashMismatch(_) => {
158 GetError::NoncompliantNode(e.into())
161 }
162 Read(e) => e.into(),
163 Io(e) => e.into(),
164 }
165 }
166}
167
168impl From<std::io::Error> for GetError {
169 fn from(value: std::io::Error) -> Self {
170 GetError::Io(value.into())
173 }
174}