lib

Core libraries for Radroots
git clone https://radroots.dev/git/lib.git
Log | Files | Refs | README | LICENSE

serde_ext.rs (1696B)


      1 #[cfg(feature = "serde")]
      2 pub mod epoch_seconds {
      3     use serde::{Deserialize, Deserializer, de::Error as DeError};
      4 
      5     pub fn de<'de, D>(de: D) -> Result<u32, D::Error>
      6     where
      7         D: Deserializer<'de>,
      8     {
      9         let v = u64::deserialize(de)?;
     10         if v > u32::MAX as u64 {
     11             return Err(D::Error::custom(
     12                 "timestamp must be epoch **seconds**, not ms",
     13             ));
     14         }
     15         Ok(v as u32)
     16     }
     17 }
     18 
     19 #[cfg(all(test, feature = "serde"))]
     20 mod tests {
     21     use super::epoch_seconds;
     22     #[cfg(not(feature = "std"))]
     23     use alloc::format;
     24     #[cfg(not(feature = "std"))]
     25     use alloc::string::ToString;
     26     use serde::Deserialize;
     27     #[cfg(feature = "std")]
     28     use std::string::ToString;
     29 
     30     #[derive(Debug, Deserialize)]
     31     struct EpochSecondsFixture {
     32         #[serde(deserialize_with = "epoch_seconds::de")]
     33         ts: u32,
     34     }
     35 
     36     #[test]
     37     fn epoch_seconds_accepts_u32_max() {
     38         let fixture: EpochSecondsFixture =
     39             serde_json::from_str(&format!(r#"{{"ts":{}}}"#, u32::MAX)).unwrap();
     40         assert_eq!(fixture.ts, u32::MAX);
     41     }
     42 
     43     #[test]
     44     fn epoch_seconds_rejects_overflow() {
     45         let err = serde_json::from_str::<EpochSecondsFixture>(&format!(
     46             r#"{{"ts":{}}}"#,
     47             u32::MAX as u64 + 1
     48         ))
     49         .unwrap_err();
     50         let msg = err.to_string();
     51         assert!(msg.contains("epoch **seconds**"));
     52     }
     53 
     54     #[test]
     55     fn epoch_seconds_rejects_invalid_input_type() {
     56         let err =
     57             serde_json::from_str::<EpochSecondsFixture>(r#"{"ts":"1700000000"}"#).unwrap_err();
     58         let msg = err.to_string();
     59         assert!(msg.contains("invalid type"));
     60     }
     61 }