oddity_rtsp_protocol/
request.rs1use std::fmt;
2
3use super::{
4 message::{Bytes, Headers, Message, Method, Uri, Version},
5 range::Range,
6 transport::Transport,
7 Error,
8};
9
10#[derive(Clone, Debug)]
11pub struct Request {
12 pub method: Method,
13 pub uri: Uri,
14 pub version: Version,
15 pub headers: Headers,
16 pub body: Option<Bytes>,
17}
18
19impl Message for Request {
20 type Metadata = RequestMetadata;
21
22 fn new(metadata: RequestMetadata, headers: Headers, body: Option<Bytes>) -> Self {
23 Self {
24 method: metadata.method,
25 uri: metadata.uri,
26 version: metadata.version,
27 headers,
28 body,
29 }
30 }
31}
32
33impl Request {
34 pub fn uri(&self) -> &Uri {
35 &self.uri
36 }
37
38 pub fn path(&self) -> &str {
39 self.uri.path().trim_end_matches('/')
40 }
41
42 pub fn require(&self) -> Option<&str> {
43 self.headers.get("Require").map(|val| val.as_str())
44 }
45
46 pub fn accept(&self) -> Vec<&str> {
47 self.headers
48 .get("Accept")
49 .map(|val| val.split(',').map(|part| part.trim()).collect::<Vec<_>>())
50 .unwrap_or_default()
51 }
52
53 pub fn session(&self) -> Option<&str> {
54 self.headers.get("Session").map(|val| val.as_str())
55 }
56
57 pub fn transport(&self) -> Result<Vec<Transport>, Error> {
58 if let Some(value) = self.headers.get("Transport") {
59 value
60 .split(',')
61 .map(|part| part.parse())
62 .collect::<Result<Vec<_>, _>>()
63 } else {
64 Ok(Vec::new())
65 }
66 }
67
68 pub fn range(&self) -> Option<Result<Range, Error>> {
69 self.headers.get("Range").map(|value| value.parse())
70 }
71}
72
73impl fmt::Display for Request {
74 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
75 write!(
76 f,
77 "Version: {}, Method: {}, Uri: {}",
78 self.version, self.method, self.uri
79 )?;
80
81 if !self.headers.is_empty() {
82 writeln!(f, "\nHeaders:")?;
83 for (var, val) in &self.headers {
84 writeln!(f, " - {}: {}", &var, &val)?;
85 }
86 }
87
88 if let Some(body) = &self.body {
89 writeln!(f, "[{} bytes]", body.len())?;
90 }
91
92 Ok(())
93 }
94}
95
96#[derive(Clone, Debug)]
97pub struct RequestMetadata {
98 method: Method,
99 uri: Uri,
100 version: Version,
101}
102
103impl RequestMetadata {
104 pub(super) fn new(method: Method, uri: Uri, version: Version) -> Self {
105 Self {
106 method,
107 uri,
108 version,
109 }
110 }
111}