Skip to content

Commit 4ae7a0a

Browse files
committed
fix(typescript): fix baseline types
1 parent a193fa0 commit 4ae7a0a

File tree

1 file changed

+73
-6
lines changed

1 file changed

+73
-6
lines changed

crates/rari-data/src/baseline.rs

Lines changed: 73 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
use std::borrow::Cow;
12
use std::collections::BTreeMap;
23
use std::fmt;
34
use std::marker::PhantomData;
@@ -6,9 +7,10 @@ use std::path::Path;
67
use indexmap::IndexMap;
78
use rari_utils::concat_strs;
89
use rari_utils::io::read_to_string;
9-
use schemars::JsonSchema;
10+
use schemars::schema::Schema;
11+
use schemars::{JsonSchema, SchemaGenerator};
1012
use serde::de::{self, value, SeqAccess, Visitor};
11-
use serde::{Deserialize, Deserializer, Serialize};
13+
use serde::{Deserialize, Deserializer, Serialize, Serializer};
1214
use serde_json::Value;
1315
use url::Url;
1416

@@ -141,7 +143,7 @@ impl WebFeatures {
141143
});
142144
}
143145
match status.baseline {
144-
Some(BaselineHighLow::False(false)) => {
146+
Some(BaselineHighLow::False) => {
145147
let Support {
146148
chrome,
147149
chrome_android,
@@ -301,13 +303,63 @@ pub struct Support {
301303
#[serde(default, skip_serializing_if = "Option::is_none")]
302304
safari_ios: Option<String>,
303305
}
304-
#[derive(Deserialize, Serialize, Clone, Copy, Debug, PartialEq, Eq, JsonSchema)]
306+
#[derive(Deserialize, Serialize, Clone, Copy, Debug, PartialEq, Eq)]
305307
#[serde(rename_all = "snake_case")]
306308
pub enum BaselineHighLow {
307309
High,
308310
Low,
309-
#[serde(untagged)]
310-
False(bool),
311+
#[serde(
312+
untagged,
313+
serialize_with = "serialize_false",
314+
deserialize_with = "deserialize_false"
315+
)]
316+
False,
317+
}
318+
319+
// Deriving JsonSchema fails to type the false case. So we do it manually.
320+
impl JsonSchema for BaselineHighLow {
321+
fn schema_name() -> String {
322+
"BaselineHighLow".into()
323+
}
324+
325+
fn schema_id() -> Cow<'static, str> {
326+
concat!(module_path!(), "::BaselineHighLow").into()
327+
}
328+
329+
fn json_schema(_gen: &mut SchemaGenerator) -> Schema {
330+
serde_json::from_str(
331+
r#"{"oneOf": [
332+
{
333+
"type": "string",
334+
"enum": ["high", "low"]
335+
},
336+
{
337+
"type": "boolean",
338+
"enum": [false]
339+
}
340+
]}"#,
341+
)
342+
.unwrap()
343+
}
344+
}
345+
346+
fn serialize_false<S>(serializer: S) -> Result<S::Ok, S::Error>
347+
where
348+
S: Serializer,
349+
{
350+
serializer.serialize_bool(false)
351+
}
352+
353+
fn deserialize_false<'de, D>(deserializer: D) -> Result<(), D::Error>
354+
where
355+
D: Deserializer<'de>,
356+
{
357+
let value = bool::deserialize(deserializer)?;
358+
if !value {
359+
Ok(())
360+
} else {
361+
Err(serde::de::Error::custom("expected false"))
362+
}
311363
}
312364

313365
#[derive(Deserialize, Serialize, Clone, Debug, JsonSchema)]
@@ -378,3 +430,18 @@ where
378430

379431
deserializer.deserialize_any(TOrVec::<T>(PhantomData))
380432
}
433+
434+
#[cfg(test)]
435+
mod test {
436+
use super::*;
437+
438+
#[test]
439+
fn test_baseline_high_low() {
440+
let json = r#"false"#;
441+
let bl = serde_json::from_str::<BaselineHighLow>(json);
442+
assert!(matches!(bl, Ok(BaselineHighLow::False)));
443+
let json = r#""high""#;
444+
let bl = serde_json::from_str::<BaselineHighLow>(json);
445+
assert!(matches!(bl, Ok(BaselineHighLow::High)));
446+
}
447+
}

0 commit comments

Comments
 (0)