use std::net::IpAddr;
use std::sync::Arc;
use flowscope::L4Proto;
use super::predicate::{FieldSource, Predicate};
use crate::ctx::Ctx;
use crate::error::Result;
use crate::protocol::FlowProtocol;
use crate::protocol::event_typed::FlowEnded;
pub type FlowHandler<P> =
Arc<dyn for<'c> Fn(&FlowEnded<P>, &mut Ctx<'c>) -> Result<()> + Send + Sync>;
#[derive(Clone)]
pub struct FlowSubscription<P: FlowProtocol> {
pub(crate) predicate: Predicate,
pub(crate) handler: FlowHandler<P>,
}
impl<P: FlowProtocol> std::fmt::Debug for FlowSubscription<P> {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
f.debug_struct("FlowSubscription")
.field("predicate", &self.predicate)
.field("handler", &"<fn>")
.finish()
}
}
pub(crate) struct FlowEndedFields<'a, P: FlowProtocol> {
pub(crate) evt: &'a FlowEnded<P>,
}
impl<P: FlowProtocol> FieldSource for FlowEndedFields<'_, P> {
fn l4proto(&self) -> Option<L4Proto> {
self.evt.l4.or(Some(self.evt.key.proto))
}
fn src_port(&self) -> Option<u16> {
Some(self.evt.key.a.port())
}
fn dst_port(&self) -> Option<u16> {
Some(self.evt.key.b.port())
}
fn src_ip(&self) -> Option<IpAddr> {
Some(self.evt.key.a.ip())
}
fn dst_ip(&self) -> Option<IpAddr> {
Some(self.evt.key.b.ip())
}
fn total_bytes(&self) -> Option<u64> {
Some(self.evt.stats.total_bytes())
}
fn total_packets(&self) -> Option<u64> {
Some(self.evt.stats.total_packets())
}
}