From 8fe733fc3046593611599ee71cb059aa4f17c697 Mon Sep 17 00:00:00 2001 From: Florian Briand Date: Sun, 6 Oct 2024 14:49:28 +0200 Subject: [PATCH] feat: use an enum instead of raw ID for CPS type --- crates/fsv/src/fsv_parsing/groups/mod.rs | 20 ++++++++++++++++- .../fsv_parsing/groups/ssv_lire_carte_ps.rs | 22 ++++++++++++++++--- 2 files changed, 38 insertions(+), 4 deletions(-) diff --git a/crates/fsv/src/fsv_parsing/groups/mod.rs b/crates/fsv/src/fsv_parsing/groups/mod.rs index 03e1fbb..132acea 100644 --- a/crates/fsv/src/fsv_parsing/groups/mod.rs +++ b/crates/fsv/src/fsv_parsing/groups/mod.rs @@ -17,10 +17,19 @@ where { let text = String::from_utf8(data_field.data) .map_err(|e| DekuError::Parse(e.to_string().into()))?; - T::from_str(&text) + text.parse::() .map_err(|e| DekuError::Parse(e.to_string().into())) } +/// # Extract an enum id from a string +/// Deku enums only supports numbers as id, and we usually extract strings +/// from data fields. This function is used as a context function to convert +/// a string, such as obtained with NumericString, to an enum id +pub fn extract_enum_id_from_str(id_string: &str, default: T) -> T + where T: FromStr { + id_string.parse::().unwrap_or(default) +} + // ------------------- DATA FIELD TYPES ------------------- /// # Data field structure @@ -105,4 +114,13 @@ mod test { assert_eq!(software_version.version, "07"); assert_eq!(software_version.revision, "20"); } + + #[test] + fn test_map_from_data_field() { + let data_field = DataField { + data: vec![48, 55], + }; + let id: u8 = map_from_data_field(data_field).unwrap(); + assert_eq!(id, 7); + } } \ No newline at end of file diff --git a/crates/fsv/src/fsv_parsing/groups/ssv_lire_carte_ps.rs b/crates/fsv/src/fsv_parsing/groups/ssv_lire_carte_ps.rs index 5c45c26..64677e1 100644 --- a/crates/fsv/src/fsv_parsing/groups/ssv_lire_carte_ps.rs +++ b/crates/fsv/src/fsv_parsing/groups/ssv_lire_carte_ps.rs @@ -8,7 +8,7 @@ use crate::fsv_parsing::groups::NumericString; /// 1 occurence pub mod group_1_holder { - use crate::fsv_parsing::groups::AlphaNumericString; + use crate::fsv_parsing::groups::{ extract_enum_id_from_str, AlphaNumericString }; use super::*; @@ -16,6 +16,9 @@ pub mod group_1_holder { #[deku_derive(DekuRead)] #[derive(Debug, PartialEq)] pub struct Holder { + #[deku(temp)] + card_type_raw: NumericString, + #[deku(ctx = "extract_enum_id_from_str::(&*card_type_raw.0, 255)")] pub card_type: CardPSType, pub national_id_type: NationalIDType, pub national_id: AlphaNumericString, // /!\ CE and not CA @@ -29,7 +32,19 @@ pub mod group_1_holder { // Fields #[deku_derive(DekuRead)] #[derive(Debug, PartialEq)] - pub struct CardPSType(pub NumericString); + #[deku(ctx = "id: u8", id = "id")] + pub enum CardPSType { + #[deku(id = 0)] + CPS, // Carte de Professionnel de Santé (CPS) + #[deku(id = 1)] + CPF, // Carte de Professionnel de Santé en Formation (CPF) + #[deku(id = 2)] + CPE, // Carte de Personnel / Directeur⋅ice d'Établissement de Santé (CDE/CPE) + #[deku(id = 3)] + CPA, // Carte de Personnel / Directeur⋅ice Autorisé⋅e (CDA/CPA) + #[deku(id = 4)] + CPM, // Carte de Personne Morale + } #[deku_derive(DekuRead)] #[derive(Debug, PartialEq)] @@ -45,6 +60,7 @@ pub mod group_1_holder { #[cfg(test)] mod tests { use deku::DekuContainerRead as _; + use group_1_holder::CardPSType; use crate::fsv_parsing::blocks::BlockHeader; @@ -133,7 +149,7 @@ mod tests { env_logger::init(); // Uncomment and run with RUST_LOG=trace for deku debugging let offset = 3*8; let (_rest, holder) = group_1_holder::Holder::from_bytes((data::BUFFER, offset)).unwrap(); - assert_eq!(holder.card_type.0.0, "0", "Card type"); + assert_eq!(holder.card_type, CardPSType::CPS, "Card type"); assert_eq!(holder.national_id_type.0.0, "8", "National ID type"); assert_eq!(holder.national_id.0, "99700593686", "National Id"); assert_eq!(holder.national_id_key.0, "6", "National ID Key");