actori_http/header/common/accept.rs
1use mime::Mime;
2
3use crate::header::{qitem, QualityItem};
4use crate::http::header;
5
6header! {
7 /// `Accept` header, defined in [RFC7231](http://tools.ietf.org/html/rfc7231#section-5.3.2)
8 ///
9 /// The `Accept` header field can be used by user agents to specify
10 /// response media types that are acceptable. Accept header fields can
11 /// be used to indicate that the request is specifically limited to a
12 /// small set of desired types, as in the case of a request for an
13 /// in-line image
14 ///
15 /// # ABNF
16 ///
17 /// ```text
18 /// Accept = #( media-range [ accept-params ] )
19 ///
20 /// media-range = ( "*/*"
21 /// / ( type "/" "*" )
22 /// / ( type "/" subtype )
23 /// ) *( OWS ";" OWS parameter )
24 /// accept-params = weight *( accept-ext )
25 /// accept-ext = OWS ";" OWS token [ "=" ( token / quoted-string ) ]
26 /// ```
27 ///
28 /// # Example values
29 /// * `audio/*; q=0.2, audio/basic`
30 /// * `text/plain; q=0.5, text/html, text/x-dvi; q=0.8, text/x-c`
31 ///
32 /// # Examples
33 /// ```rust
34 /// # extern crate actori_http;
35 /// extern crate mime;
36 /// use actori_http::Response;
37 /// use actori_http::http::header::{Accept, qitem};
38 ///
39 /// # fn main() {
40 /// let mut builder = Response::Ok();
41 ///
42 /// builder.set(
43 /// Accept(vec![
44 /// qitem(mime::TEXT_HTML),
45 /// ])
46 /// );
47 /// # }
48 /// ```
49 ///
50 /// ```rust
51 /// # extern crate actori_http;
52 /// extern crate mime;
53 /// use actori_http::Response;
54 /// use actori_http::http::header::{Accept, qitem};
55 ///
56 /// # fn main() {
57 /// let mut builder = Response::Ok();
58 ///
59 /// builder.set(
60 /// Accept(vec![
61 /// qitem(mime::APPLICATION_JSON),
62 /// ])
63 /// );
64 /// # }
65 /// ```
66 ///
67 /// ```rust
68 /// # extern crate actori_http;
69 /// extern crate mime;
70 /// use actori_http::Response;
71 /// use actori_http::http::header::{Accept, QualityItem, q, qitem};
72 ///
73 /// # fn main() {
74 /// let mut builder = Response::Ok();
75 ///
76 /// builder.set(
77 /// Accept(vec![
78 /// qitem(mime::TEXT_HTML),
79 /// qitem("application/xhtml+xml".parse().unwrap()),
80 /// QualityItem::new(
81 /// mime::TEXT_XML,
82 /// q(900)
83 /// ),
84 /// qitem("image/webp".parse().unwrap()),
85 /// QualityItem::new(
86 /// mime::STAR_STAR,
87 /// q(800)
88 /// ),
89 /// ])
90 /// );
91 /// # }
92 /// ```
93 (Accept, header::ACCEPT) => (QualityItem<Mime>)+
94
95 test_accept {
96 // Tests from the RFC
97 test_header!(
98 test1,
99 vec![b"audio/*; q=0.2, audio/basic"],
100 Some(HeaderField(vec![
101 QualityItem::new("audio/*".parse().unwrap(), q(200)),
102 qitem("audio/basic".parse().unwrap()),
103 ])));
104 test_header!(
105 test2,
106 vec![b"text/plain; q=0.5, text/html, text/x-dvi; q=0.8, text/x-c"],
107 Some(HeaderField(vec![
108 QualityItem::new(mime::TEXT_PLAIN, q(500)),
109 qitem(mime::TEXT_HTML),
110 QualityItem::new(
111 "text/x-dvi".parse().unwrap(),
112 q(800)),
113 qitem("text/x-c".parse().unwrap()),
114 ])));
115 // Custom tests
116 test_header!(
117 test3,
118 vec![b"text/plain; charset=utf-8"],
119 Some(Accept(vec![
120 qitem(mime::TEXT_PLAIN_UTF_8),
121 ])));
122 test_header!(
123 test4,
124 vec![b"text/plain; charset=utf-8; q=0.5"],
125 Some(Accept(vec![
126 QualityItem::new(mime::TEXT_PLAIN_UTF_8,
127 q(500)),
128 ])));
129
130 #[test]
131 fn test_fuzzing1() {
132 use crate::test::TestRequest;
133 let req = TestRequest::with_header(crate::header::ACCEPT, "chunk#;e").finish();
134 let header = Accept::parse(&req);
135 assert!(header.is_ok());
136 }
137 }
138}
139
140impl Accept {
141 /// A constructor to easily create `Accept: */*`.
142 pub fn star() -> Accept {
143 Accept(vec![qitem(mime::STAR_STAR)])
144 }
145
146 /// A constructor to easily create `Accept: application/json`.
147 pub fn json() -> Accept {
148 Accept(vec![qitem(mime::APPLICATION_JSON)])
149 }
150
151 /// A constructor to easily create `Accept: text/*`.
152 pub fn text() -> Accept {
153 Accept(vec![qitem(mime::TEXT_STAR)])
154 }
155
156 /// A constructor to easily create `Accept: image/*`.
157 pub fn image() -> Accept {
158 Accept(vec![qitem(mime::IMAGE_STAR)])
159 }
160}