/rust/registry/src/index.crates.io-6f17d22bba15001f/http-1.3.1/src/uri/builder.rs
Line | Count | Source (jump to first uncovered line) |
1 | | use std::convert::TryInto; |
2 | | |
3 | | use super::{Authority, Parts, PathAndQuery, Scheme}; |
4 | | use crate::Uri; |
5 | | |
6 | | /// A builder for `Uri`s. |
7 | | /// |
8 | | /// This type can be used to construct an instance of `Uri` |
9 | | /// through a builder pattern. |
10 | | #[derive(Debug)] |
11 | | pub struct Builder { |
12 | | parts: Result<Parts, crate::Error>, |
13 | | } |
14 | | |
15 | | impl Builder { |
16 | | /// Creates a new default instance of `Builder` to construct a `Uri`. |
17 | | /// |
18 | | /// # Examples |
19 | | /// |
20 | | /// ``` |
21 | | /// # use http::*; |
22 | | /// |
23 | | /// let uri = uri::Builder::new() |
24 | | /// .scheme("https") |
25 | | /// .authority("hyper.rs") |
26 | | /// .path_and_query("/") |
27 | | /// .build() |
28 | | /// .unwrap(); |
29 | | /// ``` |
30 | | #[inline] |
31 | 0 | pub fn new() -> Builder { |
32 | 0 | Builder::default() |
33 | 0 | } Unexecuted instantiation: <http::uri::builder::Builder>::new Unexecuted instantiation: <http::uri::builder::Builder>::new |
34 | | |
35 | | /// Set the `Scheme` for this URI. |
36 | | /// |
37 | | /// # Examples |
38 | | /// |
39 | | /// ``` |
40 | | /// # use http::*; |
41 | | /// |
42 | | /// let mut builder = uri::Builder::new(); |
43 | | /// builder.scheme("https"); |
44 | | /// ``` |
45 | 0 | pub fn scheme<T>(self, scheme: T) -> Self |
46 | 0 | where |
47 | 0 | T: TryInto<Scheme>, |
48 | 0 | <T as TryInto<Scheme>>::Error: Into<crate::Error>, |
49 | 0 | { |
50 | 0 | self.map(move |mut parts| { |
51 | 0 | let scheme = scheme.try_into().map_err(Into::into)?; |
52 | 0 | parts.scheme = Some(scheme); |
53 | 0 | Ok(parts) |
54 | 0 | }) Unexecuted instantiation: <http::uri::builder::Builder>::scheme::<http::uri::scheme::Scheme>::{closure#0} Unexecuted instantiation: <http::uri::builder::Builder>::scheme::<_>::{closure#0} |
55 | 0 | } Unexecuted instantiation: <http::uri::builder::Builder>::scheme::<http::uri::scheme::Scheme> Unexecuted instantiation: <http::uri::builder::Builder>::scheme::<_> |
56 | | |
57 | | /// Set the `Authority` for this URI. |
58 | | /// |
59 | | /// # Examples |
60 | | /// |
61 | | /// ``` |
62 | | /// # use http::*; |
63 | | /// |
64 | | /// let uri = uri::Builder::new() |
65 | | /// .authority("tokio.rs") |
66 | | /// .build() |
67 | | /// .unwrap(); |
68 | | /// ``` |
69 | 0 | pub fn authority<T>(self, auth: T) -> Self |
70 | 0 | where |
71 | 0 | T: TryInto<Authority>, |
72 | 0 | <T as TryInto<Authority>>::Error: Into<crate::Error>, |
73 | 0 | { |
74 | 0 | self.map(move |mut parts| { |
75 | 0 | let auth = auth.try_into().map_err(Into::into)?; |
76 | 0 | parts.authority = Some(auth); |
77 | 0 | Ok(parts) |
78 | 0 | }) Unexecuted instantiation: <http::uri::builder::Builder>::authority::<http::uri::authority::Authority>::{closure#0} Unexecuted instantiation: <http::uri::builder::Builder>::authority::<_>::{closure#0} |
79 | 0 | } Unexecuted instantiation: <http::uri::builder::Builder>::authority::<http::uri::authority::Authority> Unexecuted instantiation: <http::uri::builder::Builder>::authority::<_> |
80 | | |
81 | | /// Set the `PathAndQuery` for this URI. |
82 | | /// |
83 | | /// # Examples |
84 | | /// |
85 | | /// ``` |
86 | | /// # use http::*; |
87 | | /// |
88 | | /// let uri = uri::Builder::new() |
89 | | /// .path_and_query("/hello?foo=bar") |
90 | | /// .build() |
91 | | /// .unwrap(); |
92 | | /// ``` |
93 | 0 | pub fn path_and_query<T>(self, p_and_q: T) -> Self |
94 | 0 | where |
95 | 0 | T: TryInto<PathAndQuery>, |
96 | 0 | <T as TryInto<PathAndQuery>>::Error: Into<crate::Error>, |
97 | 0 | { |
98 | 0 | self.map(move |mut parts| { |
99 | 0 | let p_and_q = p_and_q.try_into().map_err(Into::into)?; |
100 | 0 | parts.path_and_query = Some(p_and_q); |
101 | 0 | Ok(parts) |
102 | 0 | }) Unexecuted instantiation: <http::uri::builder::Builder>::path_and_query::<http::uri::path::PathAndQuery>::{closure#0} Unexecuted instantiation: <http::uri::builder::Builder>::path_and_query::<&str>::{closure#0} Unexecuted instantiation: <http::uri::builder::Builder>::path_and_query::<_>::{closure#0} |
103 | 0 | } Unexecuted instantiation: <http::uri::builder::Builder>::path_and_query::<http::uri::path::PathAndQuery> Unexecuted instantiation: <http::uri::builder::Builder>::path_and_query::<&str> Unexecuted instantiation: <http::uri::builder::Builder>::path_and_query::<_> |
104 | | |
105 | | /// Consumes this builder, and tries to construct a valid `Uri` from |
106 | | /// the configured pieces. |
107 | | /// |
108 | | /// # Errors |
109 | | /// |
110 | | /// This function may return an error if any previously configured argument |
111 | | /// failed to parse or get converted to the internal representation. For |
112 | | /// example if an invalid `scheme` was specified via `scheme("!@#%/^")` |
113 | | /// the error will be returned when this function is called rather than |
114 | | /// when `scheme` was called. |
115 | | /// |
116 | | /// Additionally, the various forms of URI require certain combinations of |
117 | | /// parts to be set to be valid. If the parts don't fit into any of the |
118 | | /// valid forms of URI, a new error is returned. |
119 | | /// |
120 | | /// # Examples |
121 | | /// |
122 | | /// ``` |
123 | | /// # use http::*; |
124 | | /// |
125 | | /// let uri = Uri::builder() |
126 | | /// .build() |
127 | | /// .unwrap(); |
128 | | /// ``` |
129 | 0 | pub fn build(self) -> Result<Uri, crate::Error> { |
130 | 0 | let parts = self.parts?; |
131 | 0 | Uri::from_parts(parts).map_err(Into::into) |
132 | 0 | } |
133 | | |
134 | | // private |
135 | | |
136 | 0 | fn map<F>(self, func: F) -> Self |
137 | 0 | where |
138 | 0 | F: FnOnce(Parts) -> Result<Parts, crate::Error>, |
139 | 0 | { |
140 | 0 | Builder { |
141 | 0 | parts: self.parts.and_then(func), |
142 | 0 | } |
143 | 0 | } Unexecuted instantiation: <http::uri::builder::Builder>::map::<<http::uri::builder::Builder>::path_and_query<http::uri::path::PathAndQuery>::{closure#0}> Unexecuted instantiation: <http::uri::builder::Builder>::map::<<http::uri::builder::Builder>::path_and_query<&str>::{closure#0}> Unexecuted instantiation: <http::uri::builder::Builder>::map::<<http::uri::builder::Builder>::scheme<http::uri::scheme::Scheme>::{closure#0}> Unexecuted instantiation: <http::uri::builder::Builder>::map::<<http::uri::builder::Builder>::authority<http::uri::authority::Authority>::{closure#0}> Unexecuted instantiation: <http::uri::builder::Builder>::map::<_> |
144 | | } |
145 | | |
146 | | impl Default for Builder { |
147 | | #[inline] |
148 | 0 | fn default() -> Builder { |
149 | 0 | Builder { |
150 | 0 | parts: Ok(Parts::default()), |
151 | 0 | } |
152 | 0 | } Unexecuted instantiation: <http::uri::builder::Builder as core::default::Default>::default Unexecuted instantiation: <http::uri::builder::Builder as core::default::Default>::default |
153 | | } |
154 | | |
155 | | impl From<Uri> for Builder { |
156 | 0 | fn from(uri: Uri) -> Self { |
157 | 0 | Self { |
158 | 0 | parts: Ok(uri.into_parts()), |
159 | 0 | } |
160 | 0 | } |
161 | | } |
162 | | |
163 | | #[cfg(test)] |
164 | | mod tests { |
165 | | use super::*; |
166 | | |
167 | | #[test] |
168 | | fn build_from_str() { |
169 | | let uri = Builder::new() |
170 | | .scheme(Scheme::HTTP) |
171 | | .authority("hyper.rs") |
172 | | .path_and_query("/foo?a=1") |
173 | | .build() |
174 | | .unwrap(); |
175 | | assert_eq!(uri.scheme_str(), Some("http")); |
176 | | assert_eq!(uri.authority().unwrap().host(), "hyper.rs"); |
177 | | assert_eq!(uri.path(), "/foo"); |
178 | | assert_eq!(uri.query(), Some("a=1")); |
179 | | } |
180 | | |
181 | | #[test] |
182 | | fn build_from_string() { |
183 | | for i in 1..10 { |
184 | | let uri = Builder::new() |
185 | | .path_and_query(format!("/foo?a={}", i)) |
186 | | .build() |
187 | | .unwrap(); |
188 | | let expected_query = format!("a={}", i); |
189 | | assert_eq!(uri.path(), "/foo"); |
190 | | assert_eq!(uri.query(), Some(expected_query.as_str())); |
191 | | } |
192 | | } |
193 | | |
194 | | #[test] |
195 | | fn build_from_string_ref() { |
196 | | for i in 1..10 { |
197 | | let p_a_q = format!("/foo?a={}", i); |
198 | | let uri = Builder::new().path_and_query(&p_a_q).build().unwrap(); |
199 | | let expected_query = format!("a={}", i); |
200 | | assert_eq!(uri.path(), "/foo"); |
201 | | assert_eq!(uri.query(), Some(expected_query.as_str())); |
202 | | } |
203 | | } |
204 | | |
205 | | #[test] |
206 | | fn build_from_uri() { |
207 | | let original_uri = Uri::default(); |
208 | | let uri = Builder::from(original_uri.clone()).build().unwrap(); |
209 | | assert_eq!(original_uri, uri); |
210 | | } |
211 | | } |