feat(protocol): negotiate registered gateway profiles
This commit is contained in:
+15
-10
@@ -1,6 +1,6 @@
|
||||
// Code generated by tools/generate.py; DO NOT EDIT.
|
||||
#![allow(non_snake_case)]
|
||||
pub const SCHEMA_SHA256: &str = "fe4d6be69665f09f04e2cd89273ebc5d2dddf4cde98b94a9d8c4f726504ffe1b";
|
||||
pub const SCHEMA_SHA256: &str = "3aec8dd72bdbb6b9657c8df3160252c93034c7c1032d471e01eae2ef91e47716";
|
||||
pub const CURRENT_WIRE_VERSION: &str = "1";
|
||||
pub const N_MINUS_1_WIRE_VERSION: &str = "0";
|
||||
pub const N_MINUS_2_WIRE_VERSION: &str = "-1";
|
||||
@@ -210,11 +210,11 @@ pub struct CapabilityProfile {
|
||||
media: String,
|
||||
audio: String,
|
||||
sourceRateControl: String,
|
||||
clientDecode: String,
|
||||
clientDecode: Vec<String>,
|
||||
}
|
||||
|
||||
impl CapabilityProfile {
|
||||
pub fn new(transport: String, framing: String, media: String, audio: String, sourceRateControl: String, clientDecode: String) -> Result<Self, ValidationError> {
|
||||
pub fn new(transport: String, framing: String, media: String, audio: String, sourceRateControl: String, clientDecode: Vec<String>) -> Result<Self, ValidationError> {
|
||||
let value = Self { transport, framing, media, audio, sourceRateControl, clientDecode };
|
||||
value.validate()?;
|
||||
Ok(value)
|
||||
@@ -235,9 +235,10 @@ impl CapabilityProfile {
|
||||
if self.sourceRateControl.is_empty() { return Err(ValidationError::new("source_rate_control", "required")); }
|
||||
if !self.sourceRateControl.is_empty() && self.sourceRateControl.len() < 1 { return Err(ValidationError::new("source_rate_control", "min_length")); }
|
||||
if self.sourceRateControl.len() > 64 { return Err(ValidationError::new("source_rate_control", "max_length")); }
|
||||
if self.clientDecode.is_empty() { return Err(ValidationError::new("client_decode", "required")); }
|
||||
if !self.clientDecode.is_empty() && self.clientDecode.len() < 1 { return Err(ValidationError::new("client_decode", "min_length")); }
|
||||
if self.clientDecode.len() > 64 { return Err(ValidationError::new("client_decode", "max_length")); }
|
||||
if self.clientDecode.len() < 1 { return Err(ValidationError::new("client_decode", "min_items")); }
|
||||
if self.clientDecode.len() > 2 { return Err(ValidationError::new("client_decode", "max_items")); }
|
||||
for item in self.clientDecode.iter() { if item != "h264-opus" && item != "hevc-opus" { return Err(ValidationError::new("client_decode", "invalid_item")); } }
|
||||
for (index, item) in self.clientDecode.iter().enumerate() { if self.clientDecode[..index].contains(item) { return Err(ValidationError::new("client_decode", "duplicate_item")); } }
|
||||
Ok(())
|
||||
}
|
||||
pub fn transport(&self) -> &String { &self.transport }
|
||||
@@ -245,7 +246,7 @@ impl CapabilityProfile {
|
||||
pub fn media(&self) -> &String { &self.media }
|
||||
pub fn audio(&self) -> &String { &self.audio }
|
||||
pub fn sourceRateControl(&self) -> &String { &self.sourceRateControl }
|
||||
pub fn clientDecode(&self) -> &String { &self.clientDecode }
|
||||
pub fn clientDecode(&self) -> &Vec<String> { &self.clientDecode }
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
@@ -1729,7 +1730,9 @@ impl TunnelAdmissionRequest {
|
||||
pub fn capabilities(&self) -> &CapabilityProfile { &self.capabilities }
|
||||
pub fn device_admission_transcript(&self) -> Vec<u8> {
|
||||
let reconnect_sequence = self.reconnectSequence.to_string();
|
||||
let fields = [&self.sessionId, &self.gatewayId, &self.audience, &self.grant, &reconnect_sequence, &self.clientNonce, &self.capabilities.transport, &self.capabilities.framing, &self.capabilities.media, &self.capabilities.audio, &self.capabilities.sourceRateControl, &self.capabilities.clientDecode];
|
||||
let client_decode_count = self.capabilities.clientDecode.len().to_string();
|
||||
let mut fields = vec![self.sessionId.as_str(), self.gatewayId.as_str(), self.audience.as_str(), self.grant.as_str(), reconnect_sequence.as_str(), self.clientNonce.as_str(), self.capabilities.transport.as_str(), self.capabilities.framing.as_str(), self.capabilities.media.as_str(), self.capabilities.audio.as_str(), self.capabilities.sourceRateControl.as_str(), client_decode_count.as_str()];
|
||||
fields.extend(self.capabilities.clientDecode.iter().map(String::as_str));
|
||||
let mut transcript = String::from("versevdi/tunnel-admission/v1");
|
||||
for field in fields { transcript.push_str(&format!("{}:{}", field.as_bytes().len(), field)); }
|
||||
transcript.into_bytes()
|
||||
@@ -1759,11 +1762,13 @@ impl VersionNegotiation {
|
||||
}
|
||||
|
||||
pub fn intersect_capability_profiles(profiles: &[CapabilityProfile]) -> Result<CapabilityProfile, ValidationError> {
|
||||
let selected = profiles.first().ok_or_else(|| ValidationError::new("capabilities", "no_overlap"))?.clone();
|
||||
let mut selected = profiles.first().ok_or_else(|| ValidationError::new("capabilities", "no_overlap"))?.clone();
|
||||
selected.validate().map_err(|_| ValidationError::new("capabilities", "no_overlap"))?;
|
||||
for profile in &profiles[1..] {
|
||||
profile.validate().map_err(|_| ValidationError::new("capabilities", "no_overlap"))?;
|
||||
if profile != &selected { return Err(ValidationError::new("capabilities", "no_overlap")); }
|
||||
if profile.transport != selected.transport || profile.framing != selected.framing || profile.media != selected.media || profile.audio != selected.audio || profile.sourceRateControl != selected.sourceRateControl { return Err(ValidationError::new("capabilities", "no_overlap")); }
|
||||
selected.clientDecode.retain(|candidate| profile.clientDecode.contains(candidate));
|
||||
if selected.clientDecode.is_empty() { return Err(ValidationError::new("capabilities", "no_overlap")); }
|
||||
}
|
||||
Ok(selected)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user