• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

aisk / rust-memcache / 8507933640

01 Apr 2024 12:18PM UTC coverage: 73.414%. First build
8507933640

Pull #142

github

web-flow
Merge 7693a28d8 into 9fa76e7db
Pull Request #142: :sparkles: add automatic typed json ser/de operations

0 of 3 new or added lines in 1 file covered. (0.0%)

1389 of 1892 relevant lines covered (73.41%)

6122.37 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

13.29
/src/error.rs
1
use r2d2;
2
use std::borrow::Cow;
3
use std::error;
4
use std::fmt;
5
use std::io;
6
use std::num;
7
use std::str;
8
use std::string;
9
use url;
10

11
/// Client-side errors
12
#[derive(Debug, PartialEq)]
×
13
pub enum ClientError {
14
    /// The key provided was longer than 250 bytes.
15
    KeyTooLong,
16
    /// The server returned an error prefixed with CLIENT_ERROR in response to a command.
17
    Error(Cow<'static, str>),
×
18
}
19

20
impl fmt::Display for ClientError {
21
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
×
22
        match self {
×
23
            ClientError::KeyTooLong => write!(f, "The provided key was too long."),
×
24
            ClientError::Error(s) => write!(f, "{}", s),
×
25
        }
26
    }
×
27
}
28

29
impl From<ClientError> for MemcacheError {
30
    fn from(err: ClientError) -> Self {
×
31
        MemcacheError::ClientError(err)
×
32
    }
×
33
}
34

35
/// Server-side errors
36
#[derive(Debug)]
×
37
pub enum ServerError {
38
    /// When using binary protocol, the server returned magic byte other
39
    /// than 0x81 in the response packet.
40
    BadMagic(u8),
×
41
    /// The client did not expect this response from the server.
42
    BadResponse(Cow<'static, str>),
×
43
    /// The server returned an error prefixed with SERVER_ERROR in response to a command.
44
    Error(String),
×
45
}
46

47
impl fmt::Display for ServerError {
48
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
×
49
        match self {
×
50
            ServerError::BadMagic(e) => write!(f, "Expected 0x81 as magic in response header, but found: {:x}", e),
×
51
            ServerError::BadResponse(s) => write!(f, "Unexpected: {} in response", s),
×
52
            ServerError::Error(s) => write!(f, "{}", s),
×
53
        }
54
    }
×
55
}
56

57
/// Command specific errors.
58
#[derive(Debug, PartialEq)]
×
59
pub enum CommandError {
60
    /// The client tried to set a key which already existed in the server.
61
    KeyExists,
62
    /// The client tried to set a key which does not exist in the server.
63
    KeyNotFound,
64
    /// The value for a key was too large. The limit is usually 1MB.
65
    ValueTooLarge,
66
    /// Invalid arguments were passed to the command.
67
    InvalidArguments,
68
    /// The server requires authentication.
69
    AuthenticationRequired,
70
    /// When using binary protocol, the server returned an unknown response status.
71
    Unknown(u16),
×
72
    /// The client sent an invalid command to the server.
73
    InvalidCommand,
74
}
75

76
impl MemcacheError {
77
    pub(crate) fn try_from(s: &str) -> Result<&str, MemcacheError> {
955✔
78
        if s == "ERROR\r\n" {
955✔
79
            Err(CommandError::InvalidCommand)?
×
80
        } else if s.starts_with("CLIENT_ERROR") {
955✔
81
            Err(ClientError::from(String::from(s)))?
×
82
        } else if s.starts_with("SERVER_ERROR") {
955✔
83
            Err(ServerError::from(String::from(s)))?
×
84
        } else if s == "NOT_FOUND\r\n" {
955✔
85
            Err(CommandError::KeyNotFound)?
2✔
86
        } else if s == "EXISTS\r\n" {
953✔
87
            Err(CommandError::KeyExists)?
1✔
88
        } else {
89
            Ok(s)
952✔
90
        }
91
    }
955✔
92
}
93

94
impl From<String> for ClientError {
95
    fn from(s: String) -> Self {
×
96
        ClientError::Error(Cow::Owned(s))
×
97
    }
×
98
}
99

100
impl From<String> for ServerError {
101
    fn from(s: String) -> Self {
×
102
        ServerError::Error(s)
×
103
    }
×
104
}
105

106
impl fmt::Display for CommandError {
107
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
×
108
        match self {
×
109
            CommandError::KeyExists => write!(f, "Key already exists in the server."),
×
110
            CommandError::KeyNotFound => write!(f, "Key was not found in the server."),
×
111
            CommandError::ValueTooLarge => write!(f, "Value was too large."),
×
112
            CommandError::InvalidArguments => write!(f, "Invalid arguments provided."),
×
113
            CommandError::AuthenticationRequired => write!(f, "Authentication required."),
×
114
            CommandError::Unknown(code) => write!(f, "Unknown error occurred with code: {}.", code),
×
115
            CommandError::InvalidCommand => write!(f, "Invalid command sent to the server."),
×
116
        }
117
    }
×
118
}
119

120
impl From<u16> for CommandError {
121
    fn from(status: u16) -> CommandError {
1,019✔
122
        match status {
1,019✔
123
            0x1 => CommandError::KeyNotFound,
514✔
124
            0x2 => CommandError::KeyExists,
505✔
125
            0x3 => CommandError::ValueTooLarge,
×
126
            0x4 => CommandError::InvalidArguments,
×
127
            0x20 => CommandError::AuthenticationRequired,
×
128
            e => CommandError::Unknown(e),
×
129
        }
130
    }
1,019✔
131
}
132

133
impl From<CommandError> for MemcacheError {
134
    fn from(err: CommandError) -> Self {
1,021✔
135
        MemcacheError::CommandError(err)
1,021✔
136
    }
1,021✔
137
}
138

139
impl From<ServerError> for MemcacheError {
140
    fn from(err: ServerError) -> Self {
×
141
        MemcacheError::ServerError(err)
×
142
    }
×
143
}
144

145
#[derive(Debug)]
×
146
pub enum ParseError {
147
    Bool(str::ParseBoolError),
×
148
    Int(num::ParseIntError),
×
149
    Float(num::ParseFloatError),
×
150
    String(string::FromUtf8Error),
×
151
    Str(std::str::Utf8Error),
×
152
    Url(url::ParseError),
×
153
}
154

155
impl error::Error for ParseError {
156
    fn source(&self) -> Option<&(dyn error::Error + 'static)> {
×
157
        match self {
×
158
            ParseError::Bool(ref e) => e.source(),
×
159
            ParseError::Int(ref e) => e.source(),
×
160
            ParseError::Float(ref e) => e.source(),
×
161
            ParseError::String(ref e) => e.source(),
×
162
            ParseError::Str(ref e) => e.source(),
×
163
            ParseError::Url(ref e) => e.source(),
×
164
        }
165
    }
×
166
}
167

168
impl fmt::Display for ParseError {
169
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
×
170
        match self {
×
171
            ParseError::Bool(ref e) => e.fmt(f),
×
172
            ParseError::Int(ref e) => e.fmt(f),
×
173
            ParseError::Float(ref e) => e.fmt(f),
×
174
            ParseError::String(ref e) => e.fmt(f),
×
175
            ParseError::Str(ref e) => e.fmt(f),
×
176
            ParseError::Url(ref e) => e.fmt(f),
×
177
        }
178
    }
×
179
}
180

181
impl From<ParseError> for MemcacheError {
182
    fn from(err: ParseError) -> Self {
×
183
        MemcacheError::ParseError(err)
×
184
    }
×
185
}
186

187
impl From<string::FromUtf8Error> for MemcacheError {
188
    fn from(err: string::FromUtf8Error) -> MemcacheError {
×
189
        ParseError::String(err).into()
×
190
    }
×
191
}
192

193
impl From<std::str::Utf8Error> for MemcacheError {
194
    fn from(err: std::str::Utf8Error) -> MemcacheError {
×
195
        ParseError::Str(err).into()
×
196
    }
×
197
}
198

199
impl From<num::ParseIntError> for MemcacheError {
200
    fn from(err: num::ParseIntError) -> MemcacheError {
×
201
        ParseError::Int(err).into()
×
202
    }
×
203
}
204

205
impl From<num::ParseFloatError> for MemcacheError {
206
    fn from(err: num::ParseFloatError) -> MemcacheError {
×
207
        ParseError::Float(err).into()
×
208
    }
×
209
}
210

211
impl From<url::ParseError> for MemcacheError {
212
    fn from(err: url::ParseError) -> MemcacheError {
×
213
        ParseError::Url(err).into()
×
214
    }
×
215
}
216

217
impl From<str::ParseBoolError> for MemcacheError {
218
    fn from(err: str::ParseBoolError) -> MemcacheError {
×
219
        ParseError::Bool(err).into()
×
220
    }
×
221
}
222

223
/// Stands for errors raised from rust-memcache
224
#[derive(Debug)]
×
225
pub enum MemcacheError {
226
    /// Error raised when the provided memcache URL doesn't have a host name
227
    BadURL(String),
×
228
    /// `std::io` related errors.
229
    IOError(io::Error),
×
230
    /// Client Errors
231
    ClientError(ClientError),
×
232
    /// Server Errors
233
    ServerError(ServerError),
×
234
    /// Command specific Errors
235
    CommandError(CommandError),
×
236
    #[cfg(feature = "tls")]
237
    OpensslError(openssl::ssl::HandshakeError<std::net::TcpStream>),
×
238
    /// Parse errors
239
    ParseError(ParseError),
×
240
    /// ConnectionPool errors
241
    PoolError(r2d2::Error),
×
242
    /// Json errors (only available with `json` feature) for invalid json strings
243
    #[cfg(feature = "json")]
NEW
244
    JsonError(serde_json::Error),
×
245
}
246

247
impl fmt::Display for MemcacheError {
248
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
×
249
        match *self {
×
250
            MemcacheError::BadURL(ref s) => s.fmt(f),
×
251
            MemcacheError::IOError(ref err) => err.fmt(f),
×
252
            #[cfg(feature = "tls")]
253
            MemcacheError::OpensslError(ref err) => err.fmt(f),
×
254
            MemcacheError::ParseError(ref err) => err.fmt(f),
×
255
            MemcacheError::ClientError(ref err) => err.fmt(f),
×
256
            MemcacheError::ServerError(ref err) => err.fmt(f),
×
257
            MemcacheError::CommandError(ref err) => err.fmt(f),
×
258
            MemcacheError::PoolError(ref err) => err.fmt(f),
×
259
            #[cfg(feature = "json")]
NEW
260
            MemcacheError::JsonError(ref err) => err.fmt(f),
×
261
        }
262
    }
×
263
}
264

265
impl error::Error for MemcacheError {
266
    fn source(&self) -> Option<&(dyn error::Error + 'static)> {
×
267
        match *self {
×
268
            MemcacheError::BadURL(_) => None,
×
269
            MemcacheError::IOError(ref err) => err.source(),
×
270
            #[cfg(feature = "tls")]
271
            MemcacheError::OpensslError(ref err) => err.source(),
×
272
            MemcacheError::ParseError(ref p) => p.source(),
×
273
            MemcacheError::ClientError(_) => None,
×
274
            MemcacheError::ServerError(_) => None,
×
275
            MemcacheError::CommandError(_) => None,
×
276
            MemcacheError::PoolError(ref p) => p.source(),
×
277
            #[cfg(feature = "json")]
NEW
278
            MemcacheError::JsonError(ref e) => e.source(),
×
279
        }
280
    }
×
281
}
282

283
impl From<io::Error> for MemcacheError {
284
    fn from(err: io::Error) -> MemcacheError {
2✔
285
        MemcacheError::IOError(err)
2✔
286
    }
2✔
287
}
288

289
#[cfg(feature = "tls")]
290
impl From<openssl::error::ErrorStack> for MemcacheError {
291
    fn from(err: openssl::error::ErrorStack) -> MemcacheError {
×
292
        MemcacheError::OpensslError(openssl::ssl::HandshakeError::<std::net::TcpStream>::from(err))
×
293
    }
×
294
}
295

296
#[cfg(feature = "tls")]
297
impl From<openssl::ssl::HandshakeError<std::net::TcpStream>> for MemcacheError {
298
    fn from(err: openssl::ssl::HandshakeError<std::net::TcpStream>) -> MemcacheError {
×
299
        MemcacheError::OpensslError(err)
×
300
    }
×
301
}
302

303
impl From<r2d2::Error> for MemcacheError {
304
    fn from(err: r2d2::Error) -> MemcacheError {
×
305
        MemcacheError::PoolError(err)
×
306
    }
×
307
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc