Skip to main content

moqtap_client/draft12/
track_status.rs

1/// TrackStatus lifecycle states (draft-12).
2///
3/// TRACK_STATUS is a single request/response pair:
4/// the requester sends TRACK_STATUS_REQUEST, and the publisher
5/// replies with TRACK_STATUS. There are no OK / ERROR variants.
6#[derive(Debug, Clone, Copy, PartialEq, Eq)]
7pub enum TrackStatusState {
8    /// Initial state before any TRACK_STATUS_REQUEST is sent.
9    Idle,
10    /// TRACK_STATUS_REQUEST has been sent; awaiting TRACK_STATUS reply.
11    Pending,
12    /// Track status reply received.
13    Done,
14}
15
16/// Errors that can occur during track status state transitions.
17#[derive(Debug, thiserror::Error, PartialEq, Eq)]
18pub enum TrackStatusError {
19    /// An event was received that is not valid for the current state.
20    #[error("invalid transition from {from:?} on event {event}")]
21    InvalidTransition {
22        /// The state the machine was in when the invalid event arrived.
23        from: TrackStatusState,
24        /// The name of the event that was rejected.
25        event: String,
26    },
27}
28
29/// Pure state machine for a MoQT track status request (draft-12).
30/// Transitions: Idle → Pending → Done.
31pub struct TrackStatusStateMachine {
32    state: TrackStatusState,
33}
34
35impl Default for TrackStatusStateMachine {
36    fn default() -> Self {
37        Self::new()
38    }
39}
40
41impl TrackStatusStateMachine {
42    /// Creates a new state machine in the [`TrackStatusState::Idle`] state.
43    pub fn new() -> Self {
44        Self { state: TrackStatusState::Idle }
45    }
46
47    /// Returns the current state of the track status request.
48    pub fn state(&self) -> TrackStatusState {
49        self.state
50    }
51
52    /// Idle → Pending (TRACK_STATUS_REQUEST sent).
53    pub fn on_track_status_request_sent(&mut self) -> Result<(), TrackStatusError> {
54        if self.state == TrackStatusState::Idle {
55            self.state = TrackStatusState::Pending;
56            Ok(())
57        } else {
58            Err(TrackStatusError::InvalidTransition {
59                from: self.state,
60                event: "on_track_status_request_sent".to_string(),
61            })
62        }
63    }
64
65    /// Pending → Done (TRACK_STATUS received).
66    pub fn on_track_status(&mut self) -> Result<(), TrackStatusError> {
67        if self.state == TrackStatusState::Pending {
68            self.state = TrackStatusState::Done;
69            Ok(())
70        } else {
71            Err(TrackStatusError::InvalidTransition {
72                from: self.state,
73                event: "on_track_status".to_string(),
74            })
75        }
76    }
77}