hab das error-handling vereinfacht, es panict jetzt sofort sobald ein fehler gefunden wurde, anstatt die fehler zurückzugeben. ratio ist, dass die fehler eh nicht behandelt werden können, und sonst nur weiter oben im call-stack zum abbruch geführt hätten. parst jetzt ein bischen mehr attribute, es ist im code einstellbar beim fehlen welcher attribute gepanict werden soll und bei welchen nur eine zeile auf stderr gesetzt werden soll; schreibt bei fehlenden attributen jetzt eine warnung auf stderr. kann jetzt auch die in verzeichnisse aufgeteilten einträge verarbeitenmaster
parent
f55e135b53
commit
9a3d948cbf
@ -0,0 +1,77 @@ |
||||
use std::path::Path; |
||||
use std::fs::File; |
||||
use serde_yaml; |
||||
use super::{Host, HostKind}; |
||||
|
||||
/** parsing funktioniert zweischrittig
|
||||
zunächst wird in from_file die yaml-datei ausgelesen, das resultat ist ein struct, dass in seinem aufbau der datei entspricht |
||||
danach wird in parse dieses in ein struct verwandelt, das dem logischen aufbau entspricht. |
||||
um das programm zu erweitern ist es am besten dinge zu Host/HostKind hinzuzufügen und dann den fehlern zu folgen. |
||||
*/ |
||||
#[derive(Deserialize,Debug)] |
||||
pub struct RawHost { |
||||
ansible_host: String, |
||||
#[serde(rename = "type")] |
||||
kind: String, |
||||
mac: Option<String>, |
||||
client_of: Option<String>, |
||||
coordinate: Option<[f64;2]>, |
||||
subnet: Option<String>, |
||||
link_ssid: Option<String>, |
||||
} |
||||
|
||||
impl RawHost { |
||||
/** wandelt mehr oder weniger magisch eine yaml-datei in ein RawHost um.
|
||||
die magie wird von dem (de)serialisierungsframework serde bereitgestellt */ |
||||
pub fn from_file(path: &Path) -> (Self, String) { |
||||
//TODO use methods .is_file and .is_dir on path and read path or path/vars depending on result
|
||||
let filename = path.file_stem().expect("weird path"); |
||||
let hostname = filename.to_str() |
||||
.expect(&format!("filename '{:?}' is not valid utf-8", filename)).into(); |
||||
let fd = if path.is_file() { |
||||
File::open(path) |
||||
.unwrap_or_else(|err| panic!("{} in file {}", err, hostname)) |
||||
} else if path.is_dir() { |
||||
let mut buf = path.to_path_buf(); |
||||
buf.push("vars"); |
||||
File::open(buf) |
||||
.unwrap_or_else(|err| panic!("{} in file {}", err, hostname)) |
||||
} else { |
||||
panic!("{:?} does not point to either a file or a directory", path) |
||||
}; |
||||
let antenna : Self = serde_yaml::from_reader(&fd) |
||||
.unwrap_or_else(|err| panic!("{} in file {}", err, hostname)); |
||||
(antenna, hostname) |
||||
} |
||||
|
||||
/** nimmt eine geparste datei und versucht daraus die logische struktur zu extrahieren */ |
||||
pub fn parse(self, name: String) -> Host { |
||||
// sobald ein felhender eintrag bei allen gefixt ist, bitte unten missingwarn("name") durch
|
||||
// missingpanic ersetzen
|
||||
let missingpanic= |attr: &'static str| panic!("{} does not have the required attribute {}", name, attr); |
||||
let missingwarn = |attr: &'static str| { |
||||
eprintln!("{} does not have the required attribute {}", name, attr); |
||||
"MISSING".to_string() |
||||
}; |
||||
Host |
||||
{ name: name.clone() |
||||
, ip: self.ansible_host |
||||
, kind: match self.kind.as_ref() |
||||
{ "wlan-ap" => HostKind::AccessPoint |
||||
{ mac: self.mac.unwrap_or_else(|| missingpanic("mac")) |
||||
, ssid: self.link_ssid.unwrap_or_else(|| missingwarn("link_ssid")) |
||||
, parent: self.client_of.unwrap_or_else(|| missingwarn("client_of")) |
||||
} |
||||
, "client" => HostKind::Client |
||||
{ subnet: self.subnet.unwrap_or_else(|| missingpanic("subnet")) |
||||
, coordinates: self.coordinate |
||||
, parent: self.client_of.unwrap_or_else(|| missingwarn("client_of")) |
||||
, mac: self.mac.unwrap_or_else(|| missingpanic("mac")) |
||||
, ssid: self.link_ssid.unwrap_or_else(|| missingwarn("link_ssid")) |
||||
} |
||||
, "service" => HostKind::Service |
||||
, _ => HostKind::Other |
||||
} |
||||
} |
||||
} |
||||
} |
Loading…
Reference in new issue