headers/common/
access_control_allow_methods.rs

1use std::iter::FromIterator;
2
3use http::Method;
4
5use util::FlatCsv;
6
7/// `Access-Control-Allow-Methods` header, part of
8/// [CORS](http://www.w3.org/TR/cors/#access-control-allow-methods-response-header)
9///
10/// The `Access-Control-Allow-Methods` header indicates, as part of the
11/// response to a preflight request, which methods can be used during the
12/// actual request.
13///
14/// # ABNF
15///
16/// ```text
17/// Access-Control-Allow-Methods: "Access-Control-Allow-Methods" ":" #Method
18/// ```
19///
20/// # Example values
21/// * `PUT, DELETE, XMODIFY`
22///
23/// # Examples
24///
25/// ```
26/// # extern crate headers;
27/// extern crate http;
28/// use http::Method;
29/// use headers::AccessControlAllowMethods;
30///
31/// let allow_methods = vec![Method::GET, Method::PUT]
32///     .into_iter()
33///     .collect::<AccessControlAllowMethods>();
34/// ```
35#[derive(Clone, Debug, PartialEq)]
36pub struct AccessControlAllowMethods(FlatCsv);
37
38derive_header! {
39    AccessControlAllowMethods(_),
40    name: ACCESS_CONTROL_ALLOW_METHODS
41}
42
43impl AccessControlAllowMethods {
44    /// Returns an iterator over `Method`s contained within.
45    pub fn iter<'a>(&'a self) -> impl Iterator<Item = Method> + 'a {
46        self.0.iter().filter_map(|s| s.parse().ok())
47    }
48}
49
50impl FromIterator<Method> for AccessControlAllowMethods {
51    fn from_iter<I>(iter: I) -> Self
52    where
53        I: IntoIterator<Item = Method>,
54    {
55        let methods = iter
56            .into_iter()
57            .map(|method| {
58                method
59                    .as_str()
60                    .parse::<::HeaderValue>()
61                    .expect("Method is a valid HeaderValue")
62            })
63            .collect();
64
65        AccessControlAllowMethods(methods)
66    }
67}
68
69#[cfg(test)]
70mod tests {
71    use super::super::{test_decode, test_encode};
72    use super::*;
73
74    #[test]
75    fn iter() {
76        let allowed = test_decode::<AccessControlAllowMethods>(&["GET, PUT"]).unwrap();
77
78        let as_vec = allowed.iter().collect::<Vec<_>>();
79        assert_eq!(as_vec.len(), 2);
80        assert_eq!(as_vec[0], Method::GET);
81        assert_eq!(as_vec[1], Method::PUT);
82    }
83
84    #[test]
85    fn from_iter() {
86        let allow: AccessControlAllowMethods = vec![Method::GET, Method::PUT].into_iter().collect();
87
88        let headers = test_encode(allow);
89        assert_eq!(headers["access-control-allow-methods"], "GET, PUT");
90    }
91}