dash_runtime/client/meta.rs
1//! What the caller reports about a response beyond its body: the instants it
2//! measured on its own monotonic clock and the headers the client reads.
3
4/// An MPD response as the caller observed it.
5///
6/// `sent_us` and `received_us` are the caller's monotonic microseconds when
7/// the request left and when the first response byte arrived; the client
8/// places the server's `FetchTime` at their midpoint (23009-1 A.2). Every
9/// header is optional: a client with none of them still plays, it just
10/// refreshes unconditionally and has no `Date` clock fallback.
11#[derive(Debug, Clone, Copy, PartialEq, Eq)]
12#[non_exhaustive]
13pub struct ResponseMeta<'a> {
14 /// Monotonic microseconds when the request was sent.
15 pub sent_us: u64,
16 /// Monotonic microseconds when the first response byte arrived.
17 pub received_us: u64,
18 /// The `Date` header, verbatim.
19 pub date: Option<&'a str>,
20 /// The `ETag` header, verbatim.
21 pub etag: Option<&'a str>,
22 /// The `Last-Modified` header, verbatim.
23 pub last_modified: Option<&'a str>,
24 /// The URL the response came from after redirects, when it differs from
25 /// the URL requested.
26 pub final_url: Option<&'a str>,
27}
28
29impl<'a> ResponseMeta<'a> {
30 /// A response exchanged between `sent_us` and `received_us`, no headers.
31 #[must_use]
32 pub fn new(sent_us: u64, received_us: u64) -> Self {
33 Self {
34 sent_us,
35 received_us,
36 date: None,
37 etag: None,
38 last_modified: None,
39 final_url: None,
40 }
41 }
42
43 /// A response with no round trip of its own: sent and received at `now_us`.
44 #[must_use]
45 pub fn at(now_us: u64) -> Self {
46 Self::new(now_us, now_us)
47 }
48
49 /// Set the `Date` header.
50 #[must_use]
51 pub fn with_date(mut self, date: &'a str) -> Self {
52 self.date = Some(date);
53 self
54 }
55
56 /// Set the `ETag` header.
57 #[must_use]
58 pub fn with_etag(mut self, etag: &'a str) -> Self {
59 self.etag = Some(etag);
60 self
61 }
62
63 /// Set the `Last-Modified` header.
64 #[must_use]
65 pub fn with_last_modified(mut self, last_modified: &'a str) -> Self {
66 self.last_modified = Some(last_modified);
67 self
68 }
69
70 /// Set the post-redirect URL.
71 #[must_use]
72 pub fn with_final_url(mut self, final_url: &'a str) -> Self {
73 self.final_url = Some(final_url);
74 self
75 }
76}
77
78/// A `UTCTiming` response as the caller observed it.
79#[derive(Debug, Clone, Copy, PartialEq, Eq)]
80#[non_exhaustive]
81pub struct UtcResponse<'a> {
82 /// Monotonic microseconds when the request was sent.
83 pub sent_us: u64,
84 /// Monotonic microseconds when the first response byte arrived.
85 pub received_us: u64,
86 /// The `Date` header (the time of an `http-head` exchange).
87 pub date: Option<&'a str>,
88 /// The body, empty for a `HEAD`.
89 pub body: &'a [u8],
90}
91
92impl<'a> UtcResponse<'a> {
93 /// A response with a body and no `Date`.
94 #[must_use]
95 pub fn new(sent_us: u64, received_us: u64, body: &'a [u8]) -> Self {
96 Self {
97 sent_us,
98 received_us,
99 date: None,
100 body,
101 }
102 }
103
104 /// Set the `Date` header.
105 #[must_use]
106 pub fn with_date(mut self, date: &'a str) -> Self {
107 self.date = Some(date);
108 self
109 }
110}