Files
discordp2000/src/p2000.rs
2025-03-15 12:26:31 +01:00

137 lines
3.8 KiB
Rust

// https://www.112centraal.nl/capcodes?codes=000723153
use std::str::FromStr;
#[derive(Debug)]
pub enum Service {
Politie,
Brandweer,
Ambulance,
Overige(&'static str),
}
impl std::fmt::Display for Service {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(
f,
"{}",
match self {
Service::Politie => "Politie",
Service::Brandweer => "Brandweer",
Service::Ambulance => "Ambulance",
Service::Overige(o) => *o,
}
)
}
}
#[derive(Debug)]
pub struct CapCode {
pub capcode: &'static str,
pub region: &'static str,
pub location: &'static str,
pub service: Service,
pub description: &'static str,
}
include!(concat!(env!("OUT_DIR"), "/capcodes.rs"));
#[allow(unused)]
#[derive(Debug)]
pub struct Message {
pub raw: String,
pub protocol: String,
pub timestamp: String,
pub flags: String,
pub frameid: String,
pub capcodes_raw: String,
pub capcodes: Vec<&'static CapCode>,
pub format: String,
pub message: String,
}
impl std::fmt::Display for Message {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
if self.capcodes.is_empty() {
write!(f, "[{}]: {}", self.capcodes_raw, self.message)?;
return Ok(());
}
let mut iterator = self.capcodes.iter().peekable();
while let Some(code) = iterator.next() {
write!(f, "[{}]", code.service)?;
if !code.region.is_empty() {
write!(f, "[{}]", code.region.trim())?;
}
if !code.location.is_empty() {
write!(f, "[{}]", code.location.trim())?;
}
if !code.description.is_empty() {
write!(f, "[{}]", code.description.trim())?;
}
write!(f, ": ")?;
write!(f, "{}", self.message)?;
if iterator.peek().is_some() {
writeln!(f)?;
}
}
Ok(())
}
}
impl FromStr for Message {
type Err = crate::Error;
fn from_str(s: &str) -> std::result::Result<Self, Self::Err> {
let mut parts = s.split('|'); //.collect::<Vec<&str>>();
if parts.clone().count() != 7 {
return Err("Invalid message".into());
}
let Some(protocol) = parts.next() else {
return Err("Missing Protocol".into());
};
let Some(timestamp) = parts.next() else {
return Err("Missing Timestamp".into());
};
let Some(flags) = parts.next() else {
return Err("Missing Flags".into());
};
let Some(frameid) = parts.next() else {
return Err("Missing FrameID".into());
};
let Some(capcodes) = parts.next() else {
return Err("Missing Cap Codes".into());
};
let Some(format) = parts.next() else {
return Err("Missing Format".into());
};
let Some(message) = parts.next() else {
return Err("Missing Message".into());
};
let mut cc = vec![];
let parts = capcodes.split(' ');
for c in parts {
let c = &c[2..];
let Some(cap) = CAPCODES.get(c) else {
eprintln!("Missing CapCode: {}", c);
continue;
};
cc.push(cap);
}
Ok(Self {
raw: s.to_string(),
protocol: protocol.to_string(),
timestamp: timestamp.to_string(),
flags: flags.to_string(),
frameid: frameid.to_string(),
capcodes_raw: capcodes.to_string(),
capcodes: cc,
format: format.to_string(),
message: message.trim().to_string(),
})
}
}