dahua_camera_server/
dto.rs1use dahua_camera_rtsp::Camera;
9use dahua_camera_core::CameraStatus;
10use serde::Serialize;
11use std::sync::atomic::Ordering;
12
13#[derive(Debug, Clone, Serialize)]
15pub struct CameraView {
16 pub id: String,
18 pub label: String,
20 pub status: CameraStatus,
22 pub viewers: usize,
24 pub frames: u64,
26 pub idr_frames: u64,
28 pub bytes: u64,
30 pub reconnects: u64,
32 pub lagged_drops: u64,
34 pub decoded_frames: u64,
36 pub width: Option<u16>,
38 pub height: Option<u16>,
40}
41
42impl CameraView {
43 pub fn of(camera: &Camera) -> Self {
49 let params = camera.params();
50 let stats = camera.stats();
51 Self {
52 id: camera.id().to_owned(),
53 label: camera.config().display_name().to_owned(),
54 status: camera.status(),
55 viewers: camera.viewer_count(),
56 frames: stats.frames.load(Ordering::Relaxed),
57 idr_frames: stats.idr_frames.load(Ordering::Relaxed),
58 bytes: stats.bytes.load(Ordering::Relaxed),
59 reconnects: stats.reconnects.load(Ordering::Relaxed),
60 lagged_drops: stats.lagged_drops.load(Ordering::Relaxed),
61 decoded_frames: stats.decoded_frames.load(Ordering::Relaxed),
62 width: params.as_ref().map(|p| p.codec.width),
63 height: params.as_ref().map(|p| p.codec.height),
64 }
65 }
66}
67
68#[cfg(test)]
69mod tests {
70 use super::*;
71
72 #[test]
73 fn status_serialises_as_a_tagged_object() {
74 let json = serde_json::to_value(CameraStatus::Streaming { width: 704, height: 576 })
75 .expect("serialises");
76 assert_eq!(json["state"], "streaming");
77 assert_eq!(json["width"], 704);
78 }
79
80 #[test]
81 fn idle_status_carries_no_extra_fields() {
82 let json = serde_json::to_value(CameraStatus::Idle).expect("serialises");
83 assert_eq!(json["state"], "idle");
84 assert_eq!(json.as_object().expect("object").len(), 1);
85 }
86
87 #[test]
88 fn reconnecting_status_reports_the_delay_and_reason() {
89 let json = serde_json::to_value(CameraStatus::Reconnecting {
90 after_secs: 4,
91 reason: "stream ended".into(),
92 })
93 .expect("serialises");
94 assert_eq!(json["state"], "reconnecting");
95 assert_eq!(json["after_secs"], 4);
96 assert_eq!(json["reason"], "stream ended");
97 }
98}