use serde::{Deserialize, Serialize}; use std::time::{Duration, SystemTime}; #[derive(Debug, Clone, Serialize, Deserialize)] pub struct ConnectionStats { pub total_connections: u64, pub active_connections: u32, pub read_operations: u64, pub write_operations: u64, pub errors: u64, pub bytes_transferred: u64, pub uptime_seconds: u64, } impl Default for ConnectionStats { fn default() -> Self { ConnectionStats { total_connections: 0, active_connections: 0, read_operations: 0, write_operations: 0, errors: 0, bytes_transferred: 0, uptime_seconds: 0, } } } #[derive(Debug, Clone, Serialize, Deserialize)] pub struct AccessLogEntry { pub timestamp: String, pub username: String, pub action: String, pub path: String, pub success: bool, pub bytes: u64, pub duration_ms: u64, } impl AccessLogEntry { pub fn new(username: String, action: String, path: String, success: bool, bytes: u64, duration: Duration) -> Self { let timestamp = SystemTime::now() .duration_since(SystemTime::UNIX_EPOCH) .unwrap() .as_secs(); AccessLogEntry { timestamp: timestamp.to_string(), username, action, path, success, bytes, duration_ms: duration.as_millis() as u64, } } } pub struct SMBMonitor { stats: ConnectionStats, logs: Vec, start_time: SystemTime, } impl SMBMonitor { pub fn new() -> Self { SMBMonitor { stats: ConnectionStats::default(), logs: Vec::new(), start_time: SystemTime::now(), } } pub fn log_access(&mut self, entry: AccessLogEntry) { self.logs.push(entry.clone()); if entry.success { if entry.action == "read" { self.stats.read_operations += 1; } else if entry.action == "write" { self.stats.write_operations += 1; } self.stats.bytes_transferred += entry.bytes; } else { self.stats.errors += 1; } } pub fn connection_opened(&mut self) { self.stats.total_connections += 1; self.stats.active_connections += 1; } pub fn connection_closed(&mut self) { self.stats.active_connections -= 1; } pub fn get_stats(&self) -> ConnectionStats { let uptime = SystemTime::now() .duration_since(self.start_time) .unwrap() .as_secs(); let mut stats = self.stats.clone(); stats.uptime_seconds = uptime; stats } pub fn get_logs(&self, limit: usize) -> Vec { self.logs.iter().rev().take(limit).cloned().collect() } }