use std::collections::BTreeMap;
use chrono::{DateTime, FixedOffset};
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
#[serde(rename_all = "lowercase")]
pub enum DetectionKind {
Punctual,
Linear,
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
#[serde(untagged)]
pub enum TimestampOrRange {
Single {
timestamp: DateTime<FixedOffset>,
},
Range {
t_from: DateTime<FixedOffset>,
t_to: DateTime<FixedOffset>,
},
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
#[serde(tag = "kind", rename_all = "snake_case")]
pub enum DiscardReason {
OutOfTimeRange {
gnss_first: DateTime<FixedOffset>,
gnss_last: DateTime<FixedOffset>,
},
OutOfReach {
nearest_distance_m: f64,
cutoff_m: f64,
},
UnknownNetelement { netelement_id: String },
IntrinsicOutOfRange { value: f64 },
DuplicateOfPriorDetection { kept_index: usize },
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
#[serde(tag = "status", rename_all = "snake_case")]
pub enum DetectionStatus {
Applied {
netelement_id: String,
intrinsic: f64,
},
Resolved {
netelement_id: String,
distance_m: f64,
},
Discarded { reason: DiscardReason },
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct DetectionRecord {
pub source_file: String,
pub source_row: usize,
pub kind: DetectionKind,
pub timestamp: TimestampOrRange,
pub status: DetectionStatus,
pub id: Option<String>,
pub source: Option<String>,
#[serde(default, skip_serializing_if = "BTreeMap::is_empty")]
pub metadata: BTreeMap<String, String>,
}