A small macro for flattening a map type with regex machting keys.
```rust
struct RouterStatus {
id: u32,
wifistatus: bool,
#[flatregex(regex = r"lanportstatus_\d+")]
lanports: std::collections::HashMap
fn jsontest() { let raw = r#"{ "id": 1, "wifistatus": true, "lanportstatus0": "UP", "lanportstatus1": "UP", "lanportstatus_2": "DOWN", "lanportspeed": "100" }"#;
let router_status: RouterStatus = serde_json::from_str(raw).unwrap();
assert_eq!(router_status.lanports.len(),3)
} ```
The key can be anything that implements AsRef<str>
or alternitiv the field attribute key_access
can be set with a function returning a Result<&str,_>
.
The function has to have the following signature: fn key_access_fn_name<T>(key: &T) -> Result<&str,Error>
where Error
can be any Errortype.
```rust use std::collections::BTreeMap; use std::str::Utf8Error; use std::ffi::CString; use serdeflatregex::flat_regex; use serde::Deserialize;
struct RouterStatus {
online: bool,
#[flatregex(regex = r"lanportstatus\d+",keyaccess = "cstringasstr")]
lanport_status: BTreeMap
fn cstringasstr(key: &CString) -> Result<&str,Utf8Error> { key.tostr() }
let json = serdejson::json!({ "online": true, "lanportstatus0": true, "lanportspeed0": "100", // no maching keys will be ignored "lanportstatus1": false, "lanportspeed1": "0", // no maching keys will be ignored "wifistatus": true });
let res: RouterStatus = serdejson::fromvalue(json).unwrap(); asserteq!(res.lanportstatus.len(),2) ```
The collection for flattening must be a serde-map type and implement Extend<(K,V)> + Default
.