1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
use std::fmt;
use version_compare::{CompOp, VersionCompare};
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
pub enum Version {
#[cfg(feature = "send2")]
V2,
#[cfg(feature = "send3")]
V3,
}
impl Version {
pub fn parse<'a>(ver: &'a str) -> Result<Self, &'a str> {
let mut stripped = ver.trim();
if stripped.starts_with('v') {
stripped = &stripped[1..];
}
if stripped.is_empty() {
return Err(ver);
}
#[cfg(feature = "send2")]
{
let lower =
VersionCompare::compare_to(stripped, "2.0", &CompOp::Ge).map_err(|_| ver)?;
let upper =
VersionCompare::compare_to(stripped, "3.0", &CompOp::Lt).map_err(|_| ver)?;
if lower && upper {
return Ok(Version::V2);
}
}
#[cfg(feature = "send3")]
{
let lower =
VersionCompare::compare_to(stripped, "3.0", &CompOp::Ge).map_err(|_| ver)?;
let upper =
VersionCompare::compare_to(stripped, "4.0", &CompOp::Lt).map_err(|_| ver)?;
if lower && upper {
return Ok(Version::V3);
}
}
Err(ver)
}
}
impl fmt::Display for Version {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
#[cfg(feature = "send2")]
Version::V2 => write!(f, "2"),
#[cfg(feature = "send3")]
Version::V3 => write!(f, "3"),
}
}
}
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
pub enum DesiredVersion {
Use(Version),
Assume(Version),
Lookup,
}
impl DesiredVersion {
pub fn version(self) -> Option<Version> {
match self {
DesiredVersion::Use(v) => Some(v),
DesiredVersion::Assume(v) => Some(v),
DesiredVersion::Lookup => None,
}
}
}