gst_plugin_webrtc_signalling_protocol/
lib.rs

1// SPDX-License-Identifier: MPL-2.0
2
3/// The default protocol used by the signalling server
4use serde::{Deserialize, Serialize};
5
6#[derive(Serialize, Deserialize, Debug, PartialEq, Eq)]
7#[serde(rename_all = "camelCase")]
8pub struct Peer {
9    pub id: String,
10    #[serde(default)]
11    pub meta: Option<serde_json::Value>,
12}
13
14#[derive(Serialize, Deserialize, Debug, PartialEq, Eq)]
15#[serde(tag = "type")]
16#[serde(rename_all = "camelCase")]
17/// Messages sent from the server to peers
18pub enum OutgoingMessage {
19    /// Welcoming message, sets the Peer ID linked to a new connection
20    #[serde(rename_all = "camelCase")]
21    Welcome { peer_id: String },
22    /// Notifies listeners that a peer status has changed
23    PeerStatusChanged(PeerStatus),
24    /// Instructs a peer to generate an offer or an answer and inform about the session ID
25    #[serde(rename_all = "camelCase")]
26    StartSession {
27        peer_id: String,
28        session_id: String,
29        offer: Option<String>,
30    },
31    /// Let consumer know that the requested session is starting with the specified identifier
32    #[serde(rename_all = "camelCase")]
33    SessionStarted { peer_id: String, session_id: String },
34    /// Signals that the session the peer was in was ended
35    EndSession(EndSessionMessage),
36    /// Messages directly forwarded from one peer to another
37    Peer(PeerMessage),
38    /// Provides the current list of producers
39    #[serde(rename_all = "camelCase")]
40    List { producers: Vec<Peer> },
41    /// Provides the current list of consumers (awaiting a session request)
42    #[serde(rename_all = "camelCase")]
43    ListConsumers { consumers: Vec<Peer> },
44    /// Notifies that an error occurred with the peer's current session
45    #[serde(rename_all = "camelCase")]
46    Error { details: String },
47}
48
49#[derive(Serialize, Deserialize, Debug, PartialEq, Eq, Clone)]
50#[serde(rename_all = "camelCase")]
51/// Register with a peer type
52pub enum PeerRole {
53    /// Register as a producer
54    Producer,
55    /// Register as a listener
56    Listener,
57    /// Register as a passive consumer (awaiting a session initiated by a producer peer)
58    Consumer,
59}
60
61#[derive(Serialize, Deserialize, Debug, PartialEq, Eq, Default, Clone)]
62#[serde(rename_all = "camelCase")]
63pub struct PeerStatus {
64    pub roles: Vec<PeerRole>,
65    pub meta: Option<serde_json::Value>,
66    #[serde(skip_serializing_if = "Option::is_none")]
67    #[serde(default)]
68    pub peer_id: Option<String>,
69}
70
71impl PeerStatus {
72    pub fn producing(&self) -> bool {
73        self.roles.iter().any(|t| matches!(t, PeerRole::Producer))
74    }
75
76    pub fn listening(&self) -> bool {
77        self.roles.iter().any(|t| matches!(t, PeerRole::Listener))
78    }
79
80    pub fn consuming(&self) -> bool {
81        self.roles.iter().any(|t| matches!(t, PeerRole::Consumer))
82    }
83}
84
85#[derive(Serialize, Deserialize, Debug)]
86#[serde(rename_all = "camelCase")]
87/// Ask the server to start a session (either as a producer or a consumer)
88pub struct StartSessionMessage {
89    /// Identifies the peer
90    pub peer_id: String,
91    /// An offer if the consumer peer wants the producer to answer
92    pub offer: Option<String>,
93}
94
95#[derive(Serialize, Deserialize, Debug, PartialEq, Eq, Clone)]
96#[serde(tag = "type")]
97#[serde(rename_all = "camelCase")]
98/// Conveys a SDP
99pub enum SdpMessage {
100    /// Conveys an offer
101    #[serde(rename_all = "camelCase")]
102    Offer {
103        /// The SDP
104        sdp: String,
105    },
106    /// Conveys an answer
107    #[serde(rename_all = "camelCase")]
108    Answer {
109        /// The SDP
110        sdp: String,
111    },
112}
113
114#[derive(Serialize, Deserialize, Debug, PartialEq, Eq, Clone)]
115#[serde(rename_all = "camelCase")]
116/// Contents of the peer message
117pub enum PeerMessageInner {
118    /// Conveys an ICE candidate
119    #[serde(rename_all = "camelCase")]
120    Ice {
121        /// The candidate string
122        candidate: String,
123        /// The mline index the candidate applies to
124        sdp_m_line_index: u32,
125    },
126    Sdp(SdpMessage),
127}
128
129#[derive(Serialize, Deserialize, Debug, PartialEq, Eq)]
130#[serde(rename_all = "camelCase")]
131/// Messages directly forwarded from one peer to another
132pub struct PeerMessage {
133    pub session_id: String,
134    #[serde(flatten)]
135    pub peer_message: PeerMessageInner,
136}
137
138#[derive(Serialize, Deserialize, Debug, PartialEq, Eq)]
139#[serde(rename_all = "camelCase")]
140/// End a session
141pub struct EndSessionMessage {
142    /// The identifier of the session to end
143    pub session_id: String,
144}
145
146#[derive(Serialize, Deserialize, Debug)]
147#[serde(tag = "type")]
148#[serde(rename_all = "camelCase")]
149/// Messages received by the server from peers
150pub enum IncomingMessage {
151    /// Internal message to let know about new peers
152    NewPeer,
153    /// Set current peer status
154    SetPeerStatus(PeerStatus),
155    /// Start a session with another peer
156    StartSession(StartSessionMessage),
157    /// End an existing session
158    EndSession(EndSessionMessage),
159    /// Send a message to a peer the sender is currently in session with
160    Peer(PeerMessage),
161    /// Retrieve the current list of producers
162    List,
163    /// Retrieve the current list of consumers
164    ListConsumers,
165}