diff --git a/trifid-api/Cargo.toml b/trifid-api/Cargo.toml index fa3c0a2..8aee703 100644 --- a/trifid-api/Cargo.toml +++ b/trifid-api/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "trifid-api" -version = "0.1.1" +version = "0.1.2" edition = "2021" description = "Pure-rust Defined Networking compatible management server" license = "GPL-3.0-or-later" diff --git a/trifid-api/src/codegen/mod.rs b/trifid-api/src/codegen/mod.rs index fd6ea04..1b8df99 100644 --- a/trifid-api/src/codegen/mod.rs +++ b/trifid-api/src/codegen/mod.rs @@ -197,63 +197,31 @@ pub async fn generate_config( local_range: None, }; - let mut val = Mapping::new(); + // Merge with config overrides and re-parse + let config_str = serde_yaml::to_string(&nebula_config)?; + let mut value: serde_yaml::Value = serde_yaml::from_str(&config_str)?; - for (k, v) in &info.config_overrides { - let key_split = k.split('.').collect::>(); + for (key, kv_value) in &info.config_overrides { + // split up the key + // a.b.c.d = ['a']['b']['c']['d'] = value + let key_split = key.split('.').collect::>(); - let mut value = &mut val; + let mut current_val = &mut value; - for ks_k in &key_split[..key_split.len()-1] { - if !value.contains_key(ks_k) { - value.insert(Value::String(ks_k.to_string()), Value::Mapping(Mapping::new())); - } - - value = value.get_mut(ks_k).ok_or("Invalid key-value pair")?.as_mapping_mut().unwrap(); + for key_iter in &key_split[..key_split.len()-1] { + current_val = current_val.as_mapping_mut().unwrap().entry(Value::String(key_iter.to_string())).or_insert(Value::Mapping(Mapping::new())); } - value.insert(Value::String(key_split[key_split.len()-1].to_string()), serde_yaml::from_str(v)?); + current_val.as_mapping_mut().unwrap().insert(Value::String(key_split[key_split.len()-1].to_string()), serde_yaml::from_str(kv_value)?); } - let overrides_value = Value::Mapping(val); + let config_str_merged = serde_yaml::to_string(&value)?; - debug!("{:?}", overrides_value); - - let mut value = serde_yaml::to_value(nebula_config)?; - - debug!("{:?}", value); - - merge_yaml(&mut value, overrides_value); - - debug!("{:?}", value); - - let nebula_config = serde_yaml::from_value(value)?; + let nebula_config = serde_yaml::from_str(&config_str_merged)?; Ok((nebula_config, cert)) } -// This cursed abomination credit https://stackoverflow.com/questions/67727239/how-to-combine-including-nested-array-values-two-serde-yamlvalue-objects -fn merge_yaml(a: &mut serde_yaml::Value, b: serde_yaml::Value) { - match (a, b) { - (a @ &mut serde_yaml::Value::Mapping(_), serde_yaml::Value::Mapping(b)) => { - let a = a.as_mapping_mut().unwrap(); - for (k, v) in b { - if v.is_sequence() && a.contains_key(&k) && a[&k].is_sequence() { - let mut _b = a.get(&k).unwrap().as_sequence().unwrap().to_owned(); - _b.append(&mut v.as_sequence().unwrap().to_owned()); - a[&k] = serde_yaml::Value::from(_b); - continue; - } - if !a.contains_key(&k) {a.insert(k.to_owned(), v.to_owned());} - else { merge_yaml(&mut a[&k], v); } - - } - - } - (a, b) => *a = b, - } -} - pub async fn collect_info<'a>( db: &'a Data, host: &'a str,