You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
100 lines
2.7 KiB
100 lines
2.7 KiB
use crate::version::Version; |
|
use serde::Deserialize; |
|
use url::Url; |
|
|
|
mod lts_status { |
|
use serde::{Deserialize, Deserializer}; |
|
|
|
#[derive(Deserialize, Debug, PartialEq, Eq)] |
|
#[serde(untagged)] |
|
enum LtsStatus { |
|
Nope(bool), |
|
Yes(String), |
|
} |
|
|
|
impl From<LtsStatus> for Option<String> { |
|
fn from(status: LtsStatus) -> Self { |
|
match status { |
|
LtsStatus::Nope(_) => None, |
|
LtsStatus::Yes(x) => Some(x), |
|
} |
|
} |
|
} |
|
|
|
pub fn deserialize<'de, D>(deserializer: D) -> Result<Option<String>, D::Error> |
|
where |
|
D: Deserializer<'de>, |
|
{ |
|
Ok(LtsStatus::deserialize(deserializer)?.into()) |
|
} |
|
|
|
#[cfg(test)] |
|
mod tests { |
|
use super::*; |
|
use pretty_assertions::assert_eq; |
|
|
|
#[derive(Deserialize)] |
|
struct TestSubject { |
|
#[serde(deserialize_with = "deserialize")] |
|
lts: Option<String>, |
|
} |
|
|
|
#[test] |
|
fn test_false_deserialization() { |
|
let json = serde_json::json!({ "lts": false }); |
|
let subject: TestSubject = |
|
serde_json::from_value(json).expect("Can't deserialize json"); |
|
assert_eq!(subject.lts, None); |
|
} |
|
|
|
#[test] |
|
fn test_value_deserialization() { |
|
let json = serde_json::json!({ "lts": "dubnium" }); |
|
let subject: TestSubject = |
|
serde_json::from_value(json).expect("Can't deserialize json"); |
|
assert_eq!(subject.lts, Some("dubnium".into())); |
|
} |
|
} |
|
} |
|
|
|
#[derive(Deserialize, Debug)] |
|
pub struct IndexedNodeVersion { |
|
pub version: Version, |
|
#[serde(with = "lts_status")] |
|
pub lts: Option<String>, |
|
pub date: chrono::NaiveDate, |
|
pub files: Vec<String>, |
|
} |
|
|
|
/// Prints |
|
/// |
|
/// ```rust |
|
/// use crate::remote_node_index::list; |
|
/// ``` |
|
pub fn list(base_url: &Url) -> Result<Vec<IndexedNodeVersion>, crate::http::Error> { |
|
let index_json_url = format!("{base_url}/index.json"); |
|
let resp = crate::http::get(&index_json_url)?; |
|
let mut value: Vec<IndexedNodeVersion> = resp.json()?; |
|
value.sort_by(|a, b| a.version.cmp(&b.version)); |
|
Ok(value) |
|
} |
|
|
|
#[cfg(test)] |
|
mod tests { |
|
use super::*; |
|
use pretty_assertions::assert_eq; |
|
|
|
#[test] |
|
fn test_list() { |
|
let base_url = Url::parse("https://nodejs.org/dist").unwrap(); |
|
let expected_version = Version::parse("12.0.0").unwrap(); |
|
let mut versions = list(&base_url).expect("Can't get HTTP data"); |
|
assert_eq!( |
|
versions |
|
.drain(..) |
|
.find(|x| x.version == expected_version) |
|
.map(|x| x.version), |
|
Some(expected_version) |
|
); |
|
} |
|
}
|
|
|